我最近花了很多时间,因为在angular/ngrx/typescript生态系统中某些东西的特定行为(我无法确定可能的根本原因)。
场景:我已经构建了一些效果,并将它们导出到桶文件中(index.ts
):
import {MyEffects} from './my.effects';
export const effects: any[] = [
MyEffects,
];
然后,在我的目录结构中,在另一个桶文件中,我有:
import * as EFFECTS from './effects'
export {EFFECTS};
-store
|-index.ts <= export {EFFECTS}
|-effects
|-index.ts
|-my.effects.ts
最后,在NgModule
的导入数组中:
[
...
EffectsModule.forFeature(EFFECTS.effects),
...
]
当我尝试编译它时,我收到一个太短的错误消息:
ERROR in params.map is not a function
仅此而已。它阻止了我的项目编译。还有更多...如果我运行ng serve
也会发生错误,但是如果我在监视文件更改时更改了ng serve
任何内容,它只是成功地重新编译了项目。
经过一整天的寻找可能导致它的原因,我发现别名部分没有做我认为它应该做的事情。然后,我对结构进行了一些更改,现在它正在按预期工作
溶液:
在第一个桶文件中:
import {MyEffects} from './my.effects';
export const EFFECTS: any[] = [
MyEffects,
];
在上层桶文件中:
export * from './effects'
// instead of:
// import * as SOMETHING from './effects'
// export {SOMETHING};
在NgModel
:
[
...
EffectsModule.forFeature(EFFECTS),
...
]
但。。。为什么???
我是否误解了这个过程的任何部分?
我不确定这是否重要,但是注册效果的功能是延迟加载的。
你正在创建一个奇怪的层次结构。export *
和import/export
的行为方式不同。
当您使用export *
时,TypeScript 的行为就像该文件中的所有导出符号实际上都在文件中一样,即使它们是从其他地方导入的。换句话说,该模块只是层次结构中的一个透明级别,它只对缩短路径有用(您将能够编写import {foo} from './module'
代替import {foo} from './module/src/foo
)。
相反,当您使用以下内容时:
import * as smth from './path';
export {smth}
您正在引入以前没有的进一步级别。这是smth
关键词。你不会摆脱smth
键,它就在那里,它现在正在包装你的整个模块。
回到您的示例,您应该编辑您的问题,显示如何在NgModule
中导入Effects
。 如果您像这样导入它:
import * as effects from './effects.ts';
然后,您再次引入一个包装所有变量的新符号,因此正确的路径将effects.effects.effects.etc
。
相反,使用解构和export *
可以让您在不创建包装器的情况下导入和导出变量。
现在的问题是,为什么编译器不警告你?因为打字稿编译器通常擅长捕获这些类型的问题。解决方案可能在这里:
export const effects: any[] = [
删除类型定义(any[]
)并让TypeScript干扰类型,我很确定它会显示您丢失的错误。