feat(distribution): 通道费改主站承担,并按冷却期自动释放结算
利润不再扣支付通道费;站点可配置结算冷却期,到期自动入账,已释放后退款从收款站钱包回冲。同时修复当日自动批次无法追加、三方回冲打错钱包,以及测试库自增重置被 MySQL 统计缓存跳过的问题。 Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -23,6 +23,7 @@ func distributionTestDB(t *testing.T) *gorm.DB {
|
||||
&model.DistributionSettlementBatch{}, &model.DistributionSettlementItem{},
|
||||
&model.RentalListing{}, &model.GameAccount{}, &model.User{},
|
||||
&model.WalletAccount{}, &model.WalletLedger{}, &model.WithdrawalRequest{},
|
||||
&model.Dispute{},
|
||||
); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
@@ -984,3 +985,93 @@ func TestLiveMoneyMovementFrozenInProduction(t *testing.T) {
|
||||
t.Fatalf("withdraw err = %v", err)
|
||||
}
|
||||
}
|
||||
|
||||
func TestUpdateSiteRewritesPendingReleaseAt(t *testing.T) {
|
||||
db := distributionTestDB(t)
|
||||
repo := NewRepository(db)
|
||||
now := time.Now()
|
||||
site := mustCreateDistSite(t, db, "hold_upd", "冷却回写站", "holdupd.dist.com")
|
||||
if err := db.Model(&site).Update("settlement_hold_days", 7).Error; err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
rule := mustCreateActiveRule(t, db, site.ID, ModeTwoPartyDistributorReceive, now)
|
||||
settledAt := now.Add(-time.Hour).Truncate(time.Second)
|
||||
order := model.RentalOrder{
|
||||
OrderNo: "ORD-HOLD-UPD", ListingID: 1, AccountID: 2, OwnerID: 3, RenterID: 4,
|
||||
Status: "completed", RentAmountCent: 10000, OwnerRentAmountCent: 6000,
|
||||
DistributionSiteID: &site.ID, DistributionRuleVersionID: &rule.ID,
|
||||
SettledAt: &settledAt,
|
||||
}
|
||||
if err := db.Create(&order).Error; err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
oldRelease := settledAt.AddDate(0, 0, 7)
|
||||
if err := db.Create(&model.DistributionOrderFinancial{
|
||||
OrderID: order.ID, SiteID: site.ID, RuleVersionID: rule.ID,
|
||||
GrossPaidAmountCent: 10000, SettlementStatus: "pending", ReleaseAt: &oldRelease,
|
||||
}).Error; err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
holdDays := 0
|
||||
if _, err := repo.UpdateSite(t.Context(), 0, site.ID, UpdateSiteRequest{SettlementHoldDays: &holdDays}); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
var financial model.DistributionOrderFinancial
|
||||
if err := db.Where("order_id = ?", order.ID).First(&financial).Error; err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if financial.ReleaseAt == nil || !financial.ReleaseAt.Equal(settledAt) {
|
||||
t.Fatalf("release_at = %v, want %v after hold days set to 0", financial.ReleaseAt, settledAt)
|
||||
}
|
||||
}
|
||||
|
||||
func TestGetSiteWalletPendingReleaseExcludesOpenDispute(t *testing.T) {
|
||||
db := distributionTestDB(t)
|
||||
repo := NewRepository(db)
|
||||
now := time.Now()
|
||||
site := mustCreateDistSite(t, db, "pend_dsp", "待释放纠纷站", "penddsp.dist.com")
|
||||
rule := mustCreateActiveRule(t, db, site.ID, ModeTwoPartyDistributorReceive, now)
|
||||
past := now.Add(-time.Minute)
|
||||
order := model.RentalOrder{
|
||||
OrderNo: "ORD-PEND-DSP", ListingID: 1, AccountID: 2, OwnerID: 3, RenterID: 4,
|
||||
Status: "completed", RentAmountCent: 10000, OwnerRentAmountCent: 6000, RefundStatus: "none",
|
||||
DistributionSiteID: &site.ID, DistributionRuleVersionID: &rule.ID,
|
||||
}
|
||||
if err := db.Create(&order).Error; err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := db.Create(&model.DistributionOrderFinancial{
|
||||
OrderID: order.ID, SiteID: site.ID, RuleVersionID: rule.ID,
|
||||
GrossPaidAmountCent: 10000, SettlementStatus: "pending", ReleaseAt: &past,
|
||||
}).Error; err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if err := db.Create(&model.DistributionOrderParty{
|
||||
OrderID: order.ID, SiteID: site.ID, PartyRole: "distributor_receive",
|
||||
PartyType: PartyTypeSite, PartyID: site.ID, IncomeAmountCent: 1400,
|
||||
}).Error; err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
walletDTO, err := repo.GetSiteWallet(t.Context(), 0, site.ID)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if walletDTO.PendingReleaseCent != 1400 {
|
||||
t.Fatalf("pending release = %d, want 1400", walletDTO.PendingReleaseCent)
|
||||
}
|
||||
|
||||
if err := db.Create(&model.Dispute{
|
||||
OrderID: order.ID, InitiatorID: 4, TargetUserID: 3, Type: "cannot_login", Status: "open",
|
||||
}).Error; err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
walletDTO, err = repo.GetSiteWallet(t.Context(), 0, site.ID)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if walletDTO.PendingReleaseCent != 0 {
|
||||
t.Fatalf("pending release with open dispute = %d, want 0", walletDTO.PendingReleaseCent)
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user