carbon-addons-iot-react bundle size too big - javascript

I have an CRA typescript installiation and I'm using carbon-addons-iot-react design library.
https://github.com/carbon-design-system/carbon-addons-iot-react
When i check with source-map-explorer i saw my bundle size extremely big because of the carbon-addons-iot-react imports watson icon in a odd way.
You can see it in picture;
source-map
I tried to tree-shaking way to import icons inside my components
import { Add16 } from "#carbon/icons-react"; //this to
import Add from "#carbon/icons-react/es/add/16"; //this
but i think the reason is the way carbon-addons-iot-react imports icons.
I also tried route based code splitting but it's not reducing bucket sizes.
sizes-after-build
I research a little bit for _generated folder and why it's too big. But i can't find anything on the web or issues on their repository. They use PURE React.CreateElement inside buckets, but for some reason my webpack cant threeshake on them if it's the problem.
Anybody have some ideas?
Thank you very much.

We had a similar issue to this and tracked it down to an import of components from UIShell, which was causing the whole icons library to be included in the bundle.
Switch any full path imports from UIShell to import from the top level instead.
Before:
import { HeaderNavigation } from "carbon-components-react/lib/components/UIShell";
After:
import { HeaderNavigation } from "carbon-components-react";

Related

How to stop import of node modules with relative paths in React, VS code

I have been using VS code for my React development for over a month now and everything was okay, until recently i noticed something odd, about how node modules were imported in project.
Initially, they were imported as follows, which i believe is the right way:
import { useNavigate } from "react-router-dom";
But now, they are imported like:
import { useNavigate } from "../../../node_modules/react-router-dom/index";
Please help, how can I revert this behaviour.
I have found a solution to this problem from the VS code GitHub issues section.
This was an issue caused by an extension i installed - "Babel Javascript".
According to this comment, I had to switch the language in the bottom bar of VS code being detected from Babel Javascript to Javascript. that solved the issue.
To prevent the issue from recurring, i also disabled the Babel Javascript plugin.

exporting .png files from a library to a React JavaScript project

I'm creating a utility project that will supply React components and resources to my other projects.
I'd like it to include a set of images (mostly .png files for icons) that can then be imported by the child projects.
I can't figure out how to make this work.
I can export the images from the library, and I can see them, name-mangled, in the node_modules of the child project. So, all good so far.
But, import {imgName} from "myLib" does not include the file in the child project's bundle.
It looks to me like my problem is explained by a clue in https://create-react-app.dev/docs/adding-images-fonts-and-files/:
You can import a file right in a JavaScript module. This tells
webpack to include that file in the bundle.
Presumably, CRA is not triggering this webpack behavior in my case, since I'm importing from another module, not from a file.
How can I get things working?
Assume:
I have complete ownership of the library and child projects, so I can change this solution in whatever way works. I just want to have a single common resource for the images.
I don't want to eject my child projects
Ideally, any complexity should be in the library project. The child projects should have minimal complex tooling. (My intent is for this library to be used by a team of other developers, who will want to focus on their own tasks; not on tooling details)
EDIT (ADDED LATER)
Per the comments in the first answer below, I've created a simple example of my problem. See:
Library repo: github.com/deg/media-file-bug-library
Library package: npmjs.com/package/media-file-bug-library
Client repo: github.com/deg/media-file-bug-client
Just pull the client repo and do yarn install and yarn start. This will bring up a little web page that shows the problem:
SCREEN SNAPSHOT:
The Problem is Not in CRA Trigger. Importing Png File like JavaScript Hides a Magic. Here you are importing a Image and Exporting it which then get Processed by bundler and The Bundled Index Actually Exports The name of the Processed Image File Which in Your Case is corss~nAalnlvj.png. That's Why Your Image is Broken but you are able to render name of File, The Case is Same for microbundle or parcel.
How You Can solve it is by separating your assets and components By Placing Images on separate assets folder and place your images there and then add assets to files in your files in package.json
{
.
.
"files": [ "dist", "assets"],
}
And Then Import Image & Using Like This
import React from 'react'
import ico_cross from 'media-file-bug-library-fix/assets/cross.png'
function App() {
return (
<div className="App">
<img src={ico_cross} alt="im"/>
</div>
);
}
For Further Reference Checkout
Here
A Npm Library For Your Fix I Published Npm media-file-bug-library-fix
enter image description here
hey David I found the solution please do check the above screenshot
as in you package just change in index.modern.js
// WebPack doesnt listen as a path it listen
// var cross = "cross~nAalnlvj.png";
// use import rather than simple name as it generate a full absolute path at parent level so that in child level it can be accessible as an Image
import cross from "./cross~nAalnlvj.png"

How to export a submodule in a Typescript library

So my goal is to create a library in Typescript. My intention is to split up core parts of the library into submodules like RxJS or Angular Material.
RxJS and Angular both support imports like so:
// RxJS
import { map, filter } from 'rxjs/operators';
// Angular
import { MatButtonModule } from '#angular/material/button';
However, I am unable to replicate this myself.
My goal is to do something similar and allow you to import a class with import { foo } from 'package/bar;
I have looked at RxJS's source on Github and have tried replicating what they've done but it's not working.
The library compiles fine but when I go about importing it I always get a Cannot resolve dependency 'package/foo' error.
Meanwhile doing import { test } from package (without the submodule part) works completely fine.
I've tried using paths in tsconfig to no avail. If that is the answer then I'm doing it wrong.
How do I go about doing this?
In order to achieve that, you can create your "sub-modules" in different directories (although they are technically part of the same module), and create an index.ts on each of those directories exporting there whatever you want to publish.
For example, I have done this in my NodeJs package Flowed, and you can for example do this:
import { FlowManager } from 'flowed/dist/engine';
Where the corresponding index.ts file is this one if you want to check.
Although in my case I put also available all the stuff from the root, so the previous line would be equivalent to:
import { FlowManager } from 'flowed';

How to import from '#somefolder' in angular

I was going through someone's code and found this:
import { NGSWUpdateService } from '#ngsw/ngsw-update.service';
The developer has been able to use '#ngsw/ngsw-update.service' instead of original very long path 'src/client/app/shared/ngsw/ngsw-update.service'.
So how to implement the above so that I don't have to import from relatively long paths.
Here's the code.
When you import from a path that is not relative, it'll look into the node_modules folder.
So here, it's just looking for the file ngsw-update.service here: node_modules/#ngsw/ngsw-update.service.
That's the most basic use case but you can only use that those kind of paths with files from your project by defining them into tsconfig.json (within compilerOptions.paths`, see that article for more: https://netbasal.com/sexier-imports-in-typescript-e3c645bdd3c6

What's the behavior of webpack imports in ReactJS project?

I've used multiple 3rd party libraries in my ReactJS project like lodash, d3 etc. I just found out that I've not written explicit imports
like
import d3 from 'd3'
or import _ from 'lodash'
in all my components (I've imported them in some though). Yet it all works fine and I can also get the d3 object and _ in the browser console. How is it supposed to be?
Considering this is okay behavior can I just import the node_modules dependencies for react only once in my App(Root) Component and don't import them at all in all the other child components.
P.S I'm using webpack 1 and I've verified the behavior.
Even when it works, it is a bad practice, so my advice would be to play nice and always explicitly import modules you are using.
The reason why it is working is probably because some of those modules declare globals when they are imported, so your components that do not import them still reach global.

Categories