Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

External package using styled-components and tree shaking (preserveModules/input): "Cannot read properties of undefined (reading 'withConfig')" #170

Open
danielchoragwicki opened this issue Oct 29, 2024 · 7 comments

Comments

@danielchoragwicki
Copy link

When I add styled-components to shared and import a component with styled-components from an external package, I get an error: Uncaught TypeError: Cannot read properties of undefined (reading 'withConfig'). It doesn't matter whether I import the component into the host or remote, the situation is the same.

I have prepared a simple repo with this issue: https://github.com/danielchoragwicki/module-federation-with-config-bug/
You have to add the external package (here: example-styled-components-package) to vite-host using yalc, and then run the projects.

Screenshot 2024-10-29 at 17 45 51

Yalc is used just for demo, but this problem occurs with any own package that uses styled-components in my project installing via npm. My packages have a similar configuration to example-styled-components-package.

I also noticed that the package added by yalc with the --link flag (yalc add example-styled-components-package --link) doesn't cause the problem.

@danielchoragwicki danielchoragwicki changed the title External package with styled-components: Uncaught TypeError: Cannot read properties of undefined (reading 'withConfig') External package with styled-components: "Uncaught TypeError: Cannot read properties of undefined (reading 'withConfig')" Oct 29, 2024
@gioboa
Copy link
Collaborator

gioboa commented Oct 29, 2024

Thanks @danielchoragwicki for the exhaustive description. I'll look into it to identify the problem.

---- UPDATE ----

image

The problem is button => undefined

@danielchoragwicki
Copy link
Author

Ok, but why does it work when I remove styled-components from shared in remote/host?

Screenshot 2024-10-31 at 13 22 27 Screenshot 2024-10-31 at 13 24 47

@gioboa
Copy link
Collaborator

gioboa commented Oct 31, 2024

That's a good question, can you try to debug and check the styled object in both cases please?

@danielchoragwicki
Copy link
Author

I’m not sure how to approach debugging this issue. I can’t log the styled object when the error occurs. Additionally, in preview mode (after the build), the issue doesn’t occur, so it’s only a problem in dev mode.

When styled-components is not present in shared (when the app is running), the code in the bundle looks like this and imports esm:

// example-styled-components-package.js?v=5adf8547
var ExampleButtonElement = styled_components_browser_esm_default.button.withConfig({
  displayName: "ExampleButtonstyled__ExampleButtonElement",
  componentId: "sc-1bjgygh-0"
})(["", ""], () => Ce(["background:red;border:0;margin:0;padding:20px;"]));

On the other hand, when the styled-component is placed in shared and doesn’t work:

// example-styled-components-package.js?v=b5947703
var import_styled_components = __toESM(require_viteViteHost_loadShare_styled_mf_2_components_loadShare(), 1);
var ExampleButtonElement = import_styled_components.default.button.withConfig({
  displayName: "ExampleButtonstyled__ExampleButtonElement",
  componentId: "sc-1bjgygh-0"
})(["", ""], () => (0, import_styled_components.css)(["background:red;border:0;margin:0;padding:20px;"]));
// node_modules/__mf__virtual/viteViteHost__loadShare__styled_mf_2_components__loadShare__.js
var require_viteViteHost_loadShare_styled_mf_2_components_loadShare = __commonJS({
    "node_modules/__mf__virtual/viteViteHost__loadShare__styled_mf_2_components__loadShare__.js"(exports, module) {
        var {loadShare} = require_index_cjs();
        var {initPromise} = require_viteViteHost_mf_v_runtimeInit_mf_v();
        var res = initPromise.then( (_) => loadShare("styled-components", {
            customShareInfo: {
                shareConfig: {
                    singleton: true,
                    strictVersion: false,
                    requiredVersion: "^5.3.3"
                }
            }
        }));
        var exportModule = (/*mf top-level-await placeholder replacement mf*/
        res.then( (factory) => factory()));
        module.exports = exportModule;
    }
});

const __mfproxy__awaitrequire_viteViteHost_loadShare_styled_mf_2_components_loadShare = await require_viteViteHost_loadShare_styled_mf_2_components_loadShare();
const __mfproxy__require_viteViteHost_loadShare_styled_mf_2_components_loadShare = () => __mfproxy__awaitrequire_viteViteHost_loadShare_styled_mf_2_components_loadShare;

export {__mfproxy__require_viteViteHost_loadShare_styled_mf_2_components_loadShare as require_viteViteHost_loadShare_styled_mf_2_components_loadShare};

@gioboa
Copy link
Collaborator

gioboa commented Nov 6, 2024

To unblock you, as a workaround, you can use this check command.mode === 'production' to add styled-components only in preview mode.

eg.

export default defineConfig((command) => {
  return {
    plugins: [
      federation({
        [...]
        shared: command.mode === 'production' ? { ... } : { ... }
      })  
    ],
});

@danielchoragwicki
Copy link
Author

We have found a clue about what causes this issue. It occurs when our external packages, which use styled-components, have the output.preserveModules option enabled in their vite config (https://rollupjs.org/configuration-options/#output-preservemodules) or when the input option is specified instead (https://rollupjs.org/configuration-options/#input). However, we need one of these options to enable tree-shaking and create separate chunks for all modules.

@danielchoragwicki danielchoragwicki changed the title External package with styled-components: "Uncaught TypeError: Cannot read properties of undefined (reading 'withConfig')" External package using styled-components and preserveModules/input: "Cannot read properties of undefined (reading 'withConfig')" Nov 15, 2024
@gioboa
Copy link
Collaborator

gioboa commented Nov 15, 2024

Thanks for your commitment 👏
I see, we definitely need to find a solution for that.

@danielchoragwicki danielchoragwicki changed the title External package using styled-components and preserveModules/input: "Cannot read properties of undefined (reading 'withConfig')" External package using styled-components and tree shaking (preserveModules/input): "Cannot read properties of undefined (reading 'withConfig')" Dec 3, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants