Announcing NgRx 19: NgRx Signals Features, Action Signals, and more!

2025-06-10

宣布 NgRx 19:NgRx 信号功能、动作信号等等!

我们很高兴地宣布 NgRx 框架的最新主要版本,其中包含一些令人兴奋的新功能、错误修复和其他更新。


更新了 NgRx Signals 功能🚦

NgRx Signals 在 v18 中稳定发布,是一个从头开始构建的新库,具有 Angular Signals、可选的 RxJS 互操作性和开箱即用的实体管理功能。NgRx Signals 库持续获得质量更新和改进,以增强开发人员体验。

新的道具信号存储功能

一个呼声极高的功能是在 SignalStore 创建期间定义其 props。为了支持此功能,withProps我们添加了一个基本功能,允许将静态属性或可观察对象定义为 SignalStore 成员。

export const BooksStore = signalStore(
  withEntities<Book>(),
  withRequestStatus(),
  withProps(({ isFulfilled }) => ({
    fulfilled$: toObservable(isFulfilled).pipe(filter(Boolean)),
  })),
);
Enter fullscreen mode Exit fullscreen mode

它还可以用于在一个地方定义所有依赖项:

export const MyStore = signalStore(
  withProps(() => ({
    service1: inject(Service1),
    service2: inject(Service2),
  })),
  withMethods(({ service1, service2 }) => ({
    method1() {
      service1.foo();
    },
    method2() {
      service2.bar();
    },
  }))
);
Enter fullscreen mode Exit fullscreen mode

withProps功能与 Angular Signals 的新功能集成在一起,resource包括linkedSignal

const booksStore = signalStore(
  withProps(() => {
    const bookResource = resource({
      loader: () => Promise.resolve({ id: 1, title: "'Lord of the Rings' }),"
    });
    return {
      _bookResource: bookResource,
      bookResource: bookResource.asReadonly(),
    };
  }),
);
Enter fullscreen mode Exit fullscreen mode

以上将 bookResource 公开为只读资源,并保留可写资源。

下一个示例公开prettyTitlelinkedSignal,并在内部保持可写状态。

signalStore(
  withState({ id: 1, title: "'Lord of the Rings' }),"
  withProps((store) => ({
    prettyTitle: linkedSignal(() => \`${store.id()}: ${state.store()}\`),
  })),
);
Enter fullscreen mode Exit fullscreen mode

withProps功能允许您使用 Angular Signals 进一步自定义和扩展 SignalStore。感谢Marko Stanimirović为改进 NgRx Signals 所做的持续努力!

信号方法实用功能

引入实用函数rxMethod是为了将 RxJS 完成的异步工作连接到 Angular Signals。我们还引入了实用函数,它能让你获得与仅使用信号signalMethod相同的优势。rxMethod

signalMethod是一个处理信号或静态值的副作用的工厂函数。

import { Component } from '@angular/core';
import { signalMethod } from '@ngrx/signals';

@Component({ /* ... */ })
export class NumbersComponent {
  // 👇 This method will have an input argument
  // of type `number | Signal<number>`.
  readonly logDoubledNumber = signalMethod<number>((num) => {
    const double = num * 2;
    console.log(double);
  });
}
Enter fullscreen mode Exit fullscreen mode

乍一看,signalMethod可能与 相同effect。然而, signalMethod 比 effect 有三个明显的优势:

@Component({ /* ... */ })
export class NumbersComponent {
  readonly num = signal(2);
  readonly logDoubledNumberEffect = effect(() => {
    console.log(this.num() * 2);
  });
  readonly logDoubledNumber = signalMethod<number>((num) => {
    console.log(num * 2);
  });

  constructor() {
    this.logDoubledNumber(this.num);
  }
}
Enter fullscreen mode Exit fullscreen mode

灵活输入:输入参数可以是静态值,而不仅仅是信号。此外,处理器函数可以使用不同的输入多次调用。
无需注入上下文:与需要注入上下文或注入器的特效不同,signalMethod 的“处理器函数”无需注入上下文即可调用。
显式跟踪:仅跟踪参数的信号,而“处理器函数”中的信号则不被跟踪。

阅读文档以了解有关signalMethod 的更多信息。

开发模式检查状态突变

确保状态更新不可变对于 Signal 正确发出并触发必要的 DOM 更新、派生信号或副作用至关重要。为了缓解此问题,该patchState函数在开发模式下对状态进行了深度冻结。

前:

const userState = signalState(initialState);
patchState(userState, (state) => {
  state.user.firstName = 'mutable change'; // mutable change which went through
  return state;
});
Enter fullscreen mode Exit fullscreen mode

后:

const userState = signalState(initialState);
patchState(userState, (state) => {
  state.user.firstName = 'mutable change'; // throws in dev mode
  return state;
});
Enter fullscreen mode Exit fullscreen mode

这确保了状态变化保持不变,从而提供了保留性能和最佳实践的途径。

NgRx Store 支持在信号变化时调度操作

NgRx Store 仍然是 Angular 应用程序中全局状态管理的实际选择。NgRx Store 之前引入了以信号形式选择状态的支持,现在又引入了一种符合人体工程学的方式来调度读取信号的操作。

class BookComponent {
  bookId = input.required<number>();

  constructor(store: Store) {
    store.dispatch(() => loadBook({ id: this.bookId() })));
  }
}
Enter fullscreen mode Exit fullscreen mode

dispatch方法在初始阶段以及每次bookId发生更改时执行。如果dispatch在注入上下文中调用,则信号会被跟踪,直到上下文被销毁。在上面的例子中,销毁就是在上下文BookComponent被销毁时。

当在dispatch组件注入上下文之外调用时,信号会在应用程序的整个生命周期内被全局跟踪。为了确保在这种情况下能够正确清理,请将组件的注入器提供给该dispatch方法:

class BookComponent {  
  bookId = input.required<number>();
  injector = inject(Injector);
  store = inject(Store);

  ngOnInit() {
    // runs outside the injection context
    this.store.dispatch(
      () => loadBook({ id: this.bookId() }),
      { injector: this.injector }
    );
  }
}
Enter fullscreen mode Exit fullscreen mode

感谢Rainer Hahnekamp添加这些功能!

NgRx Signals,新的默认设置🤝

NgRx Signals 是一种全新的响应式状态管理方法,并且是 RxJS 的可选组件。它还包含其他实用程序,能够以结构化的方式与 Angular Signals 协同工作,帮助开发者进行扩展。NgRx Signals 现在是推荐集成到 Angular 应用中的本地状态管理库。对于新应用,可以从 NgRx SignalStore 开始。对于现有应用,请考虑迁移到新的@ngrx/signals软件包。

NgRx 研讨会🎓

随着 NgRx 的使用率与 Angular 的持续增长,许多开发者和团队仍然需要关于如何架构和构建企业级 Angular 应用的指导。我们非常高兴地宣布即将推出由 NgRx 团队直接提供的研讨会!

从二月开始,我们将提供一到三场全天研讨会,涵盖 NgRx 的基础知识到最高级的主题。无论您的团队是刚开始使用 NgRx 还是已经使用一段时间,都能在这些研讨会中学习到新的概念。

研讨会涵盖了使用 NgRx Store 和库的全局状态,以及使用 NgRx ComponentStore 和 NgRx Signals 管理本地状态。

请访问我们的研讨会页面,从即将举行的研讨会列表中进行报名。

新的文档网站💅

新的文档改版正在进行中,它使用AnalogJS从头构建,并将采用全新的设计和更新的内容。这将确保为用户提供最佳体验,并让您更轻松地找到所需信息。此外,它还确保网站更易于维护和更新。由于我们是一个社区驱动的项目,我们始终牢记,网站应该易于贡献。

感谢Mike Ryan为 NgRx 网站新版本所做的工作。


弃用和重大变更💥

此版本包含错误修复、弃用功能和重大变更。对于大多数弃用功能或重大变更,我们提供了迁移功能,该功能会在您将应用升级到最新版本时自动运行。

请参阅版本 19 迁移指南,获取有关迁移到最新版本的完整信息。完整的变更日志可在我们的 GitHub 代码库中找到。


升级到 NgRx 19

要开始使用 NgRx 19,请确保安装以下最低版本:

  • Angular 版本 19.x
  • Angular CLI 版本 19.x
  • TypeScript 版本 5.5.x
  • RxJS 版本 ^6.5.x 或 ^7.5.x

NgRx 支持使用 Angular CLIng update命令来更新你的 NgRx 软件包。要将软件包更新到最新版本,请运行以下命令:

ng update @ngrx/store@19
Enter fullscreen mode Exit fullscreen mode

如果您的项目使用@ngrx/signals,请运行以下命令:

ng update @ngrx/signals@19
Enter fullscreen mode Exit fullscreen mode

Swag 商店和 Discord 服务器🦺

您可以通过我们的商店购买 NgRx 官方礼品!印有 NgRx 标志的 T 恤有多种尺码、材质和颜色可供选择。我们计划未来在商店中增加贴纸、磁铁等新品。立即访问我们的商店,获取您的 NgRx 礼品吧!

想要与 NgRx 社区新老成员互动的朋友们,欢迎加入我们的Discord 服务器。


为 NgRx 做贡献

我们始终致力于改进文档,并使其始终与 NgRx 框架用户保持同步。为了帮助我们,您可以开始为 NgRx 做出贡献。如果您不确定从哪里开始,请查看我们的贡献指南,并观看Jan-Niklas WortmannBrandon Roberts制作的介绍视频 ,它们可以帮助您入门。


感谢我们所有的贡献者和赞助商!

NgRx 始终是一个社区驱动的项目。设计、开发、文档和测试均在社区的帮助下完成。访问我们的社区贡献者页面,查看所有为该框架做出贡献的人员。

如果您有兴趣贡献代码,请访问我们的GitHub页面,浏览我们的未解决问题,其中一些问题已标记为专门针对新贡献者。我们还在 GitHub 上积极讨论新功能和增强功能。

我们要衷心感谢我们的金牌赞助商Nx!Nx 长期以来一直大力推广 NgRx 作为构建 Angular 应用程序的工具,并致力于支持他们所依赖的开源项目。

我们还要感谢我们的铜牌赞助商House of Angular

在BlueskyLinkedInTwitter上关注我们,了解有关 NgRx 平台的最新更新。

鏂囩珷鏉ユ簮锛�https://dev.to/ngrx/announcing-ngrx-19-ngrx-signals-features-action-signals-and-more-2b35
PREV
宣布 NgRx Signals v18:状态封装、私有存储成员、增强实体管理等等!
NEXT
30 分钟内使用 HTML 和 CSS 构建注册页面