Angular AgGrid数据绑定报错:Cannot read properties of undefined (reading 'api')
Angular AgGrid 报错:Cannot read properties of undefined (reading 'api')
问题现象
调用 this.agGrid.api.setRowData(result.value) 时触发以下错误:
ERROR TypeError: Cannot read properties of undefined (reading 'api')
原代码参考
TS代码
public columnDefs = [ { headerName: 'productTitle', field: 'productTitle', sortable: true, filter: true, }, { headerName: 'productDescription', field: 'productDescription', sortable: true, filter: true, }, ]; public rowData$: Observable<Product[]>; // For accessing the Grid's API @ViewChild('productGrid') agGrid: AgGridAngular; // initialize component ngOnInit() { this.getProducts(); } // fetch all producttypes getProducts(odataQueryString: string = undefined): any { this.productService .getAll_Product(odataQueryString) .subscribe((result: ODataResponse<Product[]>) => { if (result) { this.agGrid.api.setRowData(result.value); } }); }
HTML代码
<div class="body flex-grow-1 px-3"> <div class="container-lg"> <div class="row"> <div class="col-lg-12"> <ag-grid-angular id="productGrid" style="width: 100%; height: 100%" class="ag-theme-alpine" [columnDefs]="columnDefs" [rowData]="rowData$ | async" enablecolresize enablesorting enablefilter rowheight="22" rowselection="multiple" > <ag-grid-column headerName="productTitle" field="productTitle" [width]="125" ></ag-grid-column> <ag-grid-column headerName="productDescription" field="productDescription" [width]="120" ></ag-grid-column> </ag-grid-angular> </div> </div> </div> </div>
错误原因
- 组件实例未初始化:
ngOnInit钩子执行时,AgGrid组件还未完成视图渲染,@ViewChild('productGrid')获取到的agGrid实例为undefined,调用api自然报错。 - 数据绑定方式冲突:HTML中已通过
[rowData]="rowData$ | async"绑定异步数据,同时又在TS中手动调用setRowData,两种方式冗余且易引发逻辑冲突。 - 模板引用缺失:HTML中的
ag-grid-angular未添加模板引用变量#productGrid,导致@ViewChild无法正确定位组件。
解决方法
方法1:使用异步管道绑定(推荐)
符合Angular响应式编程习惯,无需手动操作Grid API:
修改后TS代码
public columnDefs = [ { headerName: 'productTitle', field: 'productTitle', sortable: true, filter: true, }, { headerName: 'productDescription', field: 'productDescription', sortable: true, filter: true, }, ]; public rowData$: Observable<Product[]>; ngOnInit() { this.getProducts(); } getProducts(odataQueryString: string = undefined): void { // 直接将接口返回的Observable赋值给rowData$,交由async管道处理 this.rowData$ = this.productService.getAll_Product(odataQueryString); }
修改后HTML代码
<div class="body flex-grow-1 px-3"> <div class="container-lg"> <div class="row"> <div class="col-lg-12"> <ag-grid-angular id="productGrid" style="width: 100%; height: 100%" class="ag-theme-alpine" [columnDefs]="columnDefs" [rowData]="rowData$ | async" [enableColResize]="true" [enableSorting]="true" [enableFilter]="true" [rowHeight]="22" [rowSelection]="'multiple'" > </ag-grid-angular> </div> </div> </div> </div>
注意:HTML属性需遵循Angular驼峰命名规范,例如
enablecolresize改为[enableColResize]="true",否则配置可能不生效;同时移除了重复的列定义(TS中已声明columnDefs)。
方法2:手动调用Grid API(需确保实例就绪)
如果必须通过API操作数据,推荐使用AgGrid官方的 gridReady 事件获取API:
修改后TS代码
public columnDefs = [ { headerName: 'productTitle', field: 'productTitle', sortable: true, filter: true, }, { headerName: 'productDescription', field: 'productDescription', sortable: true, filter: true, }, ]; private gridApi: any; ngOnInit() { this.getProducts(); } // Grid初始化完成时触发,获取API实例 onGridReady(params: any) { this.gridApi = params.api; } getProducts(odataQueryString: string = undefined): void { this.productService.getAll_Product(odataQueryString) .subscribe((result: ODataResponse<Product[]>) => { // 先判断API实例是否存在,再设置数据 if (result && this.gridApi) { this.gridApi.setRowData(result.value); } }); }
修改后HTML代码
<div class="body flex-grow-1 px-3"> <div class="container-lg"> <div class="row"> <div class="col-lg-12"> <ag-grid-angular id="productGrid" style="width: 100%; height: 100%" class="ag-theme-alpine" [columnDefs]="columnDefs" [enableColResize]="true" [enableSorting]="true" [enableFilter]="true" [rowHeight]="22" [rowSelection]="'multiple'" (gridReady)="onGridReady($event)" > </ag-grid-angular> </div> </div> </div> </div>
内容的提问来源于stack exchange,提问作者Jean-François Beaulieu
相关产品推荐
相关产品推荐

