angular-forms
Angularのリアクティブフォームを活用し、入力検証や状態管理を含む動的なフォームを効率的に構築するSkill。
📜 元の英語説明(参考)
Angular Reactive Forms for form building, validation, and state management. Use when creating forms, implementing validators, handling form submissions, building dynamic forms, or integrating forms with NgRx Signals in Angular applications. Covers FormControl, FormGroup, and FormArray.
🇯🇵 日本人クリエイター向け解説
Angularのリアクティブフォームを活用し、入力検証や状態管理を含む動的なフォームを効率的に構築するSkill。
※ jpskill.com 編集部が日本のビジネス現場向けに補足した解説です。Skill本体の挙動とは独立した参考情報です。
⚠️ ダウンロード・利用は自己責任でお願いします。当サイトは内容・動作・安全性について責任を負いません。
🎯 このSkillでできること
下記の説明文を読むと、このSkillがあなたに何をしてくれるかが分かります。Claudeにこの分野の依頼をすると、自動で発動します。
📦 インストール方法 (3ステップ)
- 1. 上の「ダウンロード」ボタンを押して .skill ファイルを取得
- 2. ファイル名の拡張子を .skill から .zip に変えて展開(macは自動展開可)
- 3. 展開してできたフォルダを、ホームフォルダの
.claude/skills/に置く- · macOS / Linux:
~/.claude/skills/ - · Windows:
%USERPROFILE%\.claude\skills\
- · macOS / Linux:
Claude Code を再起動すれば完了。「このSkillを使って…」と話しかけなくても、関連する依頼で自動的に呼び出されます。
詳しい使い方ガイドを見る →- 最終更新
- 2026-05-17
- 取得日時
- 2026-05-17
- 同梱ファイル
- 1
📖 Skill本文(日本語訳)
※ 原文(英語/中国語)を Gemini で日本語化したものです。Claude 自身は原文を読みます。誤訳がある場合は原文をご確認ください。
Angular Forms スキル
ルール
フォームの作成
- リアクティブフォームには
ReactiveFormsModuleを使用します。 - 個々のフォームフィールドには
FormControlを使用します。 - 複数のフォームコントロールをグループ化するには
FormGroupを使用します。 - フォームコントロールの動的なリストには
FormArrayを使用します。 - フォーム作成を簡素化するには
FormBuilderを使用します。
バリデーション
- 組み込みバリデーターを使用します:
Validators.required、Validators.email、Validators.min、Validators.max、Validators.pattern - カスタムバリデーターは
ValidationErrors | nullを返さなければなりません。 - バリデーションエラーはフィールドが
touchedになった後にのみ表示します。 - フォームが無効な場合は送信ボタンを無効にします。
フォームの状態管理
- フォームの状態を確認します:
valid、invalid、touched、dirty、pristine form.reset()を使用してフォームをリセットします。form.patchValue()またはform.setValue()を使用してフォームの値を更新します。
NgRx Signals の統合
- フォームインスタンスを
signalStoreの状態に保存します。 - 非同期フォーム送信には
rxMethodを使用します。 - 送信の成功/エラー処理には
tapResponseを使用します。 - 送信が成功したらフォームをリセットします。
フォームの送信
- フォーム送信には
(ngSubmit)イベントを使用します。 - 処理の前にフォームを検証します:
if (form.valid) - ユーザーフィードバックでエラーを処理します。
コンテキスト
概要
Angular Reactive Forms は、組み込みのバリデーション、状態管理、および Angular のリアクティブプログラミングパターンとの統合により、フォーム入力を処理するためのモデル駆動型アプローチを提供します。
このスキルを使用するタイミング
以下の必要がある場合にこのスキルをアクティブ化します。
FormControlとFormGroupを使用してリアクティブフォームを作成する- 組み込みおよびカスタムバリデーターを実装する
- フォームの送信とデータバインディングを処理する
FormArrayを使用して動的なフォームを構築する- クロスフィールドバリデーションを実装する
- フォームを NgRx Signals ストアと統合する
- 非同期バリデーターを処理する
- フォームの状態管理(
touched、dirty、valid)を実装する - 再利用可能なフォームコンポーネントを作成する
基本的なリアクティブフォームの例
import { Component } from '@angular/core';
import { ReactiveFormsModule, FormControl, FormGroup, Validators } from '@angular/forms';
@Component({
selector: 'app-user-form',
standalone: true,
imports: [ReactiveFormsModule],
template: `
<form [formGroup]="userForm" (ngSubmit)="onSubmit()">
<input formControlName="name" placeholder="Name">
@if (userForm.controls.name.touched && userForm.controls.name.errors) {
<span>Name is required</span>
}
<input formControlName="email" type="email" placeholder="Email">
@if (userForm.controls.email.touched && userForm.controls.email.errors?.['email']) {
<span>Invalid email</span>
}
<button type="submit" [disabled]="userForm.invalid">Submit</button>
</form>
`
})
export class UserFormComponent {
userForm = new FormGroup({
name: new FormControl('', [Validators.required]),
email: new FormControl('', [Validators.required, Validators.email])
});
onSubmit() {
if (this.userForm.valid) {
console.log(this.userForm.value);
}
}
}
カスタムバリデーターの例
// Custom validator function
function minAgeValidator(minAge: number): ValidatorFn {
return (control: AbstractControl): ValidationErrors | null => {
if (!control.value) return null;
const birthDate = new Date(control.value);
const age = new Date().getFullYear() - birthDate.getFullYear();
return age >= minAge ? null : { minAge: { required: minAge, actual: age } };
};
}
// Usage
age: new FormControl('', [Validators.required, minAgeValidator(18)])
NgRx Signals との統合例
export const UserFormStore = signalStore(
{ providedIn: 'root' },
withState({
form: new FormGroup({
name: new FormControl(''),
email: new FormControl('')
}),
submitting: false,
error: null as string | null
}),
withMethods((store, userService = inject(UserService)) => ({
submitForm: rxMethod<void>(
pipe(
tap(() => patchState(store, { submitting: true })),
switchMap(() => userService.createUser(store.form().value)),
tapResponse({
next: () => {
store.form().reset();
patchState(store, { submitting: false });
},
error: (error: Error) => patchState(store, {
error: error.message,
submitting: false
})
})
)
)
}))
);
参考文献
📜 原文 SKILL.md(Claudeが読む英語/中国語)を展開
Angular Forms Skill
Rules
Form Creation
- Use
ReactiveFormsModulefor reactive forms - Use
FormControlfor individual form fields - Use
FormGroupto group multiple form controls - Use
FormArrayfor dynamic lists of form controls - Use
FormBuilderfor simplified form creation
Validation
- Use built-in validators:
Validators.required,Validators.email,Validators.min,Validators.max,Validators.pattern - Custom validators MUST return
ValidationErrors | null - Show validation errors ONLY after field is touched
- Disable submit button when form is invalid
Form State Management
- Check form state:
valid,invalid,touched,dirty,pristine - Reset form using
form.reset() - Update form values using
form.patchValue()orform.setValue()
NgRx Signals Integration
- Store form instance in
signalStorestate - Use
rxMethodfor async form submission - Use
tapResponsefor handling submission success/error - Reset form on successful submission
Form Submission
- Use
(ngSubmit)event for form submission - Validate form before processing:
if (form.valid) - Handle errors with user feedback
Context
Summary
Angular Reactive Forms provide a model-driven approach to handling form inputs with built-in validation, state management, and integration with Angular's reactive programming patterns.
When to Use This Skill
Activate this skill when you need to:
- Create reactive forms with FormControl and FormGroup
- Implement built-in and custom validators
- Handle form submissions and data binding
- Build dynamic forms with FormArray
- Implement cross-field validation
- Integrate forms with NgRx Signals stores
- Handle async validators
- Implement form state management (touched, dirty, valid)
- Create reusable form components
Basic Reactive Form Example
import { Component } from '@angular/core';
import { ReactiveFormsModule, FormControl, FormGroup, Validators } from '@angular/forms';
@Component({
selector: 'app-user-form',
standalone: true,
imports: [ReactiveFormsModule],
template: `
<form [formGroup]="userForm" (ngSubmit)="onSubmit()">
<input formControlName="name" placeholder="Name">
@if (userForm.controls.name.touched && userForm.controls.name.errors) {
<span>Name is required</span>
}
<input formControlName="email" type="email" placeholder="Email">
@if (userForm.controls.email.touched && userForm.controls.email.errors?.['email']) {
<span>Invalid email</span>
}
<button type="submit" [disabled]="userForm.invalid">Submit</button>
</form>
`
})
export class UserFormComponent {
userForm = new FormGroup({
name: new FormControl('', [Validators.required]),
email: new FormControl('', [Validators.required, Validators.email])
});
onSubmit() {
if (this.userForm.valid) {
console.log(this.userForm.value);
}
}
}
Custom Validators Example
// Custom validator function
function minAgeValidator(minAge: number): ValidatorFn {
return (control: AbstractControl): ValidationErrors | null => {
if (!control.value) return null;
const birthDate = new Date(control.value);
const age = new Date().getFullYear() - birthDate.getFullYear();
return age >= minAge ? null : { minAge: { required: minAge, actual: age } };
};
}
// Usage
age: new FormControl('', [Validators.required, minAgeValidator(18)])
Integration with NgRx Signals Example
export const UserFormStore = signalStore(
{ providedIn: 'root' },
withState({
form: new FormGroup({
name: new FormControl(''),
email: new FormControl('')
}),
submitting: false,
error: null as string | null
}),
withMethods((store, userService = inject(UserService)) => ({
submitForm: rxMethod<void>(
pipe(
tap(() => patchState(store, { submitting: true })),
switchMap(() => userService.createUser(store.form().value)),
tapResponse({
next: () => {
store.form().reset();
patchState(store, { submitting: false });
},
error: (error: Error) => patchState(store, {
error: error.message,
submitting: false
})
})
)
)
}))
);