Skip to content

Angular 9 Beta:AOT 编译默认开启与包体积优化

Angular 9 目前处于 Beta 阶段,预计 2020 年初正式发布。最大的变化是 Ivy 渲染引擎将成为默认,连带着 AOT 也将默认开启。这两个变化对包体积和模板类型安全都有显著影响。

AOT vs JIT 回顾

特性JIT(运行时编译)AOT(构建时编译)
编译时机运行时构建时
用户初始加载速度慢(需要下载并解析编译器)
Bundle 中包含编译器是(+~100KB)
模板错误检测运行时构建时
Tree-shaking 效果

在 Angular 8 中,dev 模式默认是 JIT,production 才用 AOT。Angular 9 将两种模式都切成 AOT。

Ivy + AOT 带来的体积收益

根据 Angular 团队公布的数据:

  • 小型应用:减小约 30%
  • 中型应用:减小约 40%
  • 大型应用:收益相对较小,但 tree-shaking 效果改善明显

strictTemplates 系列选项

json
// tsconfig.app.json
{
  "angularCompilerOptions": {
    "strictTemplates": true, // 启用所有模板严格检查
    "strictInputTypes": true, // @Input() 类型检查
    "strictNullInputTypes": true, // 防止 null/undefined 传给 @Input
    "strictAttributeTypes": true, // DOM 属性类型检查
    "strictOutputEventTypes": true, // @Output() 事件类型检查
    "strictDomEventTypes": true // DOM 事件类型检查
  }
}

开启后,模板里的类型错误将在构建时就被捕获,而不是在运行时。

迁移中的常见问题

1. ViewChild 需要指定 { static } 选项

typescript
// Angular 8+ 必须显式指定
// static: true  = 在 ngOnInit 中可用
// static: false = 在 ngAfterViewInit 中可用
@ViewChild('myRef', { static: false }) myRef: ElementRef;

2. Renderer2 替代 Renderer

typescript
// ❌ Renderer 已在 Ivy 中删除
// ✅ 用 Renderer2
constructor(private renderer: Renderer2) {}

3. 模板类型错误修复

html
<!-- ❌ 类型不匹配会报错 -->
<app-user [userId]="'123'"></app-user>
<!-- 如果 userId 是 number -->

<!-- ✅ 类型匹配 -->
<app-user [userId]="123"></app-user>

升级方法

bash
# 待正式发布后
npm install @angular/core@9 @angular/cli@9

# 或者用 ng update
ng update @angular/core @angular/cli
# CLI 自动运行 migration schematic 处理 ViewChild static 等问题

总结

Angular 9 的核心是“默认更好”——AOT 默认开启让开发模式与生产模式一致,消除了“本地正常上线打破”的经典问题。Ivy 的体积收益将让 Angular 应用在性能指标上更具竞争力。

MIT Licensed