1. 为什么后端分页的勾选是个“坑”?
大家好,我是老张,一个在前后端摸爬滚打了十多年的老码农。今天想和大家聊聊一个在Vue项目里,尤其是用ElementUI做后台管理系统时,几乎人人都会踩的“坑”:el-table后端分页时的跨页勾选。
想象一下这个场景:你正在做一个用户管理或者订单管理的页面,数据量很大,必须用后端分页。产品经理提了个需求,要支持批量操作,比如批量删除用户、批量导出订单。你心想,这简单,给el-table加个type="selection"的列不就完事了?结果,当你勾选了第一页的几条数据,满怀期待地翻到第二页,再翻回第一页时,傻眼了——刚才辛辛苦苦勾选的记录,全没了!状态根本没保存下来。
这背后的原因其实很简单,但新手很容易被表象迷惑。ElementUI的el-table组件,其勾选状态是与当前渲染的data数组强绑定的。当你切换页码,向后台请求了新一页的数据,并用新数据替换了tableData时,Vue会重新渲染表格。对于表格组件来说,这相当于一个全新的表格实例,它根本不知道上一页你勾选了谁,所以状态自然就丢失了。
网上最常见的解决方案是告诉你用row-key配合reserve-selection属性。我刚开始也试过,但实测下来,在后端分页的场景下,这条路很容易走进死胡同。reserve-selection的设计初衷更多是为了配合前端分页或者某些特定操作(比如清空筛选后重新渲染),它内部维护的状态和我们在后端分页下需要实现的“跨页记忆”逻辑经常打架,导致全选、取消全选、分页切换时状态同步混乱,调试起来让人头大。
所以,我后来的项目里,彻底放弃了依赖el-table自身状态的想法。我们的核心思路变成了:把勾选状态的掌控权,完全收归我们自己手里。让el-table只负责“显示”,我们用一个独立的数组来“记忆”所有被勾选的数据ID。无论用户怎么翻页,我们都拿着这个“记忆清单”去告诉表格:“来,把这一页里,清单上有的数据,都给我勾选上。” 这个思路清晰、可控,也是我今天要分享的实践方案的核心。
2. 核心思路:自己当家做主,管理勾选状态
既然决定自己管理,那我们就得把整套逻辑想清楚。这就像你去超市购物,后端分页好比超市一次只让你看一个货架(一页数据),而你想买的东西可能分布在不同的货架上。你需要一个**购物车(勾选ID数组)**来记录所有你选中的商品,并且每次走到新的货架前,你都要核对一下购物车清单,把当前货架上你想买的商品放进手推车(设置为勾选状态)。
2.1 核心数据结构与事件监听
首先,我们在Vue组件的data里定义几个关键变量:
data() {
return {
// 当前表格展示的数据(当前页)
tableData: [],
// 所有被勾选数据的唯一ID集合,这是我们的“记忆中枢”
selectedIds: [],
// 所有被勾选数据的完整对象集合,方便提交或其他操作
selectedRows: [],
// 分页相关
currentPage: 1,
pageSize: 10,
total: 0,
// 加载状态
tableLoading: false
}
}
这里最重要的就是selectedIds数组。我们将用它来存储所有页码中被用户勾选上的数据行的唯一标识(通常是id、userId这类字段)。无论用户如何翻页,这个数组始终存在于内存中,不会被表格的重新渲染所影响。
接下来,我们需要在el-table上监听几个关键事件,来捕捉用户的每一次勾选动作:
<el-table
ref="myTable"
:data="tableData"
@select="handleSelect"
@select-all="handleSelectAll"
@selection-change="handleSelectionChange"
>
<el-table-column type="selection" width="55"></el-table-colum


786

被折叠的 条评论
为什么被折叠?



