feat(finance): include pickup profit in dashboard

This commit is contained in:
yml2213
2026-08-09 20:36:19 +08:00
parent 8fb7d3bac0
commit 211b9f012a
4 changed files with 136 additions and 13 deletions
@@ -11,11 +11,15 @@ func (r *Repository) Dashboard(ctx context.Context, query DashboardQuery) (*Dash
if err != nil {
return nil, err
}
summary, err := r.summary(ctx, query)
pickup, err := r.pickupSummary(ctx, query)
if err != nil {
return nil, err
}
pickup, err := r.pickupSummary(ctx, query)
summary, err := r.summary(ctx, query, pickup)
if err != nil {
return nil, err
}
mohong, err := r.mohongSummary(ctx, query)
if err != nil {
return nil, err
}
@@ -27,6 +31,7 @@ func (r *Repository) Dashboard(ctx context.Context, query DashboardQuery) (*Dash
Summary: *summary,
DailyItems: dailyItems,
PickupSummary: *pickup,
MohongSummary: *mohong,
DisbursementSummary: *disbursement,
GeneratedAt: timeutil.ShanghaiNow(),
}, nil
@@ -59,7 +64,31 @@ func (r *Repository) pickupSummary(ctx context.Context, query DashboardQuery) (*
}, nil
}
func (r *Repository) summary(ctx context.Context, query DashboardQuery) (*FinanceSummaryDTO, error) {
// mohongSummary 撞车商城按支付订单统计交易流水,不计入平台利润。
func (r *Repository) mohongSummary(ctx context.Context, query DashboardQuery) (*MohongSummaryDTO, error) {
db := r.db.WithContext(ctx)
var row struct {
FlowAmountCent int64
RefundAmountCent int64
PaidOrderCount int64
}
if err := db.Table("payment_orders").
Select(`COALESCE(SUM(CASE WHEN biz_type = 'mohong_pay' AND status = 'paid' THEN amount_cent ELSE 0 END), 0) AS flow_amount_cent,
COALESCE(SUM(CASE WHEN biz_type = 'mohong_refund' AND status = 'refunded' THEN amount_cent ELSE 0 END), 0) AS refund_amount_cent,
COALESCE(SUM(CASE WHEN biz_type = 'mohong_pay' AND status = 'paid' THEN 1 ELSE 0 END), 0) AS paid_order_count`).
Where("created_at >= ? AND created_at <= ?", query.StartDate, query.EndDate).
Scan(&row).Error; err != nil {
return nil, err
}
return &MohongSummaryDTO{
FlowAmountCent: row.FlowAmountCent,
RefundAmountCent: row.RefundAmountCent,
NetAmountCent: row.FlowAmountCent - row.RefundAmountCent,
PaidOrderCount: row.PaidOrderCount,
}, nil
}
func (r *Repository) summary(ctx context.Context, query DashboardQuery, pickup *PickupSummaryDTO) (*FinanceSummaryDTO, error) {
db := r.db.WithContext(ctx)
var payment paymentSummaryRow
if err := db.Table("payment_orders AS po").
@@ -138,12 +167,18 @@ func (r *Repository) summary(ctx context.Context, query DashboardQuery) (*Financ
return nil, err
}
pickupProfitAmountCent := int64(0)
if pickup != nil {
pickupProfitAmountCent = pickup.ProfitAmountCent
}
return &FinanceSummaryDTO{
TotalFlowAmountCent: payment.TotalFlowAmountCent,
TotalRefundAmountCent: payment.TotalRefundAmountCent,
PendingRefundAmountCent: payment.PendingRefundAmountCent,
ChannelNetAmountCent: payment.TotalFlowAmountCent - payment.TotalRefundAmountCent,
PlatformIncomeAmountCent: settlement.PlatformIncomeAmountCent,
PlatformIncomeAmountCent: settlement.PlatformIncomeAmountCent + pickupProfitAmountCent,
NormalOrderProfitAmountCent: settlement.PlatformIncomeAmountCent,
PickupProfitAmountCent: pickupProfitAmountCent,
OwnerShouldIncomeAmountCent: settlement.OwnerShouldIncomeAmountCent,
OwnerWalletIncomeAmountCent: settlement.OwnerWalletIncomeAmountCent,
OwnerEffectiveSettlementAmountCent: settlement.OwnerEffectiveSettlementAmountCent,
@@ -222,6 +257,17 @@ func (r *Repository) dailyItems(ctx context.Context, query DashboardQuery) ([]Fi
return nil, err
}
pickupProfits := make([]dailyPickupProfitRow, 0)
if err := db.Table("admin_pickups").
Select(`DATE(completed_at) AS date,
COALESCE(SUM(profit_amount_cent), 0) AS profit_amount_cent`).
Where("status = ?", "completed").
Where("completed_at >= ? AND completed_at <= ?", query.StartDate, query.EndDate).
Group("DATE(completed_at)").
Scan(&pickupProfits).Error; err != nil {
return nil, err
}
// 每日预计收入:尚未结算订单的下单预估平台手续费,按下单日期归集,口径与 summary 一致。
estimates := make([]dailyEstimatedRow, 0)
if err := db.Table("rental_orders").
@@ -275,6 +321,13 @@ func (r *Repository) dailyItems(ctx context.Context, query DashboardQuery) ([]Fi
item.OfflineSettlementPendingCount = row.OfflineSettlementPendingCount
itemsByDate[date] = item
}
for _, row := range pickupProfits {
date := dailyDateKey(row.Date)
item := itemsByDate[date]
item.Date = date
item.PlatformIncomeAmountCent += row.ProfitAmountCent
itemsByDate[date] = item
}
for _, row := range estimates {
date := dailyDateKey(row.Date)
item := itemsByDate[date]
@@ -353,6 +406,11 @@ type dailySettlementRow struct {
SettledOrderCount int64
}
type dailyPickupProfitRow struct {
Date string
ProfitAmountCent int64
}
type dailyEstimatedRow struct {
Date string
EstimatedIncomeAmountCent int64