module-federation-examples icon indicating copy to clipboard operation
module-federation-examples copied to clipboard

Dynamic shared runtime exposed with Store lost shared data

Open ytytsophia opened this issue 1 year ago • 8 comments

App1 and App2 are in different git repository App1 expose app1/getProjectId like :

class Store<T> {
  _value: T;

  set value(value: T) {
    this._value = value;
  }

  get value() {
    return this._value;
  }
}
const projectIdStore = new Store<string | undefined>();

const getProjectId = () => projectIdStore.value;

export const setProjectId = (value: string | undefined) =>
  (projectIdStore.value = value);
export default getProjectId;

I call setProjectId('1') in App1, and make app1/getProjectId shared in init functions like

shared: {
        react: {
          version: '17.0.2',
          scope: 'default',
          lib: () => React,
          shareConfig: {
            singleton: true,
            requiredVersion: '^17.0.2',
          },
        },
        'react-dom': {
          version: '17.0.2',
          scope: 'default',
          lib: () => ReactDOM,
          shareConfig: {
            singleton: true,
            requiredVersion: '^17.0.2',
          },
        },
        'project/getProjectId': {
          shareConfig: {
            singleton: true,
            requiredVersion: '^1.0.0',
          },
        },
      },

which I expect is in App2 , when I call app1/getProjectId, I can get the value which I set in App1 before, but I got undefined What should I suppose to do ? Thanks

ytytsophia avatar Sep 18 '24 11:09 ytytsophia

I saw https://github.com/module-federation/core/pull/2960/commits/ff5f03e1df14e925ec9521b8a2816f0a150be61b, Will this changes solve my problem? @ScriptedAlchemy

ytytsophia avatar Sep 18 '24 12:09 ytytsophia

Do you import the store as an exposed module, but the host also uses it? Is the host's remote entry loaded on the page as well?

ScriptedAlchemy avatar Sep 18 '24 20:09 ScriptedAlchemy

This is likely because the host has its own runtime, and so does the host's remote. So when importing an exposed module or using the "host's own remote" pattern, the exposed module in the remote entry runtime is empty. Since the host is using the module in its runtime graph and not its remotes, there are two instances of the module:

  1. In the host's main.js webpack module cache
  2. In the remote entry module cache

You can try runtimeChunk: single and can look at the single runtime chunk example for webpack-based builds in runtime plug-ins of the examples repository.

ScriptedAlchemy avatar Sep 18 '24 20:09 ScriptedAlchemy

Thanks for response But if I set runtimeChunk : single in optimization, I got errors like image and the building got stuck, When I used webpack/lib/container/ModuleFederationPlugin , there were no errors

ytytsophia avatar Sep 19 '24 02:09 ytytsophia

I wonder if the new plugin : '@module-federation/enhanced/webpack' implicitly set runtime false ?

ytytsophia avatar Sep 19 '24 02:09 ytytsophia

I set the runtime as false when i detect single runtime chunk. in webpack it should create a partial chunk or on later version now of enhanced, it should bundle the remote into the host runtime, so that by loading th host webpack runtime, it has side effect of setting get,init on the global interface to you never need to load the hosts own remote.js - this is how i do it in next.js

ScriptedAlchemy avatar Sep 29 '24 22:09 ScriptedAlchemy

We have now switched from Webpack to Rsbuild, but I’ve found that the problem still persists: the host and remote are not sharing the runtime. Note that runtimeChunk: 'single' is set in the optimization configuration.

ytytsophia avatar Oct 10 '24 08:10 ytytsophia

provide repo

ScriptedAlchemy avatar Oct 10 '24 20:10 ScriptedAlchemy