package store import ( "context" "database/sql" "fmt" "time" "provisioning/internal/model" ) type Activity struct { DB *sql.DB } func (s *Activity) Log(ctx context.Context, hostID, opID int64, level model.LogLevel, source, message string) (int64, error) { res, err := s.DB.ExecContext(ctx, ` INSERT INTO activity_log(host_id, operation_id, level, message, source) VALUES(?,?,?,?,?) `, hostID, nullInt64(opID), level, message, source) if err != nil { return 0, fmt.Errorf("insert activity: %w", err) } return res.LastInsertId() } func (s *Activity) ListByHost(ctx context.Context, hostID int64, limit int) ([]model.ActivityEntry, error) { if limit <= 0 { limit = 50 } rows, err := s.DB.QueryContext(ctx, ` SELECT id, host_id, COALESCE(operation_id, 0), level, message, source, created_at FROM activity_log WHERE host_id = ? ORDER BY created_at DESC LIMIT ? `, hostID, limit) if err != nil { return nil, fmt.Errorf("list activity: %w", err) } defer rows.Close() var out []model.ActivityEntry for rows.Next() { var e model.ActivityEntry var createdAt string if err := rows.Scan(&e.ID, &e.HostID, &e.OperationID, &e.Level, &e.Message, &e.Source, &createdAt); err != nil { return nil, fmt.Errorf("scan activity: %w", err) } e.CreatedAt, _ = time.Parse(time.RFC3339, createdAt) out = append(out, e) } return out, rows.Err() }