revert: 移除转赠资产禁止兑换积分的限制
经数据核实,转赠后兑换积分属于合法行为(资产转赠后归接收方所有)。 并发漏洞虽然产生了重复转赠/发货记录,但实际经济损失为 0 元: - 18 个重复发货资产中,没有任何一个真正被两方都发了货 - 没有任何资产被重复兑换积分 保留前两个并发修复(SELECT FOR UPDATE + RowsAffected 检查), 回退第三个业务限制(禁止转赠资产兑换积分)。
This commit is contained in:
parent
8229b41382
commit
749464c03e
@ -569,16 +569,6 @@ func (s *service) RedeemInventoryToPoints(ctx context.Context, userID int64, inv
|
||||
return 0, err
|
||||
}
|
||||
|
||||
// 校验转赠来源:通过转赠获得的资产不允许兑换积分(防薅积分漏洞)
|
||||
// 使用写库查询,避免主从延迟导致校验被绕过
|
||||
var transferCnt int64
|
||||
if err := s.repo.GetDbW().Raw("SELECT COUNT(*) FROM user_inventory_transfers WHERE inventory_id = ? AND to_user_id = ?", inventoryID, userID).Scan(&transferCnt).Error; err != nil {
|
||||
return 0, err
|
||||
}
|
||||
if transferCnt > 0 {
|
||||
return 0, fmt.Errorf("transfer_inventory_cannot_redeem")
|
||||
}
|
||||
|
||||
valueCents := inv.ValueCents
|
||||
valueSource := inv.ValueSource
|
||||
valueSnapshotAt := inv.ValueSnapshotAt
|
||||
@ -659,31 +649,6 @@ func (s *service) RedeemInventoriesToPoints(ctx context.Context, userID int64, i
|
||||
return 0, fmt.Errorf("no_valid_inventory")
|
||||
}
|
||||
|
||||
// 3.5 排除通过转赠获得的资产(防薅积分漏洞)
|
||||
// 使用写库查询,避免主从延迟导致校验被绕过
|
||||
invIDs := make([]int64, 0, len(invList))
|
||||
for _, inv := range invList {
|
||||
invIDs = append(invIDs, inv.ID)
|
||||
}
|
||||
var transferredInvs []*model.UserInventoryTransfers
|
||||
if err := s.repo.GetDbW().Raw("SELECT * FROM user_inventory_transfers WHERE inventory_id IN ? AND to_user_id = ?", invIDs, userID).Scan(&transferredInvs).Error; err != nil {
|
||||
return 0, err
|
||||
}
|
||||
transferredSet := make(map[int64]struct{}, len(transferredInvs))
|
||||
for _, t := range transferredInvs {
|
||||
transferredSet[t.InventoryID] = struct{}{}
|
||||
}
|
||||
filteredInvList := make([]*model.UserInventory, 0, len(invList))
|
||||
for _, inv := range invList {
|
||||
if _, isTransferred := transferredSet[inv.ID]; !isTransferred {
|
||||
filteredInvList = append(filteredInvList, inv)
|
||||
}
|
||||
}
|
||||
if len(filteredInvList) == 0 {
|
||||
return 0, fmt.Errorf("transfer_inventory_cannot_redeem")
|
||||
}
|
||||
invList = filteredInvList
|
||||
|
||||
// 4. 按资产快照计算总积分,缺失快照时回退商品价格并回写
|
||||
productIDs := make([]int64, 0, len(invList))
|
||||
productIDSet := make(map[int64]struct{})
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user