github.com/hoffie/larasync@v0.0.0-20151025221940-0384d2bddcef/repository/nibStore_test.go (about)

     1  package repository
     2  
     3  import (
     4  	"bytes"
     5  	"fmt"
     6  	"io/ioutil"
     7  	"path/filepath"
     8  
     9  	"github.com/agl/ed25519"
    10  
    11  	"github.com/hoffie/larasync/helpers/crypto"
    12  	"github.com/hoffie/larasync/repository/content"
    13  	"github.com/hoffie/larasync/repository/nib"
    14  
    15  	. "gopkg.in/check.v1"
    16  )
    17  
    18  type NIBStoreTest struct {
    19  	dir                string
    20  	repository         *Repository
    21  	nibStore           *NIBStore
    22  	storage            content.Storage
    23  	transactionManager *TransactionManager
    24  }
    25  
    26  var _ = Suite(&NIBStoreTest{})
    27  
    28  func (t *NIBStoreTest) SetUpTest(c *C) {
    29  	t.dir = c.MkDir()
    30  	t.repository = New(filepath.Join(t.dir, "repo"))
    31  	t.repository.Create()
    32  
    33  	pubKey, privKey, err := ed25519.GenerateKey(
    34  		bytes.NewBufferString("just some deterministic 'random' bytes"))
    35  	c.Assert(err, IsNil)
    36  
    37  	err = t.repository.keys.SetSigningPrivateKey(*privKey)
    38  	c.Assert(err, IsNil)
    39  	signingPubKey, err := t.repository.keys.SigningPublicKey()
    40  	c.Assert(*pubKey, DeepEquals, signingPubKey)
    41  
    42  	fileStorage := content.NewFileStorage(filepath.Join(t.dir, "nibs"))
    43  	err = fileStorage.CreateDir()
    44  	c.Assert(err, IsNil)
    45  
    46  	t.storage = fileStorage
    47  
    48  	transactionStorage := content.NewFileStorage(filepath.Join(t.dir, "transactions"))
    49  	err = transactionStorage.CreateDir()
    50  	c.Assert(err, IsNil)
    51  
    52  	t.transactionManager = newTransactionManager(
    53  		transactionStorage,
    54  		t.repository.GetManagementDir())
    55  	t.nibStore = newNIBStore(
    56  		t.storage,
    57  		t.repository.keys,
    58  		t.transactionManager,
    59  	)
    60  }
    61  
    62  func (t *NIBStoreTest) getTestNIB() *nib.NIB {
    63  	n := &nib.NIB{ID: "test"}
    64  	n.AppendRevision(&nib.Revision{})
    65  	n.AppendRevision(&nib.Revision{})
    66  	return n
    67  }
    68  
    69  func (t *NIBStoreTest) addTestNIB(c *C) *nib.NIB {
    70  	n := t.getTestNIB()
    71  	err := t.nibStore.Add(n)
    72  	c.Assert(err, IsNil)
    73  	return n
    74  }
    75  
    76  // It should be able to add a NIB
    77  func (t *NIBStoreTest) TestNibAddition(c *C) {
    78  	testNib := t.addTestNIB(c)
    79  	c.Assert(testNib.ID, Not(Equals), "")
    80  }
    81  
    82  // It should create a transaction with the NIBs ID on
    83  // addition.
    84  func (t *NIBStoreTest) TestTransactionAddition(c *C) {
    85  	testNib := t.addTestNIB(c)
    86  	transaction, err := t.transactionManager.CurrentTransaction()
    87  	c.Assert(err, IsNil)
    88  	c.Assert(transaction.NIBIDs, DeepEquals, []string{testNib.ID})
    89  }
    90  
    91  func (t *NIBStoreTest) TestNibGet(c *C) {
    92  	testNib := t.addTestNIB(c)
    93  	n, err := t.nibStore.Get(testNib.ID)
    94  	c.Assert(err, IsNil)
    95  	c.Assert(n.ID, Equals, testNib.ID)
    96  }
    97  
    98  func (t *NIBStoreTest) TestNibGetSignatureMangled(c *C) {
    99  	testNib := t.addTestNIB(c)
   100  	reader, err := t.storage.Get(testNib.ID)
   101  	data, err := ioutil.ReadAll(reader)
   102  	c.Assert(err, IsNil)
   103  	err = reader.Close()
   104  	c.Assert(err, IsNil)
   105  	data[len(data)-1] = 50
   106  	err = t.storage.Set(testNib.ID, bytes.NewReader(data))
   107  	c.Assert(err, IsNil)
   108  	_, err = t.nibStore.Get(testNib.ID)
   109  	c.Assert(err, NotNil)
   110  }
   111  
   112  func (t *NIBStoreTest) TestNibGetContentMangled(c *C) {
   113  	testNib := t.addTestNIB(c)
   114  	reader, err := t.storage.Get(testNib.ID)
   115  	data, err := ioutil.ReadAll(reader)
   116  	c.Assert(err, IsNil)
   117  	err = reader.Close()
   118  	c.Assert(err, IsNil)
   119  	data[0] = 50
   120  	err = t.storage.Set(testNib.ID, bytes.NewReader(data))
   121  	c.Assert(err, IsNil)
   122  	_, err = t.nibStore.Get(testNib.ID)
   123  	c.Assert(err, NotNil)
   124  }
   125  
   126  func (t *NIBStoreTest) TestNibExistsPositive(c *C) {
   127  	testNib := t.addTestNIB(c)
   128  	c.Assert(t.nibStore.Exists(testNib.ID), Equals, true)
   129  }
   130  
   131  func (t *NIBStoreTest) TestNibExistsNegative(c *C) {
   132  	c.Assert(t.nibStore.Exists("Does not exist"), Equals, false)
   133  }
   134  
   135  func (t *NIBStoreTest) TestNibVerificationSignatureError(c *C) {
   136  	testNib := t.addTestNIB(c)
   137  	reader, err := t.storage.Get(testNib.ID)
   138  	defer reader.Close()
   139  	data, err := ioutil.ReadAll(reader)
   140  	c.Assert(err, IsNil)
   141  	data[len(data)-1] = 50
   142  
   143  	_, err = t.nibStore.VerifyAndParseBytes(data)
   144  	c.Assert(err, Equals, ErrSignatureVerification)
   145  }
   146  
   147  func (t *NIBStoreTest) TestNibVerificationMarshallingError(c *C) {
   148  	n := t.getTestNIB()
   149  	rawNIB := &bytes.Buffer{}
   150  	_, err := n.WriteTo(rawNIB)
   151  	c.Assert(err, IsNil)
   152  	// corrupt the NIB
   153  	nibBytes := rawNIB.Bytes()
   154  	nibBytes[0] = 50
   155  
   156  	// sign it:
   157  	key, err := t.repository.keys.SigningPrivateKey()
   158  	c.Assert(err, IsNil)
   159  	output := &bytes.Buffer{}
   160  	sw := crypto.NewSigningWriter(key, output)
   161  	_, err = sw.Write(nibBytes)
   162  	c.Assert(err, IsNil)
   163  	err = sw.Finalize()
   164  	c.Assert(err, IsNil)
   165  
   166  	_, err = t.nibStore.VerifyAndParseBytes(output.Bytes())
   167  	c.Assert(err, Equals, ErrUnMarshalling)
   168  }
   169  
   170  func (t *NIBStoreTest) TestNibVerification(c *C) {
   171  	testNib := t.addTestNIB(c)
   172  	reader, err := t.storage.Get(testNib.ID)
   173  	defer reader.Close()
   174  	c.Assert(err, IsNil)
   175  
   176  	data, err := ioutil.ReadAll(reader)
   177  	c.Assert(err, IsNil)
   178  
   179  	_, err = t.nibStore.VerifyAndParseBytes(data)
   180  	c.Assert(err, IsNil)
   181  }
   182  
   183  // It should return all added bytes
   184  func (t *NIBStoreTest) TestGetAllBytes(c *C) {
   185  	for i := 0; i < 100; i++ {
   186  		n := t.getTestNIB()
   187  		n.ID = fmt.Sprintf("test%d", i)
   188  		t.nibStore.Add(n)
   189  	}
   190  	found := 0
   191  
   192  	channel, err := t.nibStore.GetAllBytes()
   193  	c.Assert(err, IsNil)
   194  
   195  	for _ = range channel {
   196  		found++
   197  	}
   198  
   199  	c.Assert(found, Equals, 100)
   200  }
   201  
   202  // It should Return all nib bytes
   203  func (t *NIBStoreTest) TestGetAll(c *C) {
   204  	for i := 0; i < 100; i++ {
   205  		n := t.getTestNIB()
   206  		n.ID = fmt.Sprintf("test%d", i)
   207  		t.nibStore.Add(n)
   208  	}
   209  	seen := []string{}
   210  
   211  	channel, err := t.nibStore.GetAll()
   212  	c.Assert(err, IsNil)
   213  
   214  	for n := range channel {
   215  		if n == nil {
   216  			c.Error("error from channel")
   217  			return
   218  		}
   219  		for _, existingNib := range seen {
   220  			if existingNib == n.ID {
   221  				c.Error("Double nib found.")
   222  			}
   223  		}
   224  		seen = append(seen, n.ID)
   225  	}
   226  
   227  	c.Assert(len(seen), Equals, 100)
   228  
   229  }
   230  
   231  func (t *NIBStoreTest) TestGetFrom(c *C) {
   232  	for i := 0; i < 100; i++ {
   233  		n := t.getTestNIB()
   234  		n.ID = fmt.Sprintf("test%d", i)
   235  		t.nibStore.Add(n)
   236  	}
   237  
   238  	transaction, err := t.transactionManager.CurrentTransaction()
   239  	c.Assert(err, IsNil)
   240  	for i := 0; i < 5; i++ {
   241  		transaction, err = t.transactionManager.Get(transaction.PreviousID)
   242  		c.Assert(err, IsNil)
   243  	}
   244  
   245  	expectedIds := []string{}
   246  	for i := 95; i < 100; i++ {
   247  		expectedIds = append(expectedIds, fmt.Sprintf("test%d", i))
   248  	}
   249  	foundIds := []string{}
   250  	channel, err := t.nibStore.GetFrom(transaction.ID)
   251  
   252  	for n := range channel {
   253  		foundIds = append(foundIds, n.ID)
   254  	}
   255  
   256  	c.Assert(expectedIds, DeepEquals, foundIds)
   257  }
   258  
   259  func (t *NIBStoreTest) TestGetBytesFrom(c *C) {
   260  	for i := 0; i < 100; i++ {
   261  		n := t.getTestNIB()
   262  		n.ID = fmt.Sprintf("test%d", i)
   263  		t.nibStore.Add(n)
   264  	}
   265  
   266  	transaction, err := t.transactionManager.CurrentTransaction()
   267  	c.Assert(err, IsNil)
   268  	for i := 0; i < 5; i++ {
   269  		transaction, err = t.transactionManager.Get(transaction.PreviousID)
   270  		c.Assert(err, IsNil)
   271  	}
   272  
   273  	channel, err := t.nibStore.GetBytesFrom(transaction.ID)
   274  
   275  	found := 0
   276  	for _ = range channel {
   277  		found++
   278  	}
   279  
   280  	c.Assert(found, Equals, 5)
   281  }