收口审计治理与套餐任务进展
Constraint: 在线热修前必须保存当前迭代分支全部有效代码进展 Confidence: medium Scope-risk: broad Directive: 后续修改需保持审计事件与业务事务边界一致 Tested: git diff --cached --check Not-tested: 未运行全量测试,提交用于切换分支前保存既有工作
This commit is contained in:
93
internal/service/shop_series_grant/audit.go
Normal file
93
internal/service/shop_series_grant/audit.go
Normal file
@@ -0,0 +1,93 @@
|
||||
package shop_series_grant
|
||||
|
||||
import (
|
||||
"context"
|
||||
"strconv"
|
||||
|
||||
"gorm.io/gorm"
|
||||
|
||||
"github.com/break/junhong_cmp_fiber/internal/infrastructure/audit"
|
||||
"github.com/break/junhong_cmp_fiber/internal/model"
|
||||
"github.com/break/junhong_cmp_fiber/pkg/constants"
|
||||
"github.com/break/junhong_cmp_fiber/pkg/errors"
|
||||
)
|
||||
|
||||
type allocationAuditChange struct {
|
||||
before map[string]any
|
||||
after map[string]any
|
||||
}
|
||||
|
||||
func (s *Service) appendGrantAudit(
|
||||
ctx context.Context,
|
||||
tx *gorm.DB,
|
||||
actionCode, summary string,
|
||||
allocation *model.ShopSeriesAllocation,
|
||||
series *model.PackageSeries,
|
||||
shop *model.Shop,
|
||||
beforeData, afterData map[string]any,
|
||||
packageAllocations []*model.ShopPackageAllocation,
|
||||
priceHistories []*model.ShopPackageAllocationPriceHistory,
|
||||
packageChanges map[uint]allocationAuditChange,
|
||||
) error {
|
||||
if s.auditWriter == nil {
|
||||
return errors.New(errors.CodeInvalidStatus, "店铺系列授权统一审计接缝未配置")
|
||||
}
|
||||
resources := []audit.ResourceInput{
|
||||
audit.ShopSeriesAllocationResource(allocation, constants.AuditResourceRelationPrimary, constants.AuditResourceRoleShopSeriesAllocation, beforeData, afterData),
|
||||
audit.PackageSeriesResource(series, constants.AuditResourceRelationReference, constants.AuditResourceRolePackageSeries, nil, nil),
|
||||
audit.ShopResource(shop, constants.AuditResourceRelationReference, constants.AuditResourceRolePackageConfigShop),
|
||||
}
|
||||
for _, packageAllocation := range packageAllocations {
|
||||
change, ok := packageChanges[packageAllocation.ID]
|
||||
if !ok {
|
||||
change.after = map[string]any{
|
||||
"cost_price": packageAllocation.CostPrice, "retail_price": packageAllocation.RetailPrice,
|
||||
"expiry_base_override": packageAllocation.ExpiryBaseOverride, "status": packageAllocation.Status,
|
||||
}
|
||||
}
|
||||
resources = append(resources, audit.ShopPackageAllocationResource(
|
||||
packageAllocation, constants.AuditResourceRelationAffected, constants.AuditResourceRoleShopPackageAllocation, change.before, change.after,
|
||||
))
|
||||
var pkg model.Package
|
||||
if err := tx.WithContext(ctx).Unscoped().Where("id = ?", packageAllocation.PackageID).First(&pkg).Error; err != nil {
|
||||
return errors.Wrap(errors.CodeDatabaseError, err, "查询系列授权套餐审计快照失败")
|
||||
}
|
||||
resources = append(resources, audit.PackageResource(&pkg, constants.AuditResourceRelationReference, constants.AuditResourceRolePackageTarget, nil, nil))
|
||||
}
|
||||
for _, history := range priceHistories {
|
||||
resources = append(resources, audit.ShopPackagePriceHistoryResource(history))
|
||||
}
|
||||
return s.auditWriter.Append(ctx, tx, audit.AppendInput{
|
||||
ActionCode: actionCode, Summary: summary, ScopeType: constants.AuditScopeShop,
|
||||
ScopeID: strconv.FormatUint(uint64(shop.ID), 10), Result: constants.AuditResultSuccess,
|
||||
Resources: resources,
|
||||
})
|
||||
}
|
||||
|
||||
func (s *Service) recordGrantFailure(ctx context.Context, actionCode, summary string, allocation *model.ShopSeriesAllocation, series *model.PackageSeries, shop *model.Shop, beforeData map[string]any, businessErr error) {
|
||||
if allocation == nil || series == nil || shop == nil {
|
||||
return
|
||||
}
|
||||
s.auditWriter.RecordFailure(ctx, s.db, audit.AppendInput{
|
||||
ActionCode: actionCode, Summary: summary, ScopeType: constants.AuditScopeShop,
|
||||
ScopeID: strconv.FormatUint(uint64(shop.ID), 10), Resources: []audit.ResourceInput{
|
||||
audit.ShopSeriesAllocationResource(allocation, constants.AuditResourceRelationPrimary, constants.AuditResourceRoleShopSeriesAllocation, beforeData, nil),
|
||||
audit.PackageSeriesResource(series, constants.AuditResourceRelationReference, constants.AuditResourceRolePackageSeries, nil, nil),
|
||||
audit.ShopResource(shop, constants.AuditResourceRelationReference, constants.AuditResourceRolePackageConfigShop),
|
||||
},
|
||||
}, businessErr)
|
||||
}
|
||||
|
||||
func grantData(allocation *model.ShopSeriesAllocation) map[string]any {
|
||||
if allocation == nil {
|
||||
return nil
|
||||
}
|
||||
return map[string]any{
|
||||
"one_time_commission_amount": allocation.OneTimeCommissionAmount,
|
||||
"commission_tiers": allocation.CommissionTiersJSON,
|
||||
"enable_force_recharge": allocation.EnableForceRecharge,
|
||||
"force_recharge_amount": allocation.ForceRechargeAmount,
|
||||
"force_recharge_trigger_type": allocation.ForceRechargeTriggerType,
|
||||
"status": allocation.Status,
|
||||
}
|
||||
}
|
||||
@@ -6,6 +6,7 @@ import (
|
||||
"context"
|
||||
"time"
|
||||
|
||||
"github.com/break/junhong_cmp_fiber/internal/infrastructure/audit"
|
||||
"github.com/break/junhong_cmp_fiber/internal/model"
|
||||
"github.com/break/junhong_cmp_fiber/internal/model/dto"
|
||||
packagepkg "github.com/break/junhong_cmp_fiber/internal/service/package"
|
||||
@@ -29,6 +30,7 @@ type Service struct {
|
||||
packageStore *postgres.PackageStore
|
||||
packageSeriesStore *postgres.PackageSeriesStore
|
||||
logger *zap.Logger
|
||||
auditWriter *audit.Writer
|
||||
}
|
||||
|
||||
// initialGrantPackage 保存通过创建前校验的套餐及其请求价格。
|
||||
@@ -47,6 +49,7 @@ func New(
|
||||
packageStore *postgres.PackageStore,
|
||||
packageSeriesStore *postgres.PackageSeriesStore,
|
||||
logger *zap.Logger,
|
||||
auditWriter *audit.Writer,
|
||||
) *Service {
|
||||
return &Service{
|
||||
db: db,
|
||||
@@ -57,6 +60,7 @@ func New(
|
||||
packageStore: packageStore,
|
||||
packageSeriesStore: packageSeriesStore,
|
||||
logger: logger,
|
||||
auditWriter: auditWriter,
|
||||
}
|
||||
}
|
||||
|
||||
@@ -299,7 +303,7 @@ func (s *Service) buildGrantResponse(ctx context.Context, allocation *model.Shop
|
||||
|
||||
// Create 创建系列授权
|
||||
// POST /api/admin/shop-series-grants
|
||||
func (s *Service) Create(ctx context.Context, req *dto.CreateShopSeriesGrantRequest) (*dto.ShopSeriesGrantResponse, error) {
|
||||
func (s *Service) Create(ctx context.Context, req *dto.CreateShopSeriesGrantRequest) (_ *dto.ShopSeriesGrantResponse, retErr error) {
|
||||
expiryBaseOverride, err := packagepkg.ValidateExpiryBaseOverride(req.ExpiryBaseOverride, req.ExpiryBaseOverrideSet)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
@@ -324,6 +328,17 @@ func (s *Service) Create(ctx context.Context, req *dto.CreateShopSeriesGrantRequ
|
||||
if err != nil {
|
||||
return nil, errors.New(errors.CodeForbidden, "无权限操作该资源或资源不存在")
|
||||
}
|
||||
allocation := &model.ShopSeriesAllocation{
|
||||
ShopID: req.ShopID, SeriesID: req.SeriesID, Status: constants.StatusEnabled, CommissionTiersJSON: "[]",
|
||||
}
|
||||
businessCommitted := false
|
||||
defer func() {
|
||||
if retErr != nil && !businessCommitted {
|
||||
failedAllocation := *allocation
|
||||
failedAllocation.ID = 0
|
||||
s.recordGrantFailure(ctx, constants.AuditActionShopSeriesGrantCreated, "创建店铺套餐系列授权失败", &failedAllocation, series, targetShop, nil, retErr)
|
||||
}
|
||||
}()
|
||||
|
||||
// 2. 检查重复授权
|
||||
exists, err := s.shopSeriesAllocationStore.ExistsByShopAndSeries(ctx, req.ShopID, req.SeriesID)
|
||||
@@ -354,13 +369,7 @@ func (s *Service) Create(ctx context.Context, req *dto.CreateShopSeriesGrantRequ
|
||||
}
|
||||
|
||||
// 4. 参数验证:仅启用一次性佣金的系列才需要配置佣金金额
|
||||
allocation := &model.ShopSeriesAllocation{
|
||||
ShopID: req.ShopID,
|
||||
SeriesID: req.SeriesID,
|
||||
AllocatorShopID: allocatorShopID,
|
||||
Status: constants.StatusEnabled,
|
||||
CommissionTiersJSON: "[]",
|
||||
}
|
||||
allocation.AllocatorShopID = allocatorShopID
|
||||
allocation.Creator = operatorID
|
||||
allocation.Updater = operatorID
|
||||
|
||||
@@ -423,6 +432,8 @@ func (s *Service) Create(ctx context.Context, req *dto.CreateShopSeriesGrantRequ
|
||||
}
|
||||
|
||||
// 6. 事务中创建 ShopSeriesAllocation + N 条 ShopPackageAllocation
|
||||
createdPackageAllocations := make([]*model.ShopPackageAllocation, 0, len(req.Packages))
|
||||
createdPriceHistories := make([]*model.ShopPackageAllocationPriceHistory, 0, len(req.Packages))
|
||||
err = s.db.WithContext(ctx).Transaction(func(tx *gorm.DB) error {
|
||||
var lockedTargetShop model.Shop
|
||||
if lockErr := tx.WithContext(ctx).
|
||||
@@ -476,23 +487,28 @@ func (s *Service) Create(ctx context.Context, req *dto.CreateShopSeriesGrantRequ
|
||||
if err := txPkgStore.Create(ctx, pkgAlloc); err != nil {
|
||||
return errors.Wrap(errors.CodeDatabaseError, err, "创建套餐分配失败")
|
||||
}
|
||||
if err := txHistoryStore.Create(ctx, &model.ShopPackageAllocationPriceHistory{
|
||||
history := &model.ShopPackageAllocationPriceHistory{
|
||||
AllocationID: pkgAlloc.ID,
|
||||
OldCostPrice: 0,
|
||||
NewCostPrice: *item.CostPrice,
|
||||
ChangeReason: "初始授权",
|
||||
ChangedBy: operatorID,
|
||||
EffectiveFrom: time.Now(),
|
||||
}); err != nil {
|
||||
}
|
||||
if err := txHistoryStore.Create(ctx, history); err != nil {
|
||||
return errors.Wrap(errors.CodeDatabaseError, err, "创建套餐价格历史失败")
|
||||
}
|
||||
createdPackageAllocations = append(createdPackageAllocations, pkgAlloc)
|
||||
createdPriceHistories = append(createdPriceHistories, history)
|
||||
}
|
||||
|
||||
return nil
|
||||
return s.appendGrantAudit(ctx, tx, constants.AuditActionShopSeriesGrantCreated, "创建店铺套餐系列授权", allocation, series, targetShop,
|
||||
nil, grantData(allocation), createdPackageAllocations, createdPriceHistories, nil)
|
||||
})
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
businessCommitted = true
|
||||
|
||||
// 事务提交后构建完整响应(此时 packages 已可查询到)
|
||||
return s.buildGrantResponse(ctx, allocation, series, config)
|
||||
@@ -638,7 +654,7 @@ func (s *Service) List(ctx context.Context, req *dto.ShopSeriesGrantListRequest)
|
||||
|
||||
// Update 更新系列授权
|
||||
// PUT /api/admin/shop-series-grants/:id
|
||||
func (s *Service) Update(ctx context.Context, id uint, req *dto.UpdateShopSeriesGrantRequest) (*dto.ShopSeriesGrantResponse, error) {
|
||||
func (s *Service) Update(ctx context.Context, id uint, req *dto.UpdateShopSeriesGrantRequest) (_ *dto.ShopSeriesGrantResponse, retErr error) {
|
||||
operatorID := middleware.GetUserIDFromContext(ctx)
|
||||
operatorShopID := middleware.GetShopIDFromContext(ctx)
|
||||
|
||||
@@ -649,16 +665,27 @@ func (s *Service) Update(ctx context.Context, id uint, req *dto.UpdateShopSeries
|
||||
}
|
||||
return nil, errors.Wrap(errors.CodeDatabaseError, err, "查询授权记录失败")
|
||||
}
|
||||
before := *allocation
|
||||
series, seriesErr := s.packageSeriesStore.GetByID(ctx, allocation.SeriesID)
|
||||
if seriesErr != nil {
|
||||
return nil, errors.Wrap(errors.CodeDatabaseError, seriesErr, "查询套餐系列失败")
|
||||
}
|
||||
shop, shopErr := s.shopStore.GetByID(ctx, allocation.ShopID)
|
||||
if shopErr != nil {
|
||||
return nil, errors.Wrap(errors.CodeDatabaseError, shopErr, "查询授权店铺失败")
|
||||
}
|
||||
businessCommitted := false
|
||||
defer func() {
|
||||
if retErr != nil && !businessCommitted {
|
||||
s.recordGrantFailure(ctx, constants.AuditActionShopSeriesGrantUpdated, "更新店铺套餐系列授权失败", &before, series, shop, grantData(&before), retErr)
|
||||
}
|
||||
}()
|
||||
|
||||
// 代理只能修改自己分配出去的授权
|
||||
if operatorShopID > 0 && allocation.AllocatorShopID != operatorShopID {
|
||||
return nil, errors.New(errors.CodeForbidden, "无权限操作该授权记录")
|
||||
}
|
||||
|
||||
series, err := s.packageSeriesStore.GetByID(ctx, allocation.SeriesID)
|
||||
if err != nil {
|
||||
return nil, errors.Wrap(errors.CodeDatabaseError, err, "查询套餐系列失败")
|
||||
}
|
||||
config, err := series.GetOneTimeCommissionConfig()
|
||||
if err != nil || config == nil {
|
||||
return nil, errors.New(errors.CodeInternalError, "获取系列佣金配置失败")
|
||||
@@ -713,16 +740,23 @@ func (s *Service) Update(ctx context.Context, id uint, req *dto.UpdateShopSeries
|
||||
}
|
||||
|
||||
allocation.Updater = operatorID
|
||||
if err := s.shopSeriesAllocationStore.Update(ctx, allocation); err != nil {
|
||||
return nil, errors.Wrap(errors.CodeDatabaseError, err, "更新授权记录失败")
|
||||
if err := s.db.WithContext(ctx).Transaction(func(tx *gorm.DB) error {
|
||||
if err := postgres.NewShopSeriesAllocationStore(tx).Update(ctx, allocation); err != nil {
|
||||
return errors.Wrap(errors.CodeDatabaseError, err, "更新授权记录失败")
|
||||
}
|
||||
return s.appendGrantAudit(ctx, tx, constants.AuditActionShopSeriesGrantUpdated, "更新店铺套餐系列授权", allocation, series, shop,
|
||||
grantData(&before), grantData(allocation), nil, nil, nil)
|
||||
}); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
businessCommitted = true
|
||||
|
||||
return s.buildGrantResponse(ctx, allocation, series, config)
|
||||
}
|
||||
|
||||
// ManagePackages 管理授权套餐(新增/更新/删除)
|
||||
// PUT /api/admin/shop-series-grants/:id/packages
|
||||
func (s *Service) ManagePackages(ctx context.Context, id uint, req *dto.ManageGrantPackagesRequest) (*dto.ShopSeriesGrantResponse, error) {
|
||||
func (s *Service) ManagePackages(ctx context.Context, id uint, req *dto.ManageGrantPackagesRequest) (_ *dto.ShopSeriesGrantResponse, retErr error) {
|
||||
expiryBaseOverride, err := packagepkg.ValidateExpiryBaseOverride(req.ExpiryBaseOverride, req.ExpiryBaseOverrideSet)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
@@ -737,12 +771,29 @@ func (s *Service) ManagePackages(ctx context.Context, id uint, req *dto.ManageGr
|
||||
}
|
||||
return nil, errors.Wrap(errors.CodeDatabaseError, err, "查询授权记录失败")
|
||||
}
|
||||
series, seriesErr := s.packageSeriesStore.GetByID(ctx, allocation.SeriesID)
|
||||
if seriesErr != nil {
|
||||
return nil, errors.Wrap(errors.CodeDatabaseError, seriesErr, "查询套餐系列失败")
|
||||
}
|
||||
shop, shopErr := s.shopStore.GetByID(ctx, allocation.ShopID)
|
||||
if shopErr != nil {
|
||||
return nil, errors.Wrap(errors.CodeDatabaseError, shopErr, "查询授权店铺失败")
|
||||
}
|
||||
businessCommitted := false
|
||||
defer func() {
|
||||
if retErr != nil && !businessCommitted {
|
||||
s.recordGrantFailure(ctx, constants.AuditActionShopSeriesGrantPackagesManaged, "管理店铺系列套餐授权失败", allocation, series, shop, nil, retErr)
|
||||
}
|
||||
}()
|
||||
|
||||
// 代理只能操作自己分配的授权
|
||||
if operatorShopID > 0 && allocation.AllocatorShopID != operatorShopID {
|
||||
return nil, errors.New(errors.CodeForbidden, "无权限操作该授权记录")
|
||||
}
|
||||
|
||||
affectedAllocations := make([]*model.ShopPackageAllocation, 0, len(req.Packages))
|
||||
priceHistories := make([]*model.ShopPackageAllocationPriceHistory, 0, len(req.Packages))
|
||||
packageChanges := make(map[uint]allocationAuditChange, len(req.Packages))
|
||||
err = s.db.WithContext(ctx).Transaction(func(tx *gorm.DB) error {
|
||||
txPkgStore := postgres.NewShopPackageAllocationStore(tx)
|
||||
txHistoryStore := postgres.NewShopPackageAllocationPriceHistoryStore(tx)
|
||||
@@ -758,6 +809,11 @@ func (s *Service) ManagePackages(ctx context.Context, id uint, req *dto.ManageGr
|
||||
if deleteErr := txPkgStore.Delete(ctx, existing.ID); deleteErr != nil {
|
||||
return errors.Wrap(errors.CodeDatabaseError, deleteErr, "删除套餐分配失败")
|
||||
}
|
||||
affectedAllocations = append(affectedAllocations, existing)
|
||||
packageChanges[existing.ID] = allocationAuditChange{
|
||||
before: map[string]any{"cost_price": existing.CostPrice, "status": existing.Status},
|
||||
after: map[string]any{"deleted": true},
|
||||
}
|
||||
continue
|
||||
}
|
||||
|
||||
@@ -789,16 +845,22 @@ func (s *Service) ManagePackages(ctx context.Context, id uint, req *dto.ManageGr
|
||||
return errors.Wrap(errors.CodeDatabaseError, updateErr, "更新套餐分配失败")
|
||||
}
|
||||
if oldPrice != costPrice {
|
||||
if historyErr := txHistoryStore.Create(ctx, &model.ShopPackageAllocationPriceHistory{
|
||||
history := &model.ShopPackageAllocationPriceHistory{
|
||||
AllocationID: existing.ID,
|
||||
OldCostPrice: oldPrice,
|
||||
NewCostPrice: costPrice,
|
||||
ChangeReason: "手动调价",
|
||||
ChangedBy: operatorID,
|
||||
EffectiveFrom: time.Now(),
|
||||
}); historyErr != nil {
|
||||
}
|
||||
if historyErr := txHistoryStore.Create(ctx, history); historyErr != nil {
|
||||
return errors.Wrap(errors.CodeDatabaseError, historyErr, "创建套餐价格历史失败")
|
||||
}
|
||||
priceHistories = append(priceHistories, history)
|
||||
affectedAllocations = append(affectedAllocations, existing)
|
||||
packageChanges[existing.ID] = allocationAuditChange{
|
||||
before: map[string]any{"cost_price": oldPrice}, after: map[string]any{"cost_price": costPrice},
|
||||
}
|
||||
}
|
||||
} else {
|
||||
pkg, pkgErr := s.packageStore.GetByID(ctx, item.PackageID)
|
||||
@@ -831,23 +893,35 @@ func (s *Service) ManagePackages(ctx context.Context, id uint, req *dto.ManageGr
|
||||
if createErr := txPkgStore.Create(ctx, pkgAlloc); createErr != nil {
|
||||
return errors.Wrap(errors.CodeDatabaseError, createErr, "创建套餐分配失败")
|
||||
}
|
||||
if historyErr := txHistoryStore.Create(ctx, &model.ShopPackageAllocationPriceHistory{
|
||||
history := &model.ShopPackageAllocationPriceHistory{
|
||||
AllocationID: pkgAlloc.ID,
|
||||
OldCostPrice: 0,
|
||||
NewCostPrice: costPrice,
|
||||
ChangeReason: "新增授权",
|
||||
ChangedBy: operatorID,
|
||||
EffectiveFrom: time.Now(),
|
||||
}); historyErr != nil {
|
||||
}
|
||||
if historyErr := txHistoryStore.Create(ctx, history); historyErr != nil {
|
||||
return errors.Wrap(errors.CodeDatabaseError, historyErr, "创建套餐价格历史失败")
|
||||
}
|
||||
affectedAllocations = append(affectedAllocations, pkgAlloc)
|
||||
priceHistories = append(priceHistories, history)
|
||||
packageChanges[pkgAlloc.ID] = allocationAuditChange{after: map[string]any{
|
||||
"cost_price": pkgAlloc.CostPrice, "retail_price": pkgAlloc.RetailPrice,
|
||||
"expiry_base_override": pkgAlloc.ExpiryBaseOverride, "status": pkgAlloc.Status,
|
||||
}}
|
||||
}
|
||||
}
|
||||
return nil
|
||||
if len(affectedAllocations) == 0 {
|
||||
return nil
|
||||
}
|
||||
return s.appendGrantAudit(ctx, tx, constants.AuditActionShopSeriesGrantPackagesManaged, "管理店铺系列套餐授权", allocation, series, shop,
|
||||
nil, nil, affectedAllocations, priceHistories, packageChanges)
|
||||
})
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
businessCommitted = true
|
||||
|
||||
// 重新查询最新状态
|
||||
return s.Get(ctx, id)
|
||||
@@ -855,7 +929,7 @@ func (s *Service) ManagePackages(ctx context.Context, id uint, req *dto.ManageGr
|
||||
|
||||
// Delete 删除系列授权(软删除)
|
||||
// DELETE /api/admin/shop-series-grants/:id
|
||||
func (s *Service) Delete(ctx context.Context, id uint) error {
|
||||
func (s *Service) Delete(ctx context.Context, id uint) (retErr error) {
|
||||
operatorShopID := middleware.GetShopIDFromContext(ctx)
|
||||
|
||||
allocation, err := s.shopSeriesAllocationStore.GetByID(ctx, id)
|
||||
@@ -865,6 +939,19 @@ func (s *Service) Delete(ctx context.Context, id uint) error {
|
||||
}
|
||||
return errors.Wrap(errors.CodeDatabaseError, err, "查询授权记录失败")
|
||||
}
|
||||
series, seriesErr := s.packageSeriesStore.GetByID(ctx, allocation.SeriesID)
|
||||
if seriesErr != nil {
|
||||
return errors.Wrap(errors.CodeDatabaseError, seriesErr, "查询套餐系列失败")
|
||||
}
|
||||
shop, shopErr := s.shopStore.GetByID(ctx, allocation.ShopID)
|
||||
if shopErr != nil {
|
||||
return errors.Wrap(errors.CodeDatabaseError, shopErr, "查询授权店铺失败")
|
||||
}
|
||||
defer func() {
|
||||
if retErr != nil {
|
||||
s.recordGrantFailure(ctx, constants.AuditActionShopSeriesGrantDeleted, "删除店铺套餐系列授权失败", allocation, series, shop, grantData(allocation), retErr)
|
||||
}
|
||||
}()
|
||||
|
||||
// 代理只能删除自己分配的授权
|
||||
if operatorShopID > 0 && allocation.AllocatorShopID != operatorShopID {
|
||||
@@ -886,7 +973,12 @@ func (s *Service) Delete(ctx context.Context, id uint) error {
|
||||
txPkgStore := postgres.NewShopPackageAllocationStore(tx)
|
||||
|
||||
pkgAllocations, _ := txPkgStore.GetBySeriesAllocationID(ctx, id)
|
||||
packageChanges := make(map[uint]allocationAuditChange, len(pkgAllocations))
|
||||
for _, pa := range pkgAllocations {
|
||||
packageChanges[pa.ID] = allocationAuditChange{
|
||||
before: map[string]any{"cost_price": pa.CostPrice, "retail_price": pa.RetailPrice, "status": pa.Status},
|
||||
after: map[string]any{"deleted": true},
|
||||
}
|
||||
if delErr := txPkgStore.Delete(ctx, pa.ID); delErr != nil {
|
||||
return errors.Wrap(errors.CodeDatabaseError, delErr, "删除套餐分配失败")
|
||||
}
|
||||
@@ -895,6 +987,7 @@ func (s *Service) Delete(ctx context.Context, id uint) error {
|
||||
if delErr := txSeriesStore.Delete(ctx, id); delErr != nil {
|
||||
return errors.Wrap(errors.CodeDatabaseError, delErr, "删除系列授权失败")
|
||||
}
|
||||
return nil
|
||||
return s.appendGrantAudit(ctx, tx, constants.AuditActionShopSeriesGrantDeleted, "删除店铺套餐系列授权", allocation, series, shop,
|
||||
grantData(allocation), map[string]any{"deleted": true}, pkgAllocations, nil, packageChanges)
|
||||
})
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user