Programmingフロントエンド開発者

TypeScriptにおけるテンプレートリテラル型のメカニズムはどのように機能し、何のために必要ですか?

Hintsage AIアシスタントで面接を突破

回答。

質問の歴史

TypeScriptは長い間、個別の文字列または数値のリテラル型を記述することを許可していましたが、テンプレートリテラルの登場により、特定の文字列パターンの型付けが必要になりました。テンプレートリテラル型は、文字列のテンプレート結合に基づいて型を記述する機能を追加し、文字列値の構造を静的に検証します。

問題

特定のフォーマット(例えば、'user_42')に文字列が一致するかを普通のstring型で確認することはできません。これらはあまりにも一般的です。テンプレート型なしでは、コンパイラーは文字列が厳格に定義されたパターンに適合することを保証できません。

解決策

テンプレートリテラル型を使用すると、コンパイル時に複雑な文字列型を生成し、特定のテンプレートに対する厳格な一致性を確保できます。

コード例:

type UserId = `user_${number}`; function loadUser(id: UserId) { // ... } loadUser('user_123'); // 正常 loadUser('admin_123'); // コンパイルエラー

主な特徴:

  • リテラルの結合に基づく文字列型の生成
  • オブジェクトのキーの組み合わせ、ネスト、および操作をサポート
  • 文字列識別子、URL、その他の構造に対する型安全性の向上

ヒントを含む質問。

テンプレートリテラル型はnumber/literalのみに使用できますか?テンプレート内で任意の文字列リテラルを使用できますか?

任意のリテラル型—文字列、数値、結合を使用できます:

type EventType = `event_${'click' | 'hover'}`; // event_click | event_hover

関数がテンプレートリテラルを期待する場合、通常の文字列を渡せますか?

いいえ、型が明示的にリテラルテンプレートを期待する場合、単なるstringは適切ではありません:

function handler(type: `btn_${string}`) {} handler('btn_click'); // OK handler('button'); // コンパイルエラー

マップ型やkeyofと一緒にテンプレートリテラル型は機能しますか?

はい、テンプレートリテラル型はマップ型やオブジェクトのキーと組み合わせることができます:

const colors = {red: 1, blue: 2}; type ColorKey = keyof typeof colors; type ColorClass = `color-${ColorKey}`; // color-red | color-blue

型のエラーとアンチパターン

  • どんなstringにも適合する場所でテンプレート型を使用
  • 柔軟性を残さない非常に攻撃的なテンプレート型
  • コンパイラーが制御しないruntime値に型をバインド

実生活の例

ネガティブケース

APIが'user_XXX'形式の識別子を受け入れ、関数が型付けされていない場合、任意の文字列を渡すことができ、サーバーのエラー時にバグが発生します。

メリット:

  • 値に制限がない

デメリット:

  • チームが間違った文字列を送信し、テストが表面的になる

ポジティブケース

UserId = user_${number}型を使用し、コンパイル前に関数の引数の正当性が保証され、安全なサーバーリクエストが行われます。

メリット:

  • エラーの数を減少させ、厳格な型検証
  • コードの補完性と可読性の向上

デメリット:

  • データスキーマの変更時にテンプレート型を最新の状態に保つ必要がある