1 Anguar9 新特性简介
1.1 默认使用 Ivy 编译器
Ivy 在 Angular8 时即可使用,但需要自行在 tsconfig.json
中增加配置以开启,曾经尝试过但会有一些构建问题。在解决了数百 BUG 后,Ivy 在 Angular9 中 作为了默认的编译方式。lvy 编译器和运行时提供了不少的优点:
- 打包尺寸更小:Ivy 编译器的设计目的是删除那些无法通过摇树优化使用的 Angular 部件,并为每个 Angular 组件生成更少的代码
- 测试速度更快:改进了 Ivy 中 TestBed 的实现,以提高效率。
- 更好的调试:Ivy 为你提供了更多调试应用的工具。当使用 Ivy 运行时在开发模式下运行应用时,现在提供了新的全局对象 ng 来进行调试。
- 改进了 CSS 类和样式绑定:以前,如果一个应用程序包含了对某种样式的竞争性定义,那些样式就会破坏性地相互覆盖。在 Ivy 中,样式将以可预测的方式合并在一起。
- 改进了类型检查:Angular 编译器可以检查应用中的更多类型,还可以应用更严格的规则。这些特性可以帮助你和你的团队在开发过程的早期阶段发现 bug。
- 改进了构建错误:新的 Ivy 编译器不仅运行速度更快、有更强大的类型安全性,而且还能让所有的错误信息更容易阅读。
- 缩短了构建时间,默认启用了 AOT: Ivy 的新架构使得编译器的性能有了很大的改进。
- 改进了国际化支持:在 9.0 中通过把 i18n 的工作移到构建过程的后期,使得国际化开发效率大幅提升
1.2 更可靠的 ng update
- 始终使用最新的 CLI。从 CLI 的
8.3.19
版本开始,我们现在在升级过程中使用了 TARGET 版本的 CLI。这意味着在未来,更新将始终由最新的 CLI 自动处理。 - 进度更新更清晰。ng update 现在做了更多的工作来告诉你幕后的情况。对于每次迁移,你都会看到迁移中的更多信息。
- 更容易对更新进行调试。 默认情况下,
ng update
运行所有迁移,并在磁盘上留下最终结果更改供你检查。版本 9 的更新还引入了新的--create-commits
标志。当你运行ng update --create-commits
时,该工具会在每个迁移动作后提交代码库的状态,这样你就可以逐步理解或调试我们对代码所做的更改。
1.3 providedIn
的新选项
当你在 Angular 中创建一个 @Injectable
服务时,你必须选择它应该添加到注入器的什么位置。除了以前的 root
和 module
这两种选项之外,还有两个新选项:
platform
: 指定providedIn: 'platform'
可以在一个特殊的单例平台注入器中使用该服务,该注入器由该页面上的所有应用共享。any
: 在每个注入该令牌的模块(包括惰性加载模块)中提供一个唯一的实例。
1.4 IDE 和语言服务改进
Visual Studio Marketplace 上的 Angular 语言服务扩展已做了重大改进。随着对性能和稳定性问题的重大架构变革,许多长期存在的漏洞也得到了修复。
1.5 TypeScript 3.7 支持
Angular 已经更新,可以用 TypeScript 3.6 和 3.7 了,也包括 TypeScript 3.7 中非常受欢迎的可选串联(optional chaining)特性。为了与生态系统保持同步,还更新了其他生态系统依赖的版本,比如 Zone.JS 和 RxJS。
1.6 新的组件
官方提供了 '@angular/youtube-player
和 @angular/google-maps
组件。当然对国内来说是没什么用的,但是如果你在做国际化站点则可能会需要用到。
2 升级 Angular 9 过程指引
2.1 升级 Angular 相关依赖版本
首先确保你的 Node.js >= 10.13
。
在升级之前,建议首先参阅一下官方升级指引:
你可以直接通过执行 ng update --all --force
更新 Angular 相关依赖包版本实现“一键升级”。
不过 ng update
只会升级 Angular 生态相关的依赖包版本,对于其他的依赖包来说也最好都升级至最新版本。通过 https://www.npmjs.com/package/npm-check-updates 这个工具,可以帮助你快速进行所有依赖的版本升级:
npm install -g npm-check-updates
ncu
ncu -u
或者直接使用 npx:
npx npm-check-updates
2.2 升级后注意事项
应当注意一些已弃用或即将弃用的 API。这里有相关参考:Angualr 弃用的API和特性
2.2.1 lazy 路由定义方式必须使用 import 方式
以前定义惰性路由 loadChildren
使用包含 #
符号的字符串方式,现在必须改为使用 import
导入方式。
{ path: MENUSITE_CFG.A.shortLink, // loadChildren: './pages-sys#PagesSysModule', loadChildren: () => import('./pages-sys/pages-sys.module').then(m => m.PagesSysModule), },
2.2.2 I18n 国际化
如果你使用了官方的多语言国际化方案则需注意,Angualr9 基于 Ivy 对 I18n 的相关代码进行了重构,确保其可以在编译时内联。现在你需要使用新的包:
ng add @angular/localize
3 升级 NG-ZORRO 组件库
NG-ZORRO
是当前国内 Angular 类组件库最为优秀的 UI 组件库,是 Angular 类中后台系统的首选。
NG-ZORRO
最近也跟进升级到了 9.x 版本,其变动还是非常大的,部分组件进行了重构,在用法上存在不少的变更。如果项目中深度使用 NG-ZORRO
并进行了不少的定制,则它可能会成为是否进行升级的一个重要考量。对于一些组件如表格等的使用,假如你在项目中有自己的进一步封装还好,只需对封装组件进行修改即可;如果每个地方都是单独引用的,那么进行升级的影响范围及工作量都是非常大而繁琐的。
如果你的项目中使用了 NG-ZORRO
并打算进行新版本升级,以下内容可作参考。
3.1 NG-ZORRO 新版本特性
NG-ZORRO
9.x 新版本包含有以下特性:
- 支持 Angular Ivy
- 同步了 Ant Design 4 设计规范,并且添加了暗黑(Dark)和紧凑(Compact) 主题支持
- 性能和易用性增强
- 在之前的版本中 Table 组件已经集成了虚拟滚动,现在 Select 和 Tree 也同样支持
- Form 和 Table 简化了使用方式,现在可以编写更少的模版和配置
- 允许在子模块中添加图标,以减少首屏加载时间
- 现在当路由改变时弹出菜单将自动关闭,同时为 Modal 等组件添加了对应选项
最近半年甚至一年来在 github 上许多关于功能增加的 PR 贡献都被归类到了 9.x 版本。如果以前你对某些 PR 贡献的特性有所期待,现在升级后你即可使用它了。
3.2 升级 NG-ZORRO 指引
可参考以下方法升级 NG-ZORRO
组件库:
- 执行
ng update ng-zorro-antd
升级相关依赖 - 如果控制台出现警告消息请按提示修改对应代码
- 相关升级指引参考: https://ng.ant.design/docs/migration-v9/zh
- 更为详细的变更请参考升级日志: https://ng.ant.design/docs/changelog/zh
NG-ZORRO
的许多组件用法均有破坏性变更,不过开发模式下 console
控制台会打印那些被废弃的用法。以下为一些举例:
- 一些组件的结构有所变更,如果有自定义样式重置,可能会发生样式失效,需重新处理
- 在以前对于
nz-button
可以通过设置nzType
值为自定义类型来实现自定义按钮。 nz-tooltip
全部改为指令方式,为了避免发生冲突,其相关属性nzTitle
改为了nzTooltipTitle
。nz-popover
和nz-popconfirm
也改为了指令方式,相关属性命名也做了变更类似。i[nz-icon]
的所有属性都改为了以nz
开头。以前你可以用[type]="'user'"
的方式,现在必须改为[nzType]="'user'"
的格式NZ_DEFAULT_EMPTY_CONTENT
、NZ_ICON_DEFAULT_TWOTONE_COLOR
、NZ_MESSAGE_CONFIG
、NZ_NOTIFICATION_CONFIG
等用于定义全局默认配置的项均被移除,改为使用相关的Serviece
去实现tree
和tree-select
组件的nzDefaultExpandAll
等属性均移除了Default
字符串,改为了nzExpandAll
格式,nzOnSearchNode
则改为了nzSearchValueChange
form
的nz-form-extra
被移除了,需改为使用nz-form-control
中的nzExtra
代替form
的nz-form-explain
也被移除了,需改为使用nz-form-control
中的nzSuccessTip | nzWarningTip | nzErrorTip | nzValidatingTip
代替table
组件的不少属性都有所变更,需在开发模式下对照控制台的警告进行逐一处理- more…
纠结到底是react还是Angular