package adminaudit import ( "time" "hfb_sys/backend/internal/model" "gorm.io/datatypes" "gorm.io/gorm" ) type Repository struct { db *gorm.DB } func NewRepository(db *gorm.DB) *Repository { return &Repository{db: db} } func (r *Repository) List(query Query) (*PaginatedResult, error) { db := r.db.Table("audit_logs AS al"). Select(`al.id, al.actor_type, al.actor_id, COALESCE(au.username, '') AS actor_username, COALESCE(au.nickname, '') AS actor_nickname, al.action, al.biz_type, al.biz_id, al.ip, al.user_agent, al.detail, al.created_at`). Joins("LEFT JOIN admin_users AS au ON au.id = al.actor_id AND al.actor_type = ?", "admin") countDB := r.db.Model(&model.AuditLog{}) if query.ActorID > 0 { db = db.Where("al.actor_id = ?", query.ActorID) countDB = countDB.Where("actor_id = ?", query.ActorID) } if query.Action != "" { db = db.Where("al.action = ?", query.Action) countDB = countDB.Where("action = ?", query.Action) } if query.BizType != "" { db = db.Where("al.biz_type = ?", query.BizType) countDB = countDB.Where("biz_type = ?", query.BizType) } var total int64 if err := countDB.Count(&total).Error; err != nil { return nil, err } offset := (query.Page - 1) * query.PageSize var rows []auditLogRow if err := db.Order("al.id DESC").Offset(offset).Limit(query.PageSize).Scan(&rows).Error; err != nil { return nil, err } items := make([]LogDTO, 0, len(rows)) for _, row := range rows { items = append(items, row.toDTO()) } return &PaginatedResult{Items: items, Total: total, Page: query.Page, PageSize: query.PageSize}, nil } type auditLogRow struct { ID uint64 ActorType string ActorID uint64 ActorUsername string ActorNickname string Action string BizType string BizID *uint64 IP string UserAgent string Detail datatypes.JSON CreatedAt time.Time } func (row auditLogRow) toDTO() LogDTO { return LogDTO{ ID: row.ID, ActorType: row.ActorType, ActorID: row.ActorID, ActorUsername: row.ActorUsername, ActorNickname: row.ActorNickname, Action: row.Action, BizType: row.BizType, BizID: row.BizID, IP: row.IP, UserAgent: row.UserAgent, Detail: row.Detail, CreatedAt: row.CreatedAt, } }