fix(商品): 修复收藏/点赞批量写入被 saveAll 静默丢弃

- eb_store_product_relation 使用 (uid, product_id, type, category) 联合主键,
  Model::saveAll() 因主键字段齐全走 UPDATE 分支,导致新记录静默写入失败;
  DAO 新增 insertAll() 直连模型 insertAll 绕过该语义。
- 写入前过滤非正数商品ID(前端未取到 product_id 时会传空值),避免脏数据。
- 批量写入统一使用同一 add_time,便于按批次检索。
This commit is contained in:
吴昊天 2026-10-23 14:09:13 +08:00
parent 9a1b7e5071
commit 61d131b99f
2 changed files with 23 additions and 3 deletions

View File

@ -29,6 +29,18 @@ class StoreProductRelationDao extends BaseDao
return StoreProductRelation::class;
}
/**
* 批量插入,绕过模型 saveAll 语义
* 该表使用 (uid, product_id, type, category) 联合主键,saveAll() 会因主键字段齐全
* 而按 UPDATE 处理,导致新记录静默写入失败
* @param array $data
* @return int
*/
public function insertAll(array $data): int
{
return $this->getModel()->insertAll($data);
}
/**
* 获取收藏列表
* @param array $where

View File

@ -170,15 +170,23 @@ class StoreProductRelationServices extends BaseService
$relationType = strtolower($relationType);
$category = strtolower($category);
$relationData = [];
$productIdS = array_unique($productIdS);
// 过滤非法商品ID(如前端未取到 product_id 时传入的空值),避免写入 product_id=0 的脏数据
$productIdS = array_values(array_unique(array_filter(array_map('intval', $productIdS), function ($productId) {
return $productId > 0;
})));
if (!$productIdS) {
return true;
}
$relationProductIdS = $this->dao->getColumn(['uid' => $uid, 'type' => $relationType, 'category' => $category, 'product_id' => $productIdS], 'product_id');
$addTime = time();
foreach ($productIdS as $productId) {
if (!in_array($productId, $relationProductIdS)) {
$relationData[] = ['uid' => $uid, 'product_id' => $productId, 'type' => $relationType, 'category' => $category];
$relationData[] = ['uid' => $uid, 'product_id' => $productId, 'type' => $relationType, 'category' => $category, 'add_time' => $addTime];
}
}
if ($relationData) {
if (!$this->dao->saveAll($relationData)) {
// 该表为联合主键,Model::saveAll() 会因主键字段齐全而走 UPDATE 分支导致静默不写入,必须直接 insertAll
if ($this->dao->insertAll($relationData) < 1) {
throw new ApiException('添加失败');
}
}