Angular - 组件中module.id的含义是啥?

Posted

技术标签:

【中文标题】Angular - 组件中module.id的含义是啥?【英文标题】:Angular - What is the meanings of module.id in component?Angular - 组件中module.id的含义是什么? 【发布时间】:2016-09-07 18:33:07 【问题描述】:

在 Angular 应用程序中,我看到 @Component 具有属性 moduleId。这是什么意思?

module.id 没有在任何地方定义时,应用程序仍然可以工作。怎么还能用?

@Component(
  moduleId: module.id,
  selector: 'ng-app',
  templateUrl: 'app.component.html',
  styleUrls: ['app.component.css'],
  directives: [AppComponent]
);

【问题讨论】:

我得到 404 的链接 更新链接:blog.schwarty.com/… 【参考方案1】:

Angular 的 beta 版本(从 vesion 2-alpha.51 开始)支持组件的相关资产,例如 @Component 装饰器中的 templateUrlstyleUrls。 p>

module.id 在使用 CommonJS 时有效。您无需担心它是如何工作的。

记住:在 @Component 装饰器中设置 moduleId: module.id 是 关键在这里。如果你没有,那么 Angular 2 将会寻找 用于根级别的文件。

来自Justin Schwartzenberger's post,感谢@Pradeep Jain

2016 年 9 月 16 日更新:

如果您使用 webpack 进行捆绑,则不需要 module.id 在装饰器中。 Webpack 插件自动处理(添加它) module.id 在最终包中

【讨论】:

这如何解释 module.id 是什么? @gyozokudor 如果你没有,那么 Angular 2 将在根级别查找你的文件。【参考方案2】:

(2017-03-13)更新

删除了所有提到的 moduleId。 “组件相对路径”说明书已删除

我们在推荐的 SystemJS 配置中添加了一个新的 SystemJS 插件 (systemjs-angular-loader.js)。该插件会为您动态地将 templateUrl 和 styleUrls 中的“组件相对”路径转换为“绝对路径”。

我们强烈建议您只编写相对于组件的路径。这是这些文档中讨论的唯一形式的 URL。你不再需要写@Component( moduleId: module.id ),也不应该。

来源:https://angular.io/docs/ts/latest/guide/change-log.html

定义:

moduleId?: string

@Component 注释内的moduleId 参数采用string 值,即;

"包含该组件的模块的模块ID。"

CommonJS 用法:module.id,

SystemJS 用法:__moduleName


使用moduleId的原因

moduleId 用于解析样式表和模板的相对路径,如文档中所述。

包含该组件的模块的模块 ID。需要能够解析模板和样式的相对 URL。在 Dart 中,这可以自动确定,不需要设置。在 CommonJS 中,这总是可以设置为 module.id。

参考(旧):https://angular.io/docs/js/latest/api/core/index/ComponentMetadata-class.html

我们可以通过设置@Component元数据的moduleId属性来指定模板和样式文件相对于组件类文件的位置

参考:https://angular.io/docs/ts/latest/cookbook/component-relative-paths.html


使用示例:

文件夹结构:

RootFolder
├── index.html
├── config.js
├── app
│   ├── components
│   │   ├── my.component.ts
│   │   ├── my.component.css
│   │   ├── my.component.html

没有 module.id

@Component(
  selector: 'my-component',
  templateUrl: 'app/components/my.component.html', <- Starts from base path
  styleUrls:  ['app/components/my.component.css'] <- Starts from base path
)

带有module.id

tsconfig.json:


  "compilerOptions": 
    "module": "commonjs", <- need to change this if you want to use module.id property
...

@Component(
  moduleId: module.id,
  selector: 'my-component',
  templateUrl: 'my.component.html', <- relative to the components current path
  styleUrls:  ['my.component.css'] <- relative to the components current path
)

【讨论】:

但是它是如何工作的,module.id的引用在哪里 @NishchitDhanani 这不是必需的,但我建议检查 github.com/angular/angular/issues/6053 它映射到配置中的 map 键。喜欢app echonax 的文档链接目前无法正常工作——即使它是 Angular.io 组件页面上的链接。试试看:angular.io/docs/js/latest/api/core/index/… 在没有 module.id 的方法中,您似乎忘记了 'app' 根目录的 'components' 子目录,不是吗?我认为应该是:templateUrl: 'app/components/my.component.html', styleUrls: ['app/components/my.component.css']【参考方案3】:

如果您得到typescript error,只需declare 文件中的变量即可。

// app.component.ts
declare var module: 
   id: string;

//
@Component(
   moduleId: module.id,    // now it works without annoying Typescript
   ...
)

UPDATE - December 08, 2016

module 关键字在 node 上可用。因此,如果您在项目中安装@types/node,您的打字稿文件中将自动使用module 关键字,而无需declare

npm install -D @types/node

根据您的配置,您可能必须将其包含在您的tsconfig.json 文件中才能获得工具

//tsconfig.json

   ...
   "compilerOptions": 
       "types" : ["node"]
   
   ...


// some-component.ts
// now, no need to declare module
@Component(
   moduleId: module.id,    // now it works without annoying Typescript
   ...
)

祝你好运

【讨论】:

tnq 这么多!经过长时间的摆弄,我终于得到了我的ng build --prod --aotnpm install -D @types/node 工作:) 我做的另一件事是 moduleId: 'module.id'(注意 module.id 周围的单引号) @AnandRockzz 我很高兴你发现这篇文章很有帮助。我认为您不需要将module.id 添加为字符串。如果它有效,则似乎有些不正确。您可能需要进一步研究。【参考方案4】:

除了echonaxNishchit Dhanani 的精彩解释我想补充一点,我真的很讨厌module.id 的组件群。特别是,如果您支持 (Ahead-of-Time) AoT-compilation 并且对于一个现实的项目,这是您应该追求的目标,那么您的组件元数据中就没有像 module.id 这样的位置。

来自Docs:

使用 SystemJS 加载器和组件相关 URL 的 JiT 编译应用程序必须将 @Component.moduleId 属性设置为 module.id。当 AoT 编译的应用程序运行时,模块对象未定义。除非您像这样在 index.html 中分配全局模块值,否则应用程序将失败并出现空引用错误:

<script>window.module = 'aot';</script>

我认为在index.html 文件的生产版本中有这行是绝对不能接受的!

因此,目标是使用以下组件元数据定义为开发提供(即时)JiT 编译和为生产提供 AoT 支持:(没有moduleId: module.id 行)

@Component(      
  selector: 'my-component',
  templateUrl: 'my.component.html', <- relative to the components current path
  styleUrls:  ['my.component.css'] <- relative to the components current path
)

同时我想将样式,如my.component.css 和模板文件,如my.component.html 相对 放置到组件my.component.ts 文件路径。

为了实现这一切,我使用的解决方案是在开发阶段从多个目录源托管 Web 服务器(lite-server 或 browser-sync)!

bs-config.json:


  "port": 8000,
  "server": ["app", "."]

请查看answer 了解详情。

依赖这种方法的示例性 Angular 2 快速启动项目托管在 here。

【讨论】:

【参考方案5】:

根据 Angular 文档,您不应使用 @Component( moduleId: module.id )

请参考:https://angular.io/docs/ts/latest/guide/change-log.html

这是该页面的相关文本:

删除了所有提到的 moduleId。 “组件相对路径”说明书已删除 (2017-03-13)

我们在推荐的 SystemJS 配置中添加了一个新的 SystemJS 插件 (systemjs-angular-loader.js)。该插件会为您动态地将 templateUrl 和 styleUrls 中的“组件相对”路径转换为“绝对路径”。

我们强烈建议您只编写相对于组件的路径。这是这些文档中讨论的唯一形式的 URL。你不再需要写@Component( moduleId: module.id ),也不应该。

【讨论】:

我也会将此作为免责声明添加到我的答案中,感谢您的更新。【参考方案6】:

看起来如果你在 tsconfig.json 中使用“module”:“es6”,你不必使用这个:)

【讨论】:

如果我们这样做,它不会 transpile 到 ES6 中吗?【参考方案7】:

Angular 反射过程和 metadata_resolver 组件使用此 moduleId 值在构建组件之前评估完全限定的组件路径。

【讨论】:

【参考方案8】:

添加 moduleId: module.id 修复了在构建原生 Angular 应用程序和 Angular Web 应用程序时可能出现的几个问题。使用它是最佳实践。

它还使组件能够在当前目录中查找文件,而不是从顶部文件夹中查找文件

【讨论】:

以上是关于Angular - 组件中module.id的含义是啥?的主要内容,如果未能解决你的问题,请参考以下文章

Angular AOT 组件中的相对路径

Angular2 代码中的 TypeScript 错误:找不到名称“模块”

Angular 2如何让子组件等待异步数据准备好

在Angular 2中获取视频标签的源尺寸

angular.json文件中字段含义

打字稿中@符号的含义--Angular 2