当使用rollupJs构建ES6模块时,Material-UI ThemeProvider无效的挂钩调用

时间:2019-06-27 09:57:16

标签: reactjs ecmascript-6 module material-ui rollupjs

这里的问题确实很简单。 我目前正在开发一个应用,希望将零件拆分为多个组件。 我决定创建一个样板,使用rollupJS创建模块,以便使用NPM将这些模块导出到我的核心应用程序中。

在我的依赖项中使用MaterialUI以及在模块中使用withStyles和ThemeProvider时,我偶然发现了一个问题。

我目前已经尝试过:

  • 将模块构建为cjs(commonJS)而不是es6模块,无法正常工作
  • 将material-ui作为peerDependencies传递给其他人,几乎没有影响
  • 使用汇总功能(更改订单,使用externalPeerDependencies插件等)运行了不同的方案,但我对汇总的了解不多,所以这对我来说是死胡同,我想就此进行指导,
  • 删除ThemeProvider和/或withStyles键可以解决问题,因此至少我知道这里存在问题。 (并且我的主应用程序上的错误消息是直接指向我的模块/ node_modules中的某个函数,即使用material-ui中使用useContext()的函数)
  • 使用MuiThemeProvider代替ThemeProvider不能解决问题
  • 在这种情况下,不能使用Material UI和/或ReactJS的早期版本

消息本身就是来自React的臭名昭著的无效钩子调用

Invalid hook call. Hooks can only be called inside of the body of a function component. This could happen for one of the following reasons:
1. You might have mismatching versions of React and the renderer (such as React DOM)
2. You might be breaking the Rules of Hooks
3. You might have more than one copy of React in the same app
See blabla for tips about how to debug and fix this problem.

如您在代码中所见:

  "devDependencies": {
    ...
    "webpack-cli": "^3.3.2",
    "webpack-dev-server": "^3.5.1",
    "sass-loader": "^7.1.0",
    "@material-ui/core": "^4.0.0",
    "style-loader": "^0.23.1"
  },
  "dependencies": {
    "babel-core": "^7.0.0-bridge.0",
    "prop-types": "^15.7.2"
  },
  "peerDependencies": {
    "react": "^16.8.6",
    "react-dom": "^16.8.6",
    "react-proptypes": "^1.0.0",
    "@material-ui/core": "^4.0.0"
  }

我将依赖项作为对等体来避免React版本之间发生冲突(也包括实质性ui,但似乎几乎没有影响)。我已将devDependencies截断以避免在此处列出完整列表。

我的汇总配置:

export default {
  input: 'src/index.js',
  output: [{
    file: pkg.main,
    format: 'es'
  }],
  // All the used libs needs to be here
  external: [
    'react', 
    'react-dom',
    'react-proptypes',
    '@material-ui/core',
    '@material-ui/styles',
    'prop-types'
  ],
  plugins: [
    resolve({ preferBuiltins: false }),
    postcss({
      plugins: [
        postcssModules({
          getJSON (id, exportTokens) {
            cssExportMap[id] = exportTokens;
          }
        })
      ],
      getExportNamed: false,
      getExport (id) {
        return cssExportMap[id];
      },
      extract: 'dist/styles.css',
    }),
    json({
      'include': 'node_modules/**'
    }),
    babel({
      presets: ["@babel/preset-env", "@babel/preset-react"],
      plugins: ["@babel/plugin-proposal-class-properties",  "@babel/plugin-proposal-export-default-from"],
      exclude: [
        'node_modules/**'
      ],
    }),
    commonjs({
      include: 'node_modules/**',
      namedExports: {
        'node_modules/react-is/index.js': ['ForwardRef', 'isValidElementType']
      }
    })
  ]
}

和我的代码,如果我不显示ThemeProvider,就不会出错:

import { render } from 'react-dom'
import React, { Component } from 'react'
import { MuiThemeProvider } from '@material-ui/core/styles'

const props = {}

class Boilerplate extends Component {
  render() {
    return (<div className='title'>Hello world</div>)
  }
}

render(<MuiThemeProvider><Boilerplate /></MuiThemeProvider>, document.getElementById('app'));

非常感谢能够解决此问题的任何帮助!

1 个答案:

答案 0 :(得分:0)

对于任何想知道问题出在哪里的人, Yarn和NPM,即使在控制台中列出了React调用时,也没有列出链接模块所使用的React版本。所以我认为只有一个反应版本。使用PeerDependencies也不能解决问题。

使用https://github.com/facebook/react/issues/13991#issuecomment-496383268,我可以在主应用程序中使用Alias,并且可以解决模块中重复的react调用。