0Pricing
React Academy · レッスン

ReactにおけるConditional TypesとMapped Types

conditional typesを使い、他のprop valuesに応じて形が変わるcomponent prop typesを構築します。

「ReactにおけるConditional TypesとMapped Types」はCoddyKit上の無料React Academyレッスンです。 これはレッスン2/4です。 下記で完全なレッスンを無料で読むことができます。その後、ブラウザ内の組み込みコードエディタと24時間対応のAIチューターでハンズオン演習できます。 これはReact Academy学習パスの一部であり、ウェブとCoddyKitアプリ全体で進捗が同期されます。 React Academyコースには全4レッスンが含まれています。

条件型の基礎

条件型はT extends U ? X : Y構文を使います。TがUに代入可能なら型はXに解決され、それ以外の場合はYに解決されます。

type IsString<T> = T extends string ? true : false;

type A = IsString<string>;  // true
type B = IsString<number>;  // false
type C = IsString<'hello'>; // true

他のpropsに基づく条件付きprops

条件型を使うと、別のpropの値に基づいて、あるpropを必須またはオプショナルにできます。

type InputProps<T extends 'text' | 'number'> = {
  type: T;
} & (T extends 'number' ? { min?: number; max?: number } : { maxLength?: number });

const numInput: InputProps<'number'> = { type: 'number', min: 0, max: 100 };
const txtInput: InputProps<'text'> = { type: 'text', maxLength: 50 };

Mapped Types

Mapped Typesは、既存の型の各プロパティを変換して新しい型を作成します。in keyof構文は、すべてのキーを反復処理します。

type Optional<T> = { [K in keyof T]?: T[K] };
type Readonly<T> = { readonly [K in keyof T]: T[K] };
type Nullable<T> = { [K in keyof T]: T[K] | null };

更新フォームでpropsをオプショナルにする

すべてのフィールドが必須ではない更新フォームのpropsには、Partial<T>(組み込みのMapped Type)を使用します。

interface User { id: string; name: string; email: string; role: string; }

// Update form — all fields optional:
type UserUpdateProps = Partial<Omit<User, 'id'>>;

function UserUpdateForm(props: UserUpdateProps) {
  // name, email, role are all optional
}

Mapped TypesでRecordを使う

キーを共用体から取得し、値を一貫した形状にするルックアップ型を作成します。

type Status = 'idle' | 'loading' | 'success' | 'error';

type StatusConfig = Record<Status, {
  label: string;
  icon: React.ReactNode;
  color: string;
}>;

const statusConfig: StatusConfig = {
  idle: { label: 'Ready', icon: <ReadyIcon />, color: 'gray' },
  loading: { label: 'Loading...', icon: <Spinner />, color: 'blue' },
  success: { label: 'Done', icon: <CheckIcon />, color: 'green' },
  error: { label: 'Error', icon: <XIcon />, color: 'red' },
};

必須キーを抽出する

条件型と-?(オプショナルを削除)を使って、型の必須キーだけを抽出します。

type RequiredKeys<T> = {
  [K in keyof T]-?: undefined extends T[K] ? never : K;
}[keyof T];

interface FormData { name: string; email: string; phone?: string; }
type Required = RequiredKeys<FormData>; // 'name' | 'email'

テンプレートリテラル型

テンプレートリテラル型は文字列リテラル型を組み合わせ、型付けされたイベント名、CSSクラス文字列、APIパスを実現します。

type EventName = 'click' | 'change' | 'focus';
type HandlerName = `on${Capitalize<EventName>}`;
// 'onClick' | 'onChange' | 'onFocus'

type ApiPath<R extends string> = `/api/${R}`;
type UserPath = ApiPath<'users'>; // '/api/users'

条件付きでpropsを抽出する

ExtractとExcludeを使って共用体型をフィルタリングします。

type AllProps = 'onClick' | 'onHover' | 'onChange' | 'style';
type EventHandlers = Extract<AllProps, `on${string}`>;
// 'onClick' | 'onHover' | 'onChange'

type NonEventProps = Exclude<AllProps, `on${string}`>;
// 'style'

フォームバリデーションのためのMapped Types

フォームデータの形状を反映したバリデーションエラー型を生成します。各フィールドに1つのエラーメッセージ文字列を対応させます。

interface LoginForm { email: string; password: string; }

type FormErrors<T> = { [K in keyof T]?: string };
type LoginErrors = FormErrors<LoginForm>;
// { email?: string; password?: string }

const errors: LoginErrors = { email: 'Invalid email format' };

判別付きMapped Types

Mapped Typesと条件型を組み合わせると、判別子に基づいて形状が変化する型を作成できます。

type EventMap = {
  click: { x: number; y: number };
  keydown: { key: string; code: string };
  resize: { width: number; height: number };
};

type Handler<E extends keyof EventMap> = (event: EventMap[E]) => void;

function on<E extends keyof EventMap>(event: E, handler: Handler<E>) {
  window.addEventListener(event, handler as EventListener);
}

型を過剰設計しない場面

条件型とMapped Typesは強力ですが、複雑さも増します。実際の重複を排除したり、実際のバグを防いだりできる場合に使い、TypeScriptの知識を示すことだけを目的に使わないでください。

確認問題

Mapped Type { [K in keyof T]?: T[K] }は何をしますか?

まとめ

条件型(T extends U ? X : Y)は、代入可能性に基づいて分岐する型を作成します。Mapped Types([K in keyof T])は、型の各プロパティを変換します。更新フォーム用の部分型、型付けされたイベントマップ、フォームエラーの形状、テンプレートリテラルによるAPIパスなどに使用できます。

よくある質問

「ReactにおけるConditional TypesとMapped Types」レッスンは無料ですか?

はい。「ReactにおけるConditional TypesとMapped Types」の完全なテキストはこのウェブで無料で読めます。インタラクティブに演習し(組み込みコードエディタと24時間対応のAIチューター)、React Academyコースの残りをアンロックするには、CoddyKit PROにアップグレードしてください。 React Academyコースには全4レッスンが含まれています。

「ReactにおけるConditional TypesとMapped Types」で何を学びますか?

conditional typesを使い、他のprop valuesに応じて形が変わるcomponent prop typesを構築します。 ブラウザで直接実行するハンズオンコードでReact Academyを演習し、24時間対応のAIチューターがレッスンを進める中での質問に答えます。

React Academyを始めるのに経験は必要ですか?

事前経験は必要ありません。CoddyKitのReact Academyは初級者から上級者向けに構成されているため、ここから始めるか最初から始めて、自分のペースで進むことができます。 これはレッスン2/4です。

「ReactにおけるConditional TypesとMapped Types」レッスンにはどのくらい時間がかかりますか?

ほとんどのCoddyKitレッスンは約5~10分かかります。各レッスンはコンパクトでインタラクティブなので、着実に進歩し、ウェブとアプリ全体で正確に前回の場所から再開できます。

このReact Academyレッスンでコードを書いて実行できますか?

はい。すべてのReact Academyレッスンに組み込みコードエディタが含まれているため、ブラウザでリアルコードを書いて実行し、即座のAIフィードバックを取得できます。ローカル設定は不要です。

このコースのすべてのレッスン

  1. Component VariantsのDiscriminated Unions
  2. ReactにおけるConditional TypesとMapped Types
  3. 'as' Propを使ったPolymorphic Components
  4. 型安全なFormsとAPI Response Contracts
← React Academyに戻る