Guidewire点击按钮时List view未刷新重复添加行问题
问题现象
点击按钮时,作为局部页面(partial page)的Listview无法正常刷新,每次点击按钮都会持续追加行数据,造成列表数据重复累加。
相关实现代码
驾驶人添加逻辑的相关函数代码如下:
function getDriversFromPolicy_CA7() : CA7CommAutoDriver[] { var drivers = this.Policy.LatestPeriod.CA7Line.Drivers // **this** 指向Contingency Entity var excludeDrivers = this.ExcludeDrivers_CA7.toList() // Contingency实体包含ExcludeDrivers_CA7数组 if(excludeDrivers.Empty) { drivers?.each(\driver -> this.addToExcludeDrivers_CA7(driver) ) } else { drivers.each(\driver -> { if (excludeDrivers.where(\elt -> elt.LicenseNumber == driver.LicenseNumber).toList().Count == 0) { this.addToExcludeDrivers_CA7(driver) } }) } return this.ExcludeDrivers_CA7 } function getDriversFromTransaction_CA7() : CA7CommAutoDriver[] { var drivers = this.PolicyPeriod.CA7Line.Drivers.toList() var excludeDrivers = this.ExcludeDrivers_CA7.toList() if(this.ExcludeDrivers_CA7.IsEmpty) { drivers?.each(\driver -> this.addToExcludeDrivers_CA7(driver) ) } else { // this.ExcludeDrivers_CA7.toList().retainAll(drivers.toList()) drivers.each(\driver -> { if (excludeDrivers.where(\elt -> elt.LicenseNumber == driver.LicenseNumber).toList().Count == 0) { this.addToExcludeDrivers_CA7(driver) } }) } return this.ExcludeDrivers_CA7 } function removeDrivers_CA7(driver : CA7CommAutoDriver) { this.removeFromExcludeDrivers_CA7(driver) }
参考资料
- PCF配置截图
- UI运行效果截图
原因分析
列表重复累加的核心原因有两点:
- 数据层逻辑缺陷:两个获取驾驶人的函数均采用增量追加逻辑,仅判断新数据是否已存在就写入
ExcludeDrivers_CA7持久化数组,完全没有处理「旧数据已从源drivers列表中移除」的场景;同时注释掉的retainAll逻辑写法无效——toList()会生成数组副本,在副本上调用retainAll不会修改原持久化数组,等于没有执行清理操作。如果去重时存在对象引用不一致的问题,哪怕是同一个驾驶人,也会被判定为新数据重复追加。 - 前端配置问题:PCF端局部刷新如果配置为追加加载模式、没有绑定Listview全量重载的触发规则,也会导致每次点击都把返回的全量数据追加到现有列表末尾,造成重复。
修复方案
根据业务场景二选一即可:
方案1:不需要保留用户手动选择的排除项(每次加载全量同步源数据)
直接在每次拉取源数据后清空旧的排除列表,再全量写入最新数据,从根源避免增量追加带来的重复问题:
function getDriversFromPolicy_CA7() : CA7CommAutoDriver[] { const latestDrivers = this.Policy.LatestPeriod.CA7Line.Drivers ?: [] // 全量清空旧数据 this.ExcludeDrivers_CA7.clear() // 写入最新的源数据 latestDrivers.each(driver -> this.addToExcludeDrivers_CA7(driver)) return this.ExcludeDrivers_CA7 } function getDriversFromTransaction_CA7() : CA7CommAutoDriver[] { const latestDrivers = this.PolicyPeriod.CA7Line.Drivers.toList() ?: [] // 全量清空旧数据 this.ExcludeDrivers_CA7.clear() // 写入最新的源数据 latestDrivers.each(driver -> this.addToExcludeDrivers_CA7(driver)) return this.ExcludeDrivers_CA7 } function removeDrivers_CA7(driver : CA7CommAutoDriver) { this.removeFromExcludeDrivers_CA7(driver) }
PCF端配置按钮刷新规则时,将Listview的加载模式设置为Overwrite(覆盖)而非Append(追加),刷新目标绑定整个Listview组件即可。
方案2:需要保留用户手动操作的排除项
如果用户可以手动勾选排除驾驶人、需要在刷新时保留用户操作,就优化增量同步逻辑:每次同步先剔除源数据里已经不存在的旧条目,再用LicenseNumber作为唯一键判断是否需要追加新条目,避免对象引用不一致导致的重复判断失效:
function getDriversFromTransaction_CA7() : CA7CommAutoDriver[] { const latestDrivers = this.PolicyPeriod.CA7Line.Drivers.toList() ?: [] const latestLicenseSet = latestDrivers.collect(d -> d.LicenseNumber).toSet() // 第一步:删除源数据里已经不存在的旧条目 this.ExcludeDrivers_CA7.removeIf(d -> !latestLicenseSet.contains(d.LicenseNumber)) // 第二步:用驾照号做唯一键,追加源里新增的条目 const existLicenseSet = this.ExcludeDrivers_CA7.collect(d -> d.LicenseNumber).toSet() latestDrivers.each(driver -> { if (!existLicenseSet.contains(driver.LicenseNumber)) { this.addToExcludeDrivers_CA7(driver) } }) return this.ExcludeDrivers_CA7 }
getDriversFromPolicy_CA7函数按照相同逻辑修改即可。
内容的提问来源于stack exchange,提问作者Madhu
相关产品推荐
相关产品推荐

