Dev Study
← Angular コース

61. untracked — 依存に数えずにシグナルを読む

computed や effect の中でシグナルを読むと、そのシグナルは自動で「依存」として登録され、値が変わるたびに再計算・再実行が走ります。これがシグナルの便利さの核心ですが、ときどき「値は使いたいけれど、その値の変更では再実行してほしくない」という場面があります。たとえば effect でアクセスログを送るとき、送信のきっかけはページの変化だけにしたいのに、ログ本文に含めたいユーザー名まで依存に入ると、ユーザー名の変更でも余計なログが飛んでしまいます。

untracked(() => this.user()) のように包んで読むと、値は取得できますが依存には登録されません。つまり「読むだけで、再実行のきっかけにはしない」という読み方です。effect の中で「トリガーにしたいシグナルは普通に読む、参考情報として使うだけのシグナルは untracked で読む」と使い分けるのが基本形です。

ただし untracked を乱用すると、「値を変えたのに画面が更新されない」「effect が動かない」といった、原因の分かりにくい不具合のもとになります。基本は素直に依存させておき、再実行が多すぎて実害が出た箇所だけを untracked に切り替える、という順番で使うのが安全です。

サンプルコード(フレームワーク環境が必要なため表示のみ)

import { Component, signal, effect, untracked } from '@angular/core';

@Component({
  selector: 'app-page-logger',
  template: '<p>{{ page() }}</p>',
})
export class PageLoggerComponent {
  page = signal('home');
  userName = signal('kazu');

  constructor() {
    effect(() => {
      const page = this.page(); // 依存に登録: page が変わると再実行

      // userName は「読むだけ」。変わっても再実行しない
      const name = untracked(() => this.userName());

      console.log(`${name} さんが ${page} を表示`);
    });
  }
}
サンプルコードで身につける(5本) →

学んだ概念を、素朴な例から実務寄りの例まで5つの具体例で確認します。

公式ドキュメントで詳しく ↗