Angular Jest测试中mat-select的panelClass绑定NG0303报错排查
Angular Jest迁移后MatSelect
panelClass绑定报错解决方案 问题背景
Angular项目构建正常,其他含MatSelect的组件测试也无异常,但从Karma迁移到Jest(Angular 16/17/18版本)后,DropdownWithVirtualScrollComponent组件测试出现以下报错:
console.error NG0303: Can't bind to 'panelClass' since it isn't a known property of 'mat-select' (used in the 'DropdownWithVirtualScrollComponent' component template). 1. If 'mat-select' is an Angular component and it has the 'panelClass' input, then verify that it is a part of an @NgModule where this component is declared. 2. If 'mat-select' is a Web Component then add 'CUSTOM_ELEMENTS_SCHEMA' to the '@NgModule.schemas' of this component to suppress this message. 3. To allow any property add 'NO_ERRORS_SCHEMA' to the '@NgModule.schemas' of this component.
异常细节
- 通过
@ViewChild获取mat-select实例并打印panelClass,能正常输出设置的字符串:
fit('should create', () => { console.log(component.matselect.panelClass); // 此处可正常输出设置的字符串 expect(component).toBeTruthy(); });
- 测试代码的
beforeEach中已导入MatSelectModule:
await TestBed.configureTestingModule({ imports: [MatSelectModule, ...]})
- 即使在测试模块中添加
NO_ERRORS_SCHEMA,报错仍然存在 - 组件特殊点:mat-select的
formControl是通过@Input从父组件传入([formControl]="formControlRef",@Input() formControlRef: UntypedFormControl;),而非内部创建新的FormControl实例
解决方案
1. 补全MatSelect相关依赖模块
Jest的模板编译逻辑与Karma存在差异,需确保测试模块中不仅导入MatSelectModule,还要补充其依赖的核心模块:
await TestBed.configureTestingModule({ imports: [ MatSelectModule, MatOptionModule, // 模板用到<mat-option>时必须导入 ReactiveFormsModule // 支持formControl绑定 // 其他组件依赖的模块 ], declarations: [DropdownWithVirtualScrollComponent], schemas: [NO_ERRORS_SCHEMA] // 最后尝试添加,优先排查依赖 }).compileComponents();
2. 显式传入模拟的FormControl实例
组件依赖外部传入的formControlRef,Jest测试时需手动提供一个初始化后的实例,避免模板渲染时因未初始化触发隐式错误:
let formControlRef: UntypedFormControl; beforeEach(async () => { formControlRef = new UntypedFormControl(''); await TestBed.configureTestingModule({ imports: [MatSelectModule, MatOptionModule, ReactiveFormsModule], declarations: [DropdownWithVirtualScrollComponent] }).compileComponents(); }); beforeEach(() => { fixture = TestBed.createComponent(DropdownWithVirtualScrollComponent); component = fixture.componentInstance; // 手动注入父组件传入的FormControl component.formControlRef = formControlRef; fixture.detectChanges(); });
3. 检查Jest测试配置
确保jest.config.js/jest.config.ts使用适配Angular 16+的预设配置:
module.exports = { preset: 'jest-preset-angular', setupFilesAfterEnv: ['<rootDir>/setup-jest.ts'], globalSetup: 'jest-preset-angular/global-setup', // 其他自定义配置 };
同时确认setup-jest.ts正确初始化测试环境:
import 'jest-preset-angular/setup-jest';
4. 清理Jest缓存
Jest缓存的旧编译结果可能导致异常,执行命令清理缓存后重新测试:
npx jest --clearCache
内容的提问来源于stack exchange,提问作者ilya.chepurnoy
相关产品推荐
相关产品推荐

