使用NormalModuleReplacementPlugin

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

标签: javascript webpack

我有一个Storybook设置,需要我的React组件的子组件停止进行API调用。设置非常复杂,并且与问题无关,所以我只想说我需要组件来停止进行API调用。

我的最终目标是使子组件永远保持在“加载状态”,所以 在这里模拟服务器响应不是解决方案

我想出的方法是将我的Thunk动作创作者替换为残缺的创作者。类似于我们在Jest单元测试中所做的

// note that I'm using redux ducks: https://github.com/erikras/ducks-modular-redux

jest.mock('./ducks/students');

当然,由于Storybook不在Jest上运行,因此上述方法当然无效。因此,我目前的方法是使用NormalModuleReplacementPlugin将实模块ducks/students.js替换为带有功能但实体为空的残缺模块ducks/stubs/students.js

// ./ducks/students.js
export const loadResources() = fetch('/resources');

export default (state, actions => {
  // reducer's body
}


// ./ducks/stubs/students.js
export const loadResources() = Promise.resolve();  // STUBBED

export default (state, actions => {
  // reducer's body
}

问题是,我只需要混搭动作创建者,文件中的其他所有内容(其他动作和reducer)都必须相同。

到目前为止,我已经考虑过解决此问题的方法:

  • 将其余的实际文件复制/粘贴到存根的文件中。这不会扩展。
  • 尝试使用require.requireActual()。原来这是一个Jest自定义函数,所以我不能在Storybook上使用它。

理想情况下,我可以找到一种方法,将实际模块中的所有内容导入存根模块,然后导出存根函数和我需要的其余实际函数。

有什么想法可以在我使用NormalModuleReplacementPlugin时从存根模块中访问实际模块吗?

更新1:2019-07-08

塔伦(Tarun)建议仅模拟提取函数并返回new Promise(),以解决“无限加载”的特殊情况。

但是,从总体上看,我仍然只想保留所有API调用,以便我可以通过修改redux状态来设置故事。

“但是为什么不能仅仅模拟JSON响应呢?”我听到你问。 JSON响应不一定与应用程序域模型进行一对一映射。我们拥有负责转换的映射器功能。

如果程序员可以仅凭域模型知识就可以工作和设置测试用例,而不必知道服务器响应JSON结构,那会更好。不用说,应用程序redux存储结构是域模型。

因此,在使用NormalModuleReplacementPlugin时,我仍然需要有关如何从实际文件中提出要求的答案。

1 个答案:

答案 0 :(得分:1)

我还没有测试过,但是您可以使用聚合/重新导出模块语法并覆盖loadResources()函数来实现您想要的目标。

为此,请将您的实际模块导入./ducks/stubs/students.js,从该模块导出所有内容,然后定义/覆盖loadResources()并将其导出。然后,您可以照常使用NormalModuleReplacementPlugin,并将存根文件作为newResource传递,该存根文件将包含您想要保留的所有实际模块缩减程序/动作,以防止重击被覆盖和存根:< / p>

//ducks.stubs.students.js

export * from './ducks/students.js';

//override students.loadResources() with our stub
//order matters as the override must come after 
//the export statement above
export const loadResources() = //some stubbed behavior;
//webpack.config.js

module.exports = {
  plugins: [
    new webpack.NormalModuleReplacementPlugin(
      /ducks\.students\.js/,
      './ducks.stubs.students.js'
    )
  ]
}

此解决方案的一些注释/注释/陷阱:

  1. 可能必须更新您的导出,以使用letconst(不是大问题)
  2. 对于每个this issueexport * from表达式不应该处理default导出。因此,您可能必须添加export { default } from './ducks/students.js';。当然,请记住,您将无法导出存根文件的本机默认功能(除非您用存根覆盖了原始的default函数)。