package service import ( "context" "time" actionsignoff "wucher/internal/domain/action_signoff" ) type ActionSignoffService struct{ repo actionsignoff.Repository } func NewActionSignoffService(repo actionsignoff.Repository) *ActionSignoffService { return &ActionSignoffService{repo: repo} } func (s *ActionSignoffService) GetByFlight(ctx context.Context, flightID []byte) (*actionsignoff.ActionSignoff, error) { return s.repo.GetByFlight(ctx, flightID) } func (s *ActionSignoffService) GetByComplaint(ctx context.Context, complaintID []byte) (*actionsignoff.ActionSignoff, error) { return s.repo.GetByComplaint(ctx, complaintID) } func (s *ActionSignoffService) GetByComplaintIDs(ctx context.Context, complaintIDs [][]byte) (map[string]*actionsignoff.ActionSignoff, error) { return s.repo.GetByComplaintIDs(ctx, complaintIDs) } // UnsignByComplaint clears the signature on the complaint-linked sign-off. No-op when // there is no sign-off for the complaint or it is already unsigned. func (s *ActionSignoffService) UnsignByComplaint(ctx context.Context, complaintID []byte) (*actionsignoff.ActionSignoff, error) { row, err := s.repo.GetByComplaint(ctx, complaintID) if err != nil { return nil, err } if row == nil { return nil, nil } if row.SignedAt == nil { return row, nil } row.SignedAt = nil row.SignedBy = nil if err := s.repo.Update(ctx, row); err != nil { return nil, err } return row, nil } // SignForComplaint records (or re-stamps) the action sign-off linked to a specific // complaint — i.e. "this complaint's corrective action was signed off". Upsert by // complaint: creates the row on first sign, otherwise re-stamps signer/time. func (s *ActionSignoffService) SignForComplaint(ctx context.Context, complaintID, flightID, helicopterID []byte, signer []byte) (*actionsignoff.ActionSignoff, error) { row, err := s.repo.GetByComplaint(ctx, complaintID) if err != nil { return nil, err } now := time.Now().UTC() if row == nil { row = &actionsignoff.ActionSignoff{ HelicopterID: append([]byte(nil), helicopterID...), FlightID: append([]byte(nil), flightID...), ComplaintID: append([]byte(nil), complaintID...), SignedAt: &now, SignedBy: append([]byte(nil), signer...), } if err := s.repo.Create(ctx, row); err != nil { return nil, err } return row, nil } row.FlightID = append([]byte(nil), flightID...) row.SignedAt = &now row.SignedBy = append([]byte(nil), signer...) if err := s.repo.Update(ctx, row); err != nil { return nil, err } return row, nil } // Sign records (or re-stamps) the helicopter's action sign-off as signed by the func (s *ActionSignoffService) Sign(ctx context.Context, flightID, helicopterID []byte, signer []byte) (*actionsignoff.ActionSignoff, error) { row, err := s.repo.GetByFlight(ctx, flightID) if err != nil { return nil, err } now := time.Now().UTC() if row == nil { row = &actionsignoff.ActionSignoff{ HelicopterID: append([]byte(nil), helicopterID...), FlightID: append([]byte(nil), flightID...), SignedAt: &now, SignedBy: append([]byte(nil), signer...), } if err := s.repo.Create(ctx, row); err != nil { return nil, err } return row, nil } row.SignedAt = &now row.SignedBy = append([]byte(nil), signer...) if err := s.repo.Update(ctx, row); err != nil { return nil, err } return row, nil } // Unsign clears the signature (check → uncheck). Returns ErrNotFound when there // is nothing to unsign. func (s *ActionSignoffService) Unsign(ctx context.Context, flightID []byte, _ []byte) (*actionsignoff.ActionSignoff, error) { row, err := s.repo.GetByFlight(ctx, flightID) if err != nil { return nil, err } if row == nil { return nil, actionsignoff.ErrNotFound } row.SignedAt = nil row.SignedBy = nil if err := s.repo.Update(ctx, row); err != nil { return nil, err } return row, nil }