package admin_agent import ( "context" "fmt" "time" "sim-server/app/main/api/internal/svc" "sim-server/app/main/api/internal/types" "sim-server/common/globalkey" "github.com/zeromicro/go-zero/core/logx" ) type AdminGetOrderTrendsLogic struct { logx.Logger ctx context.Context svcCtx *svc.ServiceContext } func NewAdminGetOrderTrendsLogic(ctx context.Context, svcCtx *svc.ServiceContext) *AdminGetOrderTrendsLogic { return &AdminGetOrderTrendsLogic{ Logger: logx.WithContext(ctx), ctx: ctx, svcCtx: svcCtx, } } func (l *AdminGetOrderTrendsLogic) AdminGetOrderTrends(req *types.AdminGetOrderTrendsReq) (resp *types.AdminGetOrderTrendsResp, err error) { // 1. Parse date parameters with default to last 30 days var startDate, endDate time.Time if req.StartDate != "" { startDate, err = time.Parse("2006-01-02", req.StartDate) if err != nil { return nil, fmt.Errorf("invalid start_date format: %v", err) } } else { // Default to 30 days ago startDate = time.Now().AddDate(0, 0, -30) } if req.EndDate != "" { endDate, err = time.Parse("2006-01-02", req.EndDate) if err != nil { return nil, fmt.Errorf("invalid end_date format: %v", err) } // Set end date to end of day endDate = time.Date(endDate.Year(), endDate.Month(), endDate.Day(), 23, 59, 59, 0, time.Local) } else { // Default to today endDate = time.Now() } // Ensure start date is before end date if startDate.After(endDate) { return nil, fmt.Errorf("start_date must be before end_date") } // 2. Query all commissions in date range builder := l.svcCtx.AgentCommissionModel.SelectBuilder() builder = builder.Where("del_state = ?", globalkey.DelStateNo) builder = builder.Where("create_time >= ?", startDate) builder = builder.Where("create_time <= ?", endDate) commissions, err := l.svcCtx.AgentCommissionModel.FindAll(l.ctx, builder, "") if err != nil { return nil, fmt.Errorf("failed to query commissions: %v", err) } // 3. Group by date in Go dateMap := make(map[string]*struct { Amount float64 Count int64 }) for _, commission := range commissions { date := commission.CreateTime.Format("2006-01-02") if _, exists := dateMap[date]; !exists { dateMap[date] = &struct { Amount float64 Count int64 }{} } dateMap[date].Amount += commission.Amount dateMap[date].Count++ } // 4. Build sorted response dates := make([]string, 0, len(dateMap)) amounts := make([]float64, 0, len(dateMap)) counts := make([]int64, 0, len(dateMap)) // Sort dates sortedDates := make([]string, 0, len(dateMap)) for date := range dateMap { sortedDates = append(sortedDates, date) } // Simple bubble sort (can be optimized with sort package) for i := 0; i < len(sortedDates); i++ { for j := i + 1; j < len(sortedDates); j++ { if sortedDates[i] > sortedDates[j] { sortedDates[i], sortedDates[j] = sortedDates[j], sortedDates[i] } } } for _, date := range sortedDates { dates = append(dates, date) amounts = append(amounts, dateMap[date].Amount) counts = append(counts, dateMap[date].Count) } return &types.AdminGetOrderTrendsResp{ Dates: dates, Amounts: amounts, Counts: counts, }, nil }