结合使用Bootstrap Vue表和分页功能,以从REST API中获取数据

问题描述

给出以下Vue组件:

  • 父级组件(我们称其为ParentComponent
  • 一个自定义组件,该组件封装了样式表,包括基于Bootstrap Vue的分页。我们称之为PaginatedTable

我想在Vue应用程序中安排以下内容

  1. ParentComponent从REST API获取记录列表。该请求本身包括两个查询参数startlimit,因此该组件只能获取所有记录的子集。
  2. ParentComponent将结果列表传递到PaginatedTable
  3. 如果用户循环浏览该分页ParentComponent将仅为下一页/选定页面重新加载记录列表。

这是我当前的实现,乍一看似乎可行,但不知何故,我有点胆怯地意识到我的实现有点复杂。

有没有更简单(更像Vue的方式)的方法

PaginatedTable.vue

    <template lang="pug">
      div
        b-table(
          :items="items"
          :fields="fields"
          stacked="md"
          striped
          responsive
          :sort-by="sortBy"
          :sort-desc="sortDesc"
          per-page=0
        )
          // this enables passing in scoped slots for custom data rendering from the parent component
          // https://bootstrap-vue.org/docs/components/table#custom-data-rendering
          template(v-for="slotName in Object.keys($scopedSlots)" v-slot:[slotName]="slotScope")
            slot(:name="slotName" v-bind="slotScope")
        b-pagination(
          v-if="totalRows > perPage"
          v-model="currentPage"
          :total-rows="totalRows"
          :per-page="perPage"
          @change="onPageChange"
        ).float-sm-right.pt-2
        .clearfix
    </template>
    
    <script>
    export default {
      props: {
        // b-table properties
        items: {
          type: Array,required: true,default: () => []
        },fields: {
          type: Array,required: false,sortBy: {
          type: String,default: null
        },sortDesc: {
          type: Boolean,default: true
        },// b-pagination properties
        currentPage: {
          type: Number,default: 1
        },totalRows: {
          type: Number,default: 0
        },perPage: {
          type: Number,default: 1
        }
      },methods: {
        onPageChange(newPage) {
          this.$emit("page-change",newPage);
        }
      }
    };
    </script>

ParentComponent.vue

    <template lang="pug">
        template(v-if="!loading")
            paginated-table(
                v-else
                :fields="fields"
                :items="items"
                sort-by="date"
                :currentPage="currentPage"
                :totalRows="totalRows"
                @page-change="onPageChange"
            )
    </template>
    
    <script>
    
    export default {
      data() {
        return {
          items: [],totalRows: 0,currentPage: 1,perPage: 1,loading: false,loadingSucceeded: false,fields: [
            {
              key: "name",label: this.$t("nameColumn"),sortable: true
            },{
              key: "type",label: this.$t("typeColumn"),{
              key: "date",label: this.$t("dateColumn"),sortable: true,sortDirection: "desc"
            }
          ]
        };
      },watch: {
        currentPage: function() {
          this.fetchData();
        }
      },mounted() {
        this.fetchData();
      },methods: {
        async fetchData() {
          this.loading = true;
          try {
            const response = await SomeService.fetchData(
              (this.currentPage - 1) * this.perPage,this.perPage
            );
            this.items = response.data;
            this.totalRows = Number.parseInt(response.headers["x-total-count"]);
            this.loadingSucceeded = true;
          } catch (error) {
            this.loadingSucceeded = false;
          } finally {
            this.loading = false;
          }
        },onPageChange(newPage) {
          this.currentPage = newPage;
        }
      }
    };
    </script>

解决方法

暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!

如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。

小编邮箱:dio#foxmail.com (将#修改为@)