1package bug
 2
 3import (
 4	"github.com/pkg/errors"
 5
 6	"github.com/MichaelMure/git-bug/entities/common"
 7	"github.com/MichaelMure/git-bug/entities/identity"
 8	"github.com/MichaelMure/git-bug/entity"
 9	"github.com/MichaelMure/git-bug/entity/dag"
10	"github.com/MichaelMure/git-bug/util/timestamp"
11)
12
13var _ Operation = &SetStatusOperation{}
14
15// SetStatusOperation will change the status of a bug
16type SetStatusOperation struct {
17	dag.OpBase
18	Status common.Status `json:"status"`
19}
20
21func (op *SetStatusOperation) Id() entity.Id {
22	return dag.IdOperation(op, &op.OpBase)
23}
24
25func (op *SetStatusOperation) Apply(snapshot *Snapshot) {
26	snapshot.Status = op.Status
27	snapshot.addActor(op.Author())
28
29	id := op.Id()
30	item := &SetStatusTimelineItem{
31		// id:         id,
32		combinedId: entity.CombineIds(snapshot.Id(), id),
33		Author:     op.Author(),
34		UnixTime:   timestamp.Timestamp(op.UnixTime),
35		Status:     op.Status,
36	}
37
38	snapshot.Timeline = append(snapshot.Timeline, item)
39}
40
41func (op *SetStatusOperation) Validate() error {
42	if err := op.OpBase.Validate(op, SetStatusOp); err != nil {
43		return err
44	}
45
46	if err := op.Status.Validate(); err != nil {
47		return errors.Wrap(err, "status")
48	}
49
50	return nil
51}
52
53func NewSetStatusOp(author identity.Interface, unixTime int64, status common.Status) *SetStatusOperation {
54	return &SetStatusOperation{
55		OpBase: dag.NewOpBase(SetStatusOp, author, unixTime),
56		Status: status,
57	}
58}
59
60type SetStatusTimelineItem struct {
61	// id         entity.Id
62	combinedId entity.CombinedId
63	Author     identity.Interface
64	UnixTime   timestamp.Timestamp
65	Status     common.Status
66}
67
68func (s SetStatusTimelineItem) CombinedId() entity.CombinedId {
69	return s.combinedId
70}
71
72// IsAuthored is a sign post method for gqlgen
73func (s *SetStatusTimelineItem) IsAuthored() {}
74
75// Open is a convenience function to change a bugs state to Open
76func Open(b Interface, author identity.Interface, unixTime int64, metadata map[string]string) (*SetStatusOperation, error) {
77	op := NewSetStatusOp(author, unixTime, common.OpenStatus)
78	for key, value := range metadata {
79		op.SetMetadata(key, value)
80	}
81	if err := op.Validate(); err != nil {
82		return nil, err
83	}
84	b.Append(op)
85	return op, nil
86}
87
88// Close is a convenience function to change a bugs state to Close
89func Close(b Interface, author identity.Interface, unixTime int64, metadata map[string]string) (*SetStatusOperation, error) {
90	op := NewSetStatusOp(author, unixTime, common.ClosedStatus)
91	for key, value := range metadata {
92		op.SetMetadata(key, value)
93	}
94	if err := op.Validate(); err != nil {
95		return nil, err
96	}
97	b.Append(op)
98	return op, nil
99}