为了账号安全,请及时绑定邮箱和手机立即绑定

Angular v18 正式发布了!

今天我们非常激动地分享 Angular 发展历程中的下一个重要里程碑!在过去三个版本中,我们已经引入了许多新功能和改进。这次的重点是打磨之前发布的成果,将许多新的 API 升级至稳定状态,满足了开发者常见的需求,并实验性地发布了路线图上最令人期待的项目之一:无区(zoneless)变化检测。

Image showing the Angular logo on a white black ground with red gradient shapes in the corners. Under the Angular logo there’s a text saying “v18 is now available”

这次更新的重点包括:

  • 实验性支持无区变更检測
  • Angular.dev 现已成为 Angular 开发者的新家
  • Material 3、惰性加载视图和内置控制流现已稳定,并融入了一系列改进
  • 服务器端渲染改进包括 i18n 水合支持、更好的调试、Angular Material 中的水合支持,以及由与 Google 搜索相同的库支持的事件回放功能 详情请参阅这篇博客文章

想快速了解情况,看看我们发布会的视频:

演变中的变化检测

历史上,一个名为 zone.js 的库一直负责触发 Angular 的变化检测。这个库带来了一些开发体验和性能上的缺点。多年来,我们已经努力了多年,希望能找到一种不依赖 zone.js 的 Angular 使用方法。我们非常激动地分享首个无 zone.js 实验性 API 功能。

你可以从今天开始尝试一下 Angular 中的无区的实验性支持!将 provideExperimentalZonelessChangeDetection 添加到你的应用启动过程中。

启动应用程序(应用程序, {  
  提供项: [  
    提供实验性的无区变更检测()  
  ]  
});
// 启动应用程序,提供实验性的无区变更检测功能

在添加提供者之后,在 angular.json 文件中的 polyfills 部分移除 zone.js。

向前迈进,无边界为开发者开启了众多机会。

  • 提高微前端的可组合性和与其他框架的互操作性
  • 加快初始渲染和运行时
  • 更小的打包体积和更快的页面加载
  • 更易读的堆栈追踪
  • 简化调试

在你的组件中使用 zoneless 的最好方式是使用信号:

    @Component({  
      ...  
      template: `  
        <h1>来自 {{ name() }} 的嗨!</h1>  
        <button (click)="handleClick()">切换到无区</button>  
      `,  
    })  
    export class App {  
      protected name = signal('Angular');  

      handleClick() {  
        this.name.set('无区Angular');  
      }  
    }

如下示例中,点击按钮会调用 handleClick 方法,该方法更新信号值并刷新 UI。这与使用 zone.js 的应用类似,但有一些差异。使用 zone.js 时,Angular 会在应用程序状态可能发生变化的任何时候运行变更检测。而没有 zone 的情况下,Angular 只在较少的触发事件(如信号更新)时才进行检测。此变更还包括一个具有去重功能的新调度器,以避免短时间内重复检测变更。

当用户点击上面的按钮时,Angular 仅会因为调度器的合并功能而运行一次变更检测。更多关于无区(zoneless)的内容,请参阅我们的文档

更新到无区域模式

最近,Angular 正经历着激动人心的演变,而 zoneless 是其中的核心部分。随着框架的不断发展,我们确保现有的所有 API 都能继续正常运行,并且新加入的内容都能很好地配合使用。

Zoneless 还是我们在互操作性方面的另一种尝试。除此之外,我们还希望确保将现有应用迁移到 Zoneless 也尽可能简单。如果你的组件兼容 Angular 的 ChangeDetectionStrategy.OnPush 变更检测策略,它们也应与 Zoneless 兼容,使之迁移也更为顺畅!

默认聚合
默认情况下,数据会被自动合并在一起

从 v18 开始,我们为无区段的应用和启用了 合并 的 zone.js 应用使用相同的调度程序。为了减少新 zone.js 应用中的更改检测周期,我们默认启用了 区段合并 功能。

这种行为仅对新应用可用,因为它可能引起依赖旧变更检测机制的应用程序出现问题。合并能减少不必要的变更检测周期,显著提高某些应用的性能。

为了为现有项目启用事件合并,请在 bootstrapApplication 中配置您的 NgZone 提供者:

您可以:

bootstrapApplication
(强调符号,不是代码块)

启动应用(App, {
  提供者: [  
    提供Zone变更检测({ eventCoalescing: true })  
  ]  
});
原生等待无地域限制的应用程序

Zone.js 拦截了许多浏览器调用,以便插入 Angular 的变更检测。不幸的是,async/await 是 zone.js 无法修补的 API 之一,因此我们需要通过 Angular CLI 将其降级到 Promise。这不太理想,因为所有现代浏览器都支持 async/await,而 async/await 不仅更具表达力,而且在 JavaScript 运行时中得到了更好的优化。

如今,如果你今天开发一个使用无区域变更检测功能的实验性应用,Angular CLI 将直接采用原生的 async/await,而不再将其转换为 promises。这不仅让调试更加方便,还能够使你的包体积更小。

支持无需分区的组件

我们在 Angular CDK 和 Angular Material 中启用了无区支持功能。这也有助于我们发现并改进了一些与无区模型相关的粗糙点。

Angular 开发者的理想之地

在过去18个月里,我们一直在努力工作在 angular.dev,致力于提供一个直观且动手的入门体验,并改进了深入指南。今天,我们很高兴地告诉大家,angular.dev 成为了 Angular 的官方文档网站!

除了全新的现代界面外,你还可以找到一个基于 WebContainers互动的手把手教程,一个带有示例的互动 沙盒,由 Algolia 提供支持的改进搜索,更新的指南和教程,简化了的导航,以及其他更多新东西!

Gif showing the scrolling animation of the home page of Angular.dev. It starts with the Angular logo and ends with the playground.

Angular.dev 主页

所有对angular.io的请求现在都会自动跳转到angular.dev。以确保现有链接仍然有效,我们会将这些请求引导到v17.angular.io

可以去angular.dev看看。

终于搞定第3种材料了!

几个月之前,我们引入了对 Material 3 的实验性支持,根据开发者反馈进行了改进并完善了我们的 Material 3 组件,我们很高兴将它们升级到稳定状态!

我们还一起用新的 Material 3 主题和文档更新了 material.angular.io。

Screenshot showing the new design of material.angular.io

你可以在我们的指南中找到如何在你的应用程序中使用Angular Material 3组件。

信号API功能正在开发者预览中

在 Angular 17.1 和 17.2 版本中,我们宣布了一些新特性,包括信号输入属性、基于信号的查询,以及新的输出语法。

查阅我们的信号指南,了解如何使用这些APIs。在接下来的几个月里,我们将根据您的反馈持续改进这些功能,直到它们达到稳定版本。

延迟视图现在稳定了

在过去的六个月中,我们听到了很多关于可延迟视图的激动人心的消息,以及它们如何帮助开发人员轻松提升其应用的核心网络基准。例如,Bill.com 分享说,通过使用 @defer,他们将其中一个应用的包体积减少了 50%。现在,延迟加载视图已经可以稳定使用了!你可以在你的应用 以及库 中使用它们。

内置的控制流已经很稳定了

除了可延迟视图外,在v17版本中,我们还宣布了一种新的内置控制流功能,该功能改进了性能。我们很高兴看到这种新语法得到了广泛采用,并经过我们对社区反馈的回应,我们现在很高兴宣布该API稳定!

在预览期间,我们进一步完善了控制流的类型检查,增加了更多更符合人体工学的隐式的变量别名,并为某些性能相关的反模式设置了防护措施。

服务端渲染:改进

大约在一年前,我们引入了 hydration 并将其稳定下来。根据公共 HTTPArchive 数据集的信息,使用了 prerendering 或服务器端渲染的 Angular v17 应用中,76% 的这些应用已经开始使用 hydration。

有一个主要障碍阻碍了更多人使用hydration功能——缺少i18n支持。与Chrome Aurora团队合作后,我们很高兴地告诉大家,i18n块的hydration支持已经在v18的开发者预览版本中可用!

事件重播

不到两个月前,我们宣布了一个长期整合项目,目的是将Angular与谷歌内部框架Wiz整合。提醒大家,过去,Angular和Wiz服务于不同的应用程序领域——Wiz主要用于面向消费者的高性能应用,特别注重性能;而Angular则侧重于提高开发效率和提升开发者体验。

为了实现整合的努力,Wiz 在其渲染模型中全面集成了 Angular Signals。我们在 ng-conf 上分享了 YouTube 如何使用 Angular Signals。同样地,Angular 正在不断引入更多以性能为中心的功能,例如我稍后会详细介绍的部分水合技术。

无论是哪种情况,我们都会利用你的功能请求和其他需求来激励我们,使两个框架的主要功能合并,以满足这些要求。

An image showing the Angular and the Wiz frameworks logos connected with a line in the middle.

今天,我们很高兴地分享,运行在Google.com的核心库之一是事件分发(以前称为jsaction的库),现已加入Angular 单一代码库。从v18版本起,事件分发将在使用混合渲染时提供事件回放。

大多数开发人员不会直接处理事件分发,所以我们来看看为什么事件回放是有用的。下面是一个简单的电子商务网站的模拟示例。为了模拟非常慢的网络连接,我们故意引入了加载延迟。想象一下,当页面还在加载,尚未完全初始化时,用户想要向购物车中添加多个耳机。如果页面还没初始化完成,还不能交互,那么所有用户操作都将被丢弃。从 Angular v18 版本开始,事件分发功能将开始记录用户的事件。一旦应用程序初始化完成,事件分发会回放这些事件,购物车中最终将有六个项目。

A gif showing the event replay functionality. The user clicks on the “Add to cart” 4 times, which triggers hydration. Once Angular hydrates the user interface the 4 event the framework replays the events which adds 4 items to the cart.

在 Angular 中的事件调度和事件重播

事件回放功能在v18开发者预览版中可用。你可以使用withEventReplay()来启用它,例如:

启动应用程序(App),并提供客户端水合功能,包含事件重放功能。

更棒的调试体验

我们将 Angular DevTools 更新为可视化 Angular 的渲染过程。每个组件旁边都有一个图标来表示该组件的渲染状态。要预览 Angular 在页面上渲染的组件,您可以启用覆盖视图。如果您的应用程序有任何渲染错误,Angular DevTools 将在组件查看器中可视化它们。

A gif showing the hydration functionality in Angular DevTools. The user opens the component inspector of Angular DevTools and sees a hydration error under one of the components.

Angular DevTools 水合作调试

特别感谢我们的社区贡献者同学 Matthieu Riegler (推特用户名)实现了这个功能!

CDK和Material中的补水支持

在 v17 中,一些 Angular Material 和 CDK 组件不被用于 hydration,导致它们需要重新渲染。在 v18 中,所有组件和基本组件都支持 hydration。

我们的部分补水计划

我们在 ng-conf 和 Google I/O 上宣布了部分 hydration 技术。这是一种技术,允许你在服务器端渲染之后逐步激活应用的状态。这样可以使你在启动时加载较少的 JavaScript 代码,并提高应用性能。

部分水合化建立在可延迟视图的相同基础之上。与现在服务器端渲染 @placeholder 块不同,你可以启用一种模式,在这种模式下,Angular 将在服务器端渲染 @defer 块的内容。在客户端,Angular 将在满足模板中指定的触发条件时下载相关的 JavaScript 并对延迟块进行水合化。例如,这里有一个假设的 API 示例。

@defer (延迟服务器渲染和客户端视口呈现) {  
  <app-calendar/>  
}

在服务器端渲染日历组件。当它到达客户端时,Angular 会下载相应的 JavaScript 并使日历组件活化,使其在进入视口后才变得可交互。

我们一直在积极地进行部分数据预渲染的原型设计,它已经可以通过交互触发器进行使用了。我们正与合作伙伴一起评估数据触发器的重要性,例如,组件传递接收属性或绑定值的变化。

如果你正在开发一个对性能要求极高的大规模应用,并希望加入我们的早期访问计划以塑造部分 hydration 的未来,请发邮件联系我们 devrel@angular.io

Firebase 的强大应用托管服务

随着 web 平台变得越来越复杂,你的应用托管在性能、可靠性、生产力和扩展性方面扮演着至关重要的角色。使用混合渲染的应用程序在服务器端渲染、预渲染和客户端渲染方面有不同的托管需求。手动管理这些复杂性可能会非常麻烦。Firebase 应用托管现在可以为开发者透明地搞定这一切!

Logo of Firebase App Hosting

Firebase 今年在 Google I/O 上宣布了 App Hosting。App Hosting 简化了动态 Angular 应用程序的开发和部署过程,提供内置框架支持、GitHub 集成,以及与 Authentication、Cloud Firestore 和 Vertex AI for Firebase 等其他 Firebase 产品的集成。

我们已经和 Firebase 合作了差不多一年的时间,努力确保 Angular 开发者拥有流畅的开发体验。看看他们的[快速入门]指南,现在就可以开始使用 App Hosting 了!

还有更多呢……

在我们推进的大计划中,我们总是花时间解决开发者的常见需求。这里有一些来自v18的主要更新:

为 ng-content 指定备用内容

为 ng-content 指定备用内容是指设置一个默认显示的内容,当 ng-content 没有匹配到任何内容时使用。

我们最受欢迎的请求之一是为 ng-content 指定默认内容。从 v18 开始,您现在可以使用这个功能。这里有一个快速示例(如下)。

    @Component({  
      selector: 'app-profile',  
      template: `  
        <ng-content select=".greeting">嗨 </ng-content>  

        <ng-content>未知的用户</ng-content>  
      `,  
    })  
    export class Profile {}

现在我们可以使用这个组件了。

    <app-profile>  
      <span class="早上好">早上好 </span>  
    </app-profile>

这意味着:

    <span class="greeting">早</span>  
    这位朋友
统一控制状态变化事件

FormControlFormGroupFormArray 这些 Angular 表单类现在提供了一个名为 events 的属性,允许你订阅这些表单控件的事件流。通过它,你可以追踪值变化、未修改状态、是否被触碰以及控件的有效性状态的变化。

你现在可以使用了:

    const nameControl = new FormControl<string|null>('name', Validators.required);  
    nameControl.valueChanges.subscribe(value => {  
      // 处理每个变化  
    });

此功能请求议题在GitHub上获得了超过440个赞同。感谢我们社区的贡献者Matthieu Riegler,他将这一功能提供给了所有人!

将迁移自动化到应用构建器

在 Angular v17 中,我们宣布“application builder”已稳定,并默认启用以供新项目的使用。其内部使用 Vite 和 esbuild 替代了之前使用的 webpack。

对于大多数应用来说,开发人员可以通过更新他们的 angular.json 来升级到新的构建系统。在过去六个月里,我们收集了更多用户反馈并改进了更新体验,以使每个人能够顺利过渡到新的构建体验并获得编辑和刷新的改进。

您可以在我们的更新指南中找到我们开发的工具,这些工具可帮助您自动化更新流程。

因为 Webpack 不是新构建系统的关键路径,我们将对 Webpack 的依赖变为可选,这使我们减少了 Angular CLI 的总依赖项数量超过 50%。这将加快您的 Angular CLI 安装速度。

作为函数的路由重定向

例如,在Web开发中,我们可能会使用这样的函数来处理URL重定向。

为了增强处理重定向的灵活性,Angular v18 中,redirectTo 现在可以接受一个返回字符串的函数。例如,如果你想根据某些运行时状态重定向到某个路由,你可以在函数中实现更复杂的逻辑:

    const routes: Routes = [  
      { path: "first-component", component: FirstComponent },  
      {  
        path: "old-user-page",  
        redirectTo: ({ queryParams }) => {  
          const errorHandler = inject(ErrorHandler);  
          const userIdParam = queryParams['userId'];  
          if (userIdParam !== undefined) {  
            return `/user/${userIdParam}`;  
          } else {  
            errorHandler.handleError(new Error('尝试导航到用户页面但未提供用户ID,导致导航失败.'));  
            return `/not-found`;  // not-found 页面路径
          }  
        },  
      },  
      { path: "user/:userId", component: OtherComponent },  // 获取用户ID参数
    ];
TypeScript 5.4 版

最后但同样重要,我们更新了对 TypeScript 的依赖,让你可以利用到所有的最新功能!TypeScript 5.4 功能

社区亮点

在社区中,我们也看到了大量的进步和创新,随着 Angular 的不断创新。

一些流行的 state 管理库,比如 ngrx、ngxs 和 rxAngular,已经开始使用 Angular 信号,从而使组件中的反应性更加细腻。

两个月之前,Angular GDE(Angular 开发专家)Brandon Roberts 发布了 Analog.js 的 1.0 版本——这是一个由社区驱动的 Angular 元框架(Meta Framework)。它提供了一些很酷的功能,例如基于文件的路由、API 路由、一流的 Markdown 支持功能等等。Analog.js 团队一直在试验一种 单文件组件格式,并且社区对此反应非常积极!

确实令人兴奋的是,其他生态系统中的流行库也在为 Angular 构建适配器。Chau TranArnoud de VriesCorbin Crutchley 分别发布了对 Angular 的 TanStack StoreTanStack QueryTanStack Forms 的支持!

我们也很高兴能够参与世界各地的许多Angular社区会议,并期待今年晚些时候即将举行的会议。组织一场有数百名与会者和数十位演讲者的会议是一项艰巨的任务,向所有让这项艰巨任务变为现实的人致敬,包括ng-confAngular Belgradeng-deng-beNGPolandngRomeNG KenyangIndiaAngular TLV等这些会议!如果我们遗漏了任何会议,请在评论中与我们分享。

从v16以来,除此之外,我们还收到了超过290位贡献者的贡献!感谢所有帮助Angular变得更好的人,无论他们通过代码、问题、内容、组织社区或其他方式🙏

回想一下我们的进展

作为Angular复兴的一部分,我们在过去两年里做了很多事情,未来我们还有很多创新的想法。我想在这里回顾一下现状,并庆祝我们所处的位置。

在将 Angular 演进为一个真正反应式的框架并引入 Signals 等功能的同时,我们始终坚守使命,让开发者能够自信地交付应用程序。全球第二大网站 YouTube 已经使用了 Angular 的反应式原语,我们正作为更大工作组的一部分,共同将 Signals 添加到 web 平台,详见 GitHub 提案

我们还密切与ViteNxCypressPuppeteerStorybook等工具的开发者合作,以提升所有开发者的体验。同时,我们非常幸运地拥有一群充满热情的开发者、社区组织者、作者和演讲者,他们不断挑战Angular的极限。

感谢大家参与 Angular 的复兴潮!

点击查看更多内容
TA 点赞

若觉得本文不错,就分享一下吧!

评论

作者其他优质文章

正在加载中
  • 推荐
  • 评论
  • 收藏
  • 共同学习,写下你的评论
感谢您的支持,我会继续努力的~
扫码打赏,你说多少就多少
赞赏金额会直接到老师账户
支付方式
打开微信扫一扫,即可进行扫码打赏哦
今天注册有机会得

100积分直接送

付费专栏免费学

大额优惠券免费领

立即参与 放弃机会
意见反馈 帮助中心 APP下载
官方微信

举报

0/150
提交
取消