callstack / repack

A Webpack-based toolkit to build your React Native application with full support of Webpack ecosystem.
https://re-pack.dev
MIT License
1.46k stars 105 forks source link

Android Error when navigate Between MFEs #478

Closed nazrighazi-cd closed 8 months ago

nazrighazi-cd commented 9 months ago

Hi, I am getting this error when navigating between two MFEs.

image

I have two MFEs which is A and B. Both MFEs have multiple screens.

MFE A

MFE B

So, in my host app, I have one screen which list out icons to navigate to all screen in both MFEs. What happened is that when I navigate to screen A (MFE A), D (MFE B) and then try to navigate to screen B (MFE A), I am getting the error, and this is only happened on android devices.

Let say I'm navigating to screen A,B,C ( navigate to all screens in MFE A first ) and then navigate to screen D and back to screen A,B,C, I'm not getting the error anymore.

screen A -> navigate back -> screen D -> navigate back -> screen B = Error

Is this related to re.pack or react navigation?

jbroma commented 9 months ago

Hi @nazrighazi-cd,

It looks like an issue with configuration of webpack rather than a react-navigation issue. With the information you've provided, I think it might have to do with a dependency that's being shared, can you please share your MF configuration in both MFEs?

jbroma commented 9 months ago

I'll check it in the super-app-showcase as you reported that error there as well

https://github.com/callstack/super-app-showcase/issues/78

nazrighazi-cd commented 9 months ago

Here is my webpack

import path from 'path'; import TerserPlugin from 'terser-webpack-plugin'; import * as Repack from '@callstack/repack';

export default (env) => { const { mode = 'development', context = Repack.getDirname(import.meta.url), entry = './index.js', platform = process.env.PLATFORM, minimize = mode === 'production', devServer = undefined, bundleFilename = undefined, sourceMapFilename = undefined, assetsPath = undefined, reactNativePath = new URL('./node_modules/react-native', import.meta.url) .pathname, } = env; const dirname = Repack.getDirname(import.meta.url);

if (!platform) { throw new Error('Missing platform'); }

process.env.BABEL_ENV = mode;

return { mode, devtool: false, context, entry: [ ...Repack.getInitializationEntries(reactNativePath, { hmr: devServer && devServer.hmr, }), entry, ], resolve: { ...Repack.getResolveOptions(platform), alias: { 'react-native': reactNativePath, '@cd-next-gen-app/ui-components': new URL( '../../../libs/ui-components/src/index.ts', import.meta.url ).pathname, '@cd-next-gen-app/icons': new URL( '../../../libs/icons/src/index.ts', import.meta.url ).pathname, '@cd-next-gen-app/themes': new URL( '../../../libs/themes/src/index.ts', import.meta.url ).pathname, '@cd-next-gen-app/store': new URL( '../store/src/index.ts', import.meta.url ).pathname, '@cd-next-gen-app/containers': new URL( '../../../libs/containers/src/index.ts', import.meta.url ).pathname, '@cd-next-gen-app/components': new URL( '../../../libs/components/src/index.ts', import.meta.url ).pathname, }, },

output: {
  clean: true,
  hashFunction: 'xxhash64',
  path: path.join(dirname, 'build/generated', platform),
  filename: 'index.bundle',
  chunkFilename: '[name].chunk.bundle',
  publicPath: Repack.getPublicPath({ platform, devServer }),
},
optimization: {
  /** Enables minification based on values passed from React Native CLI or from fallback. */
  minimize,
  /** Configure minimizer to process the bundle. */
  minimizer: [
    new TerserPlugin({
      test: /\.(js)?bundle(\?.*)?$/i,
      extractComments: false,
      terserOptions: {
        format: {
          comments: false,
        },
      },
    }),
  ],
  chunkIds: 'named',
},
module: {
  rules: [
    {
      test: /\.[jt]sx?$/,
      include: [
        /node_modules(.*[/\\])+react\//,
        /node_modules(.*[/\\])+react-native/,
        /node_modules(.*[/\\])+@react-native/,
        /node_modules(.*[/\\])+@react-navigation/,
        /node_modules(.*[/\\])+@react-native-community/,
        /node_modules(.*[/\\])+@expo/,
        /node_modules(.*[/\\])+pretty-format/,
        /node_modules(.*[/\\])+metro/,
        /node_modules(.*[/\\])+abort-controller/,
        /node_modules(.*[/\\])+@callstack\/repack/,
        /node_modules(.*[/\\])+native-base/,
        /node_modules(.*[/\\])+react-freeze/,
        /node_modules(.*[/\\])+@react-stately/,
        /node_modules(.*[/\\])+react-native-mmkv/,
        /node_modules(.*[/\\])+react-native-svg/,
        /node_modules(.*[/\\])+lottie-react-native/,
        /node_modules(.*[/\\])+i18next/,
        /node_modules(.*[/\\])+react-i18next/,
      ],
      use: 'babel-loader',
    },
    {
      test: /\.[jt]sx?$/,
      exclude: /node_modules/,
      use: {
        loader: 'babel-loader',
        options: {
          /** Add React Refresh transform only when HMR is enabled. */
          plugins:
            devServer && devServer.hmr
              ? ['module:react-refresh/babel']
              : undefined,
        },
      },
    },
    {
      test: Repack.getAssetExtensionsRegExp(
        Repack.ASSET_EXTENSIONS.filter((ext) => ext !== 'svg')
      ),
      use: {
        loader: '@callstack/repack/assets-loader',
        options: {
          platform,
          devServerEnabled: Boolean(devServer),
          scalableAssetExtensions: Repack.SCALABLE_ASSETS,
        },
      },
    },
    {
      test: /\.svg$/,
      use: [
        {
          loader: '@svgr/webpack',
          options: {
            native: true,
          },
        },
      ],
    },
  ],
},
plugins: [
  new Repack.RepackPlugin({
    context,
    mode,
    platform,
    devServer,
    output: {
      bundleFilename,
      sourceMapFilename,
      assetsPath,
    },
  }),
  new Repack.plugins.ModuleFederationPlugin({
    name: 'b2c-main-app',
    shared: {
      react: {
        singleton: true,
        eager: true,
        requiredVersion: '18.2.0',
      },
      'react-native': {
        singleton: true,
        eager: true,
        requiredVersion: '0.72.7',
      },
      '@react-navigation/native': {
        singleton: true,
        eager: true,
        requiredVersion: '6.1.9',
      },
      '@react-navigation/native-stack': {
        singleton: true,
        eager: true,
        requiredVersion: '6.9.17',
      },
      '@react-navigation/bottom-tabs': {
        singleton: true,
        eager: true,
        requiredVersion: '6.5.11',
      },
      'react-native-screens': {
        singleton: true,
        eager: true,
      },
      'react-native-gesture-handler': {
        singleton: true,
        eager: true,
      },
      'react-native-flipper-zustand': {
        ...Repack.Federated.SHARED_REACT_NATIVE,
        requiredVersion: '3.0.1',
      },
      'react-native-mmkv': {
        ...Repack.Federated.SHARED_REACT_NATIVE,
      },
      'native-base': {
        singleton: true,
        eager: true,
      },
      'react-native-svg': {
        ...Repack.Federated.SHARED_REACT_NATIVE,
        requiredVersion: '13.14.0',
      },
      'react-native-safe-area-context': {
        ...Repack.Federated.SHARED_REACT_NATIVE,
        singleton: true,
        eager: true,
        requiredVersion: '4.7.2',
      },
      'react-native-webview': {
        ...Repack.Federated.SHARED_REACT_NATIVE,
      },
      'react-i18next': {
        ...Repack.Federated.SHARED_REACT_NATIVE,
      },
      i18next: {
        ...Repack.Federated.SHARED_REACT_NATIVE,
      },
      'lottie-react-native': {
        singleton: true,
        eager: true,
      },
      'react-native-reanimated': {
        ...Repack.Federated.SHARED_REACT_NATIVE,
      },
      'react-native-screens': {
        ...Repack.Federated.SHARED_REACT_NATIVE,
        singleton: true,
        eager: true,
        requiredVersion: '3.27.0',
      },
    },
  }),
],

}; };

nazrighazi-cd commented 9 months ago

@jbroma yes, I did tried in the super-app-showcase and got the same error. Thank you.

jbroma commented 9 months ago

Hi @nazrighazi-cd,

I've investigated the matter inside of super-app-showcase and found the following solution:

  1. add react-native-calendars to the host-app
  2. add react-native-calendars to shared modules (with eager: true inside of host-app)
  3. in index.js I've added the following just below the import statements: require.include('react-native-calendars')

The require.include statement makes sure the library get's included with the host-app's module and is properly shared with the rest of the super-app. This needs to be done because react-native-calendars is not used anywhere in the host-app itself.

Let me know whether that helps with your case

nazrighazi-cd commented 9 months ago

Hi @jbroma,

Thank you for the solution. Seems like on my app it was because of the momentjs library. I did follow the same step as you mentioned above but still getting the issue.

And for the super-app-showcase, seems like it's working on the calendar page. However, when i navigate to account page in booking, I'm getting the same error as before.

same step as before,which is

booking home page -> shopping home page -> booking calendar page -> booking account page = error.

nazrighazi-cd commented 9 months ago

Hi @jbroma ,

Some update on my end. Found out that the error on my app is because of number of screens I declared in mfe main navigation. I tried on super-app-showcase and seems like getting the same error.

Below is the step to recreate the error

  1. Create multiple screens in booking mfe, in my case I created 10 screens. In the screens, i used the useeffect function.

image

  1. Add all the screens in booking main navigation

image

  1. Navigate between mfe screens will return error

booking home page -> shopping home page -> booking calendar == error

image

Is there any limitation on the number of screens on the mfe? or is there any solution for this issue?

github-actions[bot] commented 8 months ago

This issue has been marked as stale because it has been inactive for 30 days. Please update this issue or it will be automatically closed in 14 days.

github-actions[bot] commented 8 months ago

This issue has been automatically closed because it has been inactive for more than 14 days. Please reopen if you want to add more context.