operation_pack.go

  1package bug
  2
  3import (
  4	"bytes"
  5	"encoding/gob"
  6
  7	"github.com/MichaelMure/git-bug/repository"
  8	"github.com/MichaelMure/git-bug/util/git"
  9)
 10
 11// OperationPack represent an ordered set of operation to apply
 12// to a Bug. These operations are stored in a single Git commit.
 13//
 14// These commits will be linked together in a linear chain of commits
 15// inside Git to form the complete ordered chain of operation to
 16// apply to get the final state of the Bug
 17type OperationPack struct {
 18	Operations []Operation
 19
 20	// Private field so not serialized by gob
 21	commitHash git.Hash
 22}
 23
 24// ParseOperationPack will deserialize an OperationPack from raw bytes
 25func ParseOperationPack(data []byte) (*OperationPack, error) {
 26	reader := bytes.NewReader(data)
 27	decoder := gob.NewDecoder(reader)
 28
 29	var opp OperationPack
 30
 31	err := decoder.Decode(&opp)
 32
 33	if err != nil {
 34		return nil, err
 35	}
 36
 37	return &opp, nil
 38}
 39
 40// Serialize will serialise an OperationPack into raw bytes
 41func (opp *OperationPack) Serialize() ([]byte, error) {
 42	var data bytes.Buffer
 43
 44	encoder := gob.NewEncoder(&data)
 45	err := encoder.Encode(*opp)
 46
 47	if err != nil {
 48		return nil, err
 49	}
 50
 51	return data.Bytes(), nil
 52}
 53
 54// Append a new operation to the pack
 55func (opp *OperationPack) Append(op Operation) {
 56	opp.Operations = append(opp.Operations, op)
 57}
 58
 59// IsEmpty tell if the OperationPack is empty
 60func (opp *OperationPack) IsEmpty() bool {
 61	return len(opp.Operations) == 0
 62}
 63
 64// IsValid tell if the OperationPack is considered valid
 65func (opp *OperationPack) IsValid() bool {
 66	return !opp.IsEmpty()
 67}
 68
 69// Write will serialize and store the OperationPack as a git blob and return
 70// its hash
 71func (opp *OperationPack) Write(repo repository.Repo) (git.Hash, error) {
 72	data, err := opp.Serialize()
 73
 74	if err != nil {
 75		return "", err
 76	}
 77
 78	hash, err := repo.StoreData(data)
 79
 80	if err != nil {
 81		return "", err
 82	}
 83
 84	return hash, nil
 85}
 86
 87// Make a deep copy
 88func (opp *OperationPack) Clone() OperationPack {
 89
 90	clone := OperationPack{
 91		Operations: make([]Operation, len(opp.Operations)),
 92		commitHash: opp.commitHash,
 93	}
 94
 95	for i, op := range opp.Operations {
 96		clone.Operations[i] = op
 97	}
 98
 99	return clone
100}