You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Angular Material表格对接GraphQL后端实现分页与报错解决

问题原因

MatTableDataSource构造函数要求传入同步的数组类型数据,你传入的query_data是Apollo Client返回的Observable<Imp_Type[]>异步流对象,本身不具备数组的length、push等属性,因此触发类型不匹配报错。同时你代码里还存在2个隐含问题:

  • 定义的Imp_Type接口中imp_sub_group类型声明错误,实际GraphQL返回的是对象而非字符串
  • 声明的MatPaginator没有绑定到dataSource,分页功能不会生效

修正方案

步骤1:修正接口定义、调整属性声明

把Imp_Type的imp_sub_group类型改为正确的对象结构,同时不要直接初始化dataSource,先做声明。

步骤2:订阅Observable获取数据后初始化数据源

在ngOnInit中订阅query_data,拿到真实数组后再初始化MatTableDataSource,同时在ngAfterViewInit中绑定分页器。

完整修正代码

import { Component, OnInit, ViewChild, AfterViewInit } from '@angular/core';
import { MatPaginator } from '@angular/material/paginator';
import { MatTableDataSource } from '@angular/material/table';
import { Apollo, gql } from 'apollo-angular';
import { map } from 'rxjs/operators';

// 修正imp_sub_group的类型定义
interface ImpSubGroup {
  imp_group_id: string;
  sub_grou_name: string;
}

interface Imp_Type {
  uuid: string;
  imp_type_name: string;
  imp_sub_group: ImpSubGroup;
}

interface Response {
  imp_type: Imp_Type[]
}

// 新增分页参数变量,适配服务端分页
const GET_IMP_TYPE = gql`
query Imp_Type($limit: Int!, $offset: Int!) {
  imp_type (limit: $limit, offset: $offset){
    uuid
    imp_type_name
    imp_sub_group {
      imp_group_id
      sub_grou_name
    }
  }
}
`;

@Component({
  selector: 'app-imp-type',
  templateUrl: './imp-type.component.html',
  styleUrls: ['./imp-type.component.scss']
})
export class ImpTypeComponent implements OnInit, AfterViewInit {
  @ViewChild(MatPaginator) paginator: MatPaginator;
  displayedColumns: string[] = ['uuid', 'imp_type_name', 'sub_grou_name'];
  // 先声明数据源,不要直接初始化
  dataSource: MatTableDataSource<Imp_Type>;

  constructor(private apollo: Apollo) { }

  ngOnInit(): void {
    // 首次加载默认取第一页10条数据
    this.loadData(0, 10);
  }

  ngAfterViewInit(): void {
    // 监听分页切换事件,触发服务端分页请求
    this.paginator.page.subscribe(event => {
      this.loadData(event.pageIndex * event.pageSize, event.pageSize);
    })
  }

  // 封装数据加载逻辑
  private loadData(offset: number, limit: number) {
    this.apollo.watchQuery<Response>({
      query: GET_IMP_TYPE,
      variables: { limit, offset }
    }).valueChanges.pipe(map(result => result.data.imp_type))
    .subscribe(data => {
      this.dataSource = new MatTableDataSource(data);
      this.dataSource.paginator = this.paginator;
    })
  }
}

额外说明

如果你的数据量不大,不需要服务端分页,可以直接一次性拉取所有数据,交由MatTableDataSource自带的客户端分页能力处理,不需要监听page事件重新请求接口。

内容的提问来源于stack exchange,提问作者Talip Akhan

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.05 14:24:02