- Angular
Can’t bind to ‘ngModel’の直し方|NG8002の原因一覧
Can't bind to 'ngModel' since it isn't a known property of 'input' は、テンプレートの [(ngModel)] を処理する部品(NgModel ディレクティブ)が、そのコンポーネントから見えていないときのエラーです。 standalone コンポーネント(NgModule を使わない、v17 以降の ng new の既定)なら、そのコンポーネントの imports に FormsModule を入れると直ります。
import { Component } from '@angular/core';
import { FormsModule } from '@angular/forms'; // ← 追加
@Component({
selector: 'app-profile',
imports: [FormsModule], // ← 追加
template: `<input [(ngModel)]="name" name="name"> {{ name }}`,
})
export class Profile {
name = '';
}
親コンポーネントの imports に FormsModule を入れても、子のテンプレートの ngModel では NG8002 が出ました。ngModel を書いたテンプレートを持つコンポーネント自身の imports に入れます。
同じ NG8002 は、ほかの名前でも出ます。エラー文の '…' の部分で原因を分けると、次のとおりです。
| エラーに出る名前 | 主な原因 | 直し方 |
|---|---|---|
ngModel |
FormsModule が imports に無い |
imports: [FormsModule] |
formGroup・formControl |
ReactiveFormsModule が無い |
imports: [ReactiveFormsModule] |
formField |
Signal Forms の FormField が無い |
imports: [FormField](@angular/forms/signals) |
| 自作コンポーネントの入力名 | 名前の誤り・input() を付け忘れ |
子の input() の名前に合わせる |
ngModle など |
スペルミス | 正しい綴りに直す |
colspan・data-id・cx |
DOM プロパティが無い(属性だけ) | [attr.colspan] のように attr. を付ける |
<my-widget> の値 |
Angular 以外のカスタム要素 | schemas: [CUSTOM_ELEMENTS_SCHEMA] |
確認環境:Angular 22.2.2(@angular/core・@angular/forms・@angular/cli)、TypeScript 6.0.3、Node.js 24.21.0(Linux)。ng new のプロジェクトで、ng build・ng serve・ng test(Vitest 5.0.4)を動かし、エラー文はすべて実際に出たものです。直したあとの表示は、ng build した画面を Chromium(Playwright)で開いて確かめました(確認日 2026年10月12日)。
本記事の内容は、ご自由にお使いください。
ご利用の際は、出典として本ページへのリンクを記載いただけますようお願いします。
(記載例)出典:株式会社RJC「Can't bind to 'ngModel'の直し方|NG8002の原因一覧」
実際のエラー文(ng serve・ng build)
imports に FormsModule が無いコンポーネントで ng serve を動かすと、ビルドの段階で止まり、次のように出ました。ng build でも同じ文面です。
Application bundle generation failed. [3.322 seconds]
✘ [ERROR] NG8002: Can't bind to 'ngModel' since it isn't a known property of 'input'. Find more at https://next.angular.dev/errors/NG8002 [plugin angular-compiler]
src/app/profile.ts:6:56:
6 │ ...profile', template: `<input [(ngModel)]="name" name="name">` })
╵ ~~~~~~~~~~~~~~~~~~
Watch mode enabled. Watching for file changes...
| 部分 | 意味 |
|---|---|
NG8002 |
コンパイル時(ビルド時)のエラー番号 |
Can't bind to 'ngModel' |
バインドできなかった名前。ここで原因を分ける |
known property of 'input' |
対象の要素。input・form・app-child など |
src/app/profile.ts:6:56 |
エラーのファイルと行・列。~~~~ の下線が該当の場所 |
NG8002 はビルド時のエラーなので、画面は開けません。 ng serve は監視を続けるので、ファイルを直して保存すると、そのままビルドし直されます。
なぜ「known property」と言われるのか
Angular は、テンプレートの [名前]="…" を次の順で探します(angular.dev の NG8002 の説明による)。
- その要素に付いているディレクティブ・コンポーネントの入力(
input()・@Input()) - その要素の DOM プロパティ(
input要素のvalueなど)
[(ngModel)] は、FormsModule の中にある NgModel ディレクティブの入力です。FormsModule を imports に入れていないと、1 の候補に NgModel が入りません。2 の input 要素にも ngModel というプロパティは無いので、「input の既知のプロパティではない」というエラーになります。
テストで出るとき
v22 の ng test(Vitest)は、テスト用のファイルもビルドしてから動かします。テストファイルの中に FormsModule の無いコンポーネントがあると、テストを動かす前に同じ NG8002 で止まりました。
Application bundle generation failed. [1.875 seconds]
✘ [ERROR] NG8002: Can't bind to 'ngModel' since it isn't a known property of 'input'. Find more at https://next.angular.dev/errors/NG8002 [plugin angular-compiler]
NgModule 構成のコンポーネント(standalone: false)を、TestBed の declarations に入れてテストするときは、別の番号で出ました。アプリ側の NgModule には FormsModule があり、テストの TestBed には無い、という形です。
TestBed.configureTestingModule({ declarations: [ModForm] }); // FormsModule が無い
Error: NG0303: Can't bind to 'ngModel' since it isn't a known property of 'input' (used in the '_ModForm' component template).
1. If 'input' is an Angular component and it has the 'ngModel' input, then verify that it is a part of an @NgModule where this component is declared.
2. To allow any property add 'NO_ERRORS_SCHEMA' to the '@NgModule.schemas' of this component.
NG0303 は、実行時に出る同じ意味のエラーです。 テストが失敗しました。TestBed にも imports: [FormsModule] を足すと通りました。
TestBed.configureTestingModule({ declarations: [ModForm], imports: [FormsModule] });
standalone のコンポーネントをテストするときは、コンポーネント自身の imports に FormsModule があれば、TestBed に足すものはありません。テストの書き方は関連記事「Angular テスト Vitest 入門|v22の書き方・移行・実行結果つき」で扱っています。
原因別の直し方
① ngModel:FormsModule を imports に入れる
冒頭のコードのとおりです。ngModel を <form> の中で使うときは、name 属性も要ります。name が無いと、FormsModule を入れたあとで次のエラーになりました。
NG01352: If ngModel is used within a form tag, either the name attribute must be set or the form
control must be defined as 'standalone' in ngModelOptions.
Example 1: <input [(ngModel)]="person.firstName" name="first">
Example 2: <input [(ngModel)]="person.firstName" [ngModelOptions]="{standalone: true}">
name を付けるか、フォームに含めない入力なら [ngModelOptions]="{ standalone: true }" を付けます。テンプレート駆動フォームの全体は、関連記事「Angularテンプレート駆動フォーム入門|ngModelとエラー表示」で扱っています。
② formGroup・formControlName:ReactiveFormsModule を入れる
NG8002: Can't bind to 'formGroup' since it isn't a known property of 'form'.
import { ReactiveFormsModule, FormControl, FormGroup } from '@angular/forms';
@Component({
selector: 'app-signup',
imports: [ReactiveFormsModule],
template: `<form [formGroup]="fg"><input formControlName="email"></form>`,
})
export class Signup {
fg = new FormGroup({ email: new FormControl('') });
}
FormsModule と ReactiveFormsModule は別物です。 [formGroup]・[formControl]・formControlName は ReactiveFormsModule の部品なので、FormsModule だけを入れてもこのエラーは消えません。両方を使うコンポーネントなら、両方を imports に並べます。リアクティブフォームは関連記事「Angularリアクティブフォームの使い方|FormGroup・バリデーション」で扱っています。
③ formField:Signal Forms の FormField を入れる
NG8002: Can't bind to 'formField' since it isn't a known property of 'input'.
Signal Forms(Signal で値を持つ新しいフォーム)の [formField] は、@angular/forms/signals の FormField ディレクティブです。FormsModule ではなく、これを入れます。
import { Component, signal } from '@angular/core';
import { form, FormField } from '@angular/forms/signals';
@Component({
selector: 'app-mail',
imports: [FormField],
template: `<input [formField]="f.email">`,
})
export class Mail {
model = signal({ email: '' });
f = form(this.model);
}
Signal Forms の API は関連記事「Angular Signal Forms入門|v22安定版のAPI早見表と完成コード」で扱っています。
④ 自作コンポーネント:入力名の誤り・input() の付け忘れ
@Component({ selector: 'app-child', template: `{{ title() }}` })
export class Child {
title = input(''); // 入力
plain = ''; // ただのフィールド(入力ではない)
}
<app-child [titel]="'a'" /> <!-- 名前の誤り -->
<app-child [plain]="'b'" /> <!-- input() が付いていない -->
NG8002: Can't bind to 'titel' since it isn't a known property of 'app-child'.
1. If 'app-child' is an Angular component and it has 'titel' input, then verify that it is included in the '@Component.imports' of this component.
2. If 'app-child' is a Web Component then add 'CUSTOM_ELEMENTS_SCHEMA' to the '@Component.schemas' of this component to suppress this message.
3. To allow any property add 'NO_ERRORS_SCHEMA' to the '@Component.schemas' of this component.
この例では Child は imports に入っていました。それでも「imports を確かめて」という案内が出ます。 案内の 1 だけを見て imports を探し続けるより、先に子コンポーネントの入力名を見ます。
| 確かめること | 例 |
|---|---|
| 入力名の綴りが子と同じか | titel → title |
子のフィールドに input() か @Input() が付いているか |
plain = '' → plain = input('') |
input() に別名(alias)を付けていないか |
input('', { alias: 'heading' }) なら [heading] |
子コンポーネントを imports に入れたか |
imports: [Child] |
input() の使い方は関連記事「Angular input・output・modelの使い方|親子の受け渡し」で扱っています。案内の 3 の NO_ERRORS_SCHEMA は、すべての不明なプロパティを許すので、綴りの誤りもビルドで見つからなくなります。
⑤ スペルミス
NG8002: Can't bind to 'ngModle' since it isn't a known property of 'input'.
FormsModule を入れていても、綴りが違えば出ます。ngModel は大文字・小文字も区別します(ngmodel も別の名前です)。
⑥ DOM プロパティが無いもの:attr. を付ける
[名前] は、DOM のプロパティに値を入れます。HTML の属性だけがあって、同じ名前のプロパティが無いものは、NG8002 になりました。
NG8002: Can't bind to 'colspan' since it isn't a known property of 'td'.
NG8002: Can't bind to 'data-id' since it isn't a known property of 'div'.
NG8002: Can't bind to 'cx' since it isn't a known property of ':svg:circle'.
attr. を付けると、属性として値が入りました。
<td [attr.colspan]="2">…</td> <!-- colspan="2" -->
<td [colSpan]="3">…</td> <!-- DOM プロパティ名なら attr. は無くてよい:colspan="3" -->
<div [attr.data-id]="7"></div> <!-- data-id="7" -->
<svg><circle [attr.cx]="5" r="2" /></svg> <!-- cx="5" -->
| 書きたいもの | エラーになった書き方 | 通った書き方 |
|---|---|---|
| 表のセル結合 | [colspan] |
[attr.colspan] か [colSpan] |
data-* 属性 |
[data-id] |
[attr.data-id] |
| SVG の属性 | [cx] |
[attr.cx] |
| ARIA 属性 | (エラーにならなかった) | [aria-label]・[attr.aria-label] |
v22.2.2 では [aria-label]="label" は NG8002 にならず、aria-label="閉じる" が入りました。 angular.dev のバインディングの説明にも、ARIA 属性に文字列をバインドできると書かれています。属性バインディングで null を渡すと、その属性は消えます。
⑦ Angular 以外のカスタム要素:CUSTOM_ELEMENTS_SCHEMA
Web Components(ブラウザ標準のカスタム要素)を使うと、要素名とプロパティの両方でエラーが出ました。
NG8001: 'my-widget' is not a known element:
1. If 'my-widget' is an Angular component, then verify that it is included in the '@Component.imports' of this component.
2. If 'my-widget' is a Web Component then add 'CUSTOM_ELEMENTS_SCHEMA' to the '@Component.schemas' of this component to suppress this message.
NG8002: Can't bind to 'value' since it isn't a known property of 'my-widget'.
import { Component, CUSTOM_ELEMENTS_SCHEMA } from '@angular/core';
@Component({
selector: 'app-host',
schemas: [CUSTOM_ELEMENTS_SCHEMA],
template: `<my-widget [value]="1"></my-widget>`,
})
export class Host {}
これでビルドが通り、my-widget 要素の value プロパティに数値の 1 が入りました(属性 value は付きません)。angular.dev では、CUSTOM_ELEMENTS_SCHEMA は「- を含む Angular 以外の要素と、- を含むプロパティ名」を許す設定と説明されています。Angular のコンポーネントにこれを付けると、④ の入力名の誤りもビルドで見つからなくなるので、カスタム要素を使うコンポーネントにだけ付けます。
NgModule 構成の場合
standalone: false のコンポーネントは、そのコンポーネントを declarations に持つ NgModule の imports に FormsModule を入れます。
@NgModule({
declarations: [ProfileComponent],
imports: [CommonModule, FormsModule], // ← ProfileComponent を宣言した NgModule に入れる
})
export class ProfileModule {}
| よくある状況 | 見るところ |
|---|---|
AppModule にはあるのに出る |
コンポーネントが別の機能モジュールで宣言されていないか |
共有モジュール(SharedModule)経由で使う |
SharedModule の exports に FormsModule があるか |
| 遅延ロードのモジュールで出る | 遅延ロードされる NgModule 自身の imports に入っているか |
NgModule の imports は、その NgModule の中で宣言したコンポーネントにしか効きません。v22.2.2 では、どの NgModule にも宣言していない standalone: false のコンポーネントでも、NG8002 が出ました。
直したあとの確かめ方
直したコンポーネントを ng build して Chromium で開き、値が入るかを読み取った結果です。
| 書き方 | 画面で読み取れた値 |
|---|---|
[(ngModel)]="name"(FormsModule あり) |
ngModel の値 |
[formGroup] + formControlName |
reactive@example.com |
[formField]="f.email" |
signal@example.com |
<app-child [title]="…"> |
子のタイトル |
[attr.colspan]="2" |
colspan="2" |
[aria-label]="label" |
aria-label="閉じる" |
<my-widget [value]="1">(スキーマあり) |
プロパティ value が 1 |
よくある質問
Q. app.config.ts に importProvidersFrom(FormsModule) を書けば全体で使えますか。
A. providers に入るのはサービスなどの提供元です。NG8002 はビルド時に「そのコンポーネントの imports から見えるディレクティブ」だけで判定されるので、ngModel は、テンプレートを持つコンポーネントの imports に入れます。提供元のエラーは関連記事「NullInjectorError No provider forの直し方|原因一覧」で扱っています。
Q. 多くのコンポーネントで FormsModule を書くのが手間です。
A. standalone 構成では、使うコンポーネントごとに imports に書く形です。よく一緒に使う部品をまとめたいときは、export const FORM_IMPORTS = [FormsModule, ReactiveFormsModule] as const; のような配列を作り、imports: [FORM_IMPORTS] と書く方法もあります。この形でもビルドが通り、ngModel が使えました。
Q. エディタでは赤線が出ないのに、ビルドで出ます(またはその逆)。
A. エディタの拡張機能(Angular Language Service)とビルドで、読んでいる設定やファイルが違うことがあります。ng build の結果を正として、エディタは再起動して読み直します。
Q. NO_ERRORS_SCHEMA を付ければ消えますか。
A. 消えますが、NG8002 の検査自体が止まるので、綴りの誤りなども見つからなくなります。エラーの名前ごとに上の表の直し方を当てるほうが、後で困りにくくなります。
まとめ
- NG8002 は「その名前の入力を持つ部品が、そのコンポーネントから見えていない」というビルド時のエラー
ngModelはFormsModule、formGroupはReactiveFormsModule、formFieldはFormFieldを、テンプレートを持つコンポーネントのimportsに入れる- 自作コンポーネントでは、入力名の綴りと
input()の付け忘れを先に見る(案内文はimportsを指すが、原因は名前のことが多い) - 属性だけのもの(
colspan・data-*・SVG)はattr.。ARIA は v22.2.2 では[aria-label]で通った - テストの
TestBedでは NG0303 として出る。TestBedのimportsにも足す
参考・出典
確認日はいずれも 2026年10月12日です。
- Angular「NG8002: Invalid Attribute」:https://angular.dev/errors/NG8002
- Angular「Binding dynamic text, properties and attributes」:https://angular.dev/guide/templates/binding
- Angular「Building a template-driven form」:https://angular.dev/guide/forms/template-driven-forms
- Angular「CUSTOM_ELEMENTS_SCHEMA」:https://angular.dev/api/core/CUSTOM_ELEMENTS_SCHEMA
- Hora de Codar「Erro: Can't Bind to ngModel Since It Isn't a Known Property of input」:https://horadecodar.com.br/erro-cant-bind-to-ngmodel-since-it-isnt-a-known-property-of-input/
本記事の内容は、ご自由にお使いください。
ご利用の際は、出典として本ページへのリンクを記載いただけますようお願いします。
(記載例)出典:株式会社RJC「Can't bind to 'ngModel'の直し方|NG8002の原因一覧」
株式会社RJC ― SI事業・SES事業・AI駆動開発。RJCは一緒に成長を楽しめる会社です。
WE ARE HIRING
RJCで一緒に開発しながら、
成長を楽しみませんか?
RJCは、Web・モバイル・AIを活用した開発プロジェクトで、テックリードやPM・PMOも活躍するシステム開発会社です。会社を知る、待遇を確かめる、話を聞いてみる。気になるところ見てみてください!
- 127日年間休日
- 12時間平均残業時間
- 毎日ガチャ遊びココロも大切にする福利厚生。アマギフなどの賞品ラインナップ!
ほかにも、チケットレストラン、書籍読み放題、2年ごとの慰労報奨(休暇 or 金一封)、11期連続の黒字決算。