add the first 2 operations

Michael MurΓ© created

Change summary

bug/comment_test.go              | 12 +++++++
bug/operations/create.go         | 45 ++++++++++++++++++++++++++
bug/operations/create_test.go    | 31 ++++++++++++++++++
bug/operations/operation.go      | 19 +++++++++++
bug/operations/operation_test.go | 57 ++++++++++++++++++++++++++++++++++
bug/operations/set_title.go      | 24 ++++++++++++++
6 files changed, 188 insertions(+)

Detailed changes

bug/comment_test.go πŸ”—

@@ -0,0 +1,12 @@
+package bug
+
+import "testing"
+
+func TestCommentEquality(t *testing.T) {
+	c1 := Comment{}
+	c2 := Comment{}
+
+	if c1 != c2 {
+		t.Fatal()
+	}
+}

bug/operations/create.go πŸ”—

@@ -0,0 +1,45 @@
+package operations
+
+import (
+	"github.com/MichaelMure/git-bug/bug"
+	"reflect"
+)
+
+// CreateOperation define the initial creation of a bug
+
+var _ Operation = CreateOperation{}
+
+type CreateOperation struct {
+	Title   string
+	Message string
+	Author  bug.Person
+}
+
+func NewCreateOp(author bug.Person, title, message string) CreateOperation {
+	return CreateOperation{
+		Title:   title,
+		Message: message,
+		Author:  author,
+	}
+}
+
+func (op CreateOperation) OpType() OperationType {
+	return CREATE
+}
+
+func (op CreateOperation) Apply(snapshot bug.Snapshot) bug.Snapshot {
+	empty := bug.Snapshot{}
+
+	if !reflect.DeepEqual(snapshot, empty) {
+		panic("Create operation should never be applied on a non-empty snapshot")
+	}
+
+	snapshot.Title = op.Title
+	snapshot.Comments = []bug.Comment{
+		{
+			Message: op.Message,
+			Author:  op.Author,
+		},
+	}
+	return snapshot
+}

bug/operations/create_test.go πŸ”—

@@ -0,0 +1,31 @@
+package operations
+
+import (
+	"github.com/MichaelMure/git-bug/bug"
+	"reflect"
+	"testing"
+)
+
+func TestCreate(t *testing.T) {
+	snapshot := bug.Snapshot{}
+
+	var rene = bug.Person{
+		Name:  "RenΓ© Descartes",
+		Email: "rene@descartes.fr",
+	}
+
+	create := NewCreateOp(rene, "title", "message")
+
+	snapshot = create.Apply(snapshot)
+
+	expected := bug.Snapshot{
+		Title: "title",
+		Comments: []bug.Comment{
+			{Author: rene, Message: "message"},
+		},
+	}
+
+	if !reflect.DeepEqual(snapshot, expected) {
+		t.Fail()
+	}
+}

bug/operations/operation.go πŸ”—

@@ -0,0 +1,19 @@
+package operations
+
+import (
+	"github.com/MichaelMure/git-bug/bug"
+)
+
+type OperationType int
+
+const (
+	UNKNOW OperationType = iota
+	CREATE
+	SET_TITLE
+	ADD_COMMENT
+)
+
+type Operation interface {
+	OpType() OperationType
+	Apply(snapshot bug.Snapshot) bug.Snapshot
+}

bug/operations/operation_test.go πŸ”—

@@ -0,0 +1,57 @@
+package operations
+
+import (
+	"github.com/MichaelMure/git-bug/bug"
+	"testing"
+)
+
+// Different type with the same fields
+type CreateOperation2 struct {
+	Title   string
+	Message string
+}
+
+func (op CreateOperation2) OpType() OperationType {
+	return UNKNOW
+}
+
+func (op CreateOperation2) Apply(snapshot bug.Snapshot) bug.Snapshot {
+	// no-op
+	return snapshot
+}
+
+func TestOperationsEquality(t *testing.T) {
+	var rene = bug.Person{
+		Name:  "RenΓ© Descartes",
+		Email: "rene@descartes.fr",
+	}
+
+	var A Operation = NewCreateOp(rene, "title", "message")
+	var B Operation = NewCreateOp(rene, "title", "message")
+	var C Operation = NewCreateOp(rene, "title", "different message")
+
+	if A != B {
+		t.Fatal("Equal value operations should be tested equals")
+	}
+
+	if A == C {
+		t.Fatal("Different value operations should be tested different")
+	}
+
+	D := CreateOperation2{Title: "title", Message: "message"}
+
+	if A == D {
+		t.Fatal("Operations equality should handle the type")
+	}
+
+	var isaac = bug.Person{
+		Name:  "Isaac Newton",
+		Email: "isaac@newton.uk",
+	}
+
+	var E Operation = NewCreateOp(isaac, "title", "message")
+
+	if A == E {
+		t.Fatal("Operation equality should handle the author")
+	}
+}

bug/operations/set_title.go πŸ”—

@@ -0,0 +1,24 @@
+package operations
+
+import "github.com/MichaelMure/git-bug/bug"
+
+var _ Operation = SetTitleOperation{}
+
+type SetTitleOperation struct {
+	Title string
+}
+
+func NewSetTitleOp(title string) SetTitleOperation {
+	return SetTitleOperation{
+		Title: title,
+	}
+}
+
+func (op SetTitleOperation) OpType() OperationType {
+	return SET_TITLE
+}
+
+func (op SetTitleOperation) Apply(snapshot bug.Snapshot) bug.Snapshot {
+	snapshot.Title = op.Title
+	return snapshot
+}