aboutsummaryrefslogtreecommitdiff
path: root/internal/node/secondary/secondary_test.go
diff options
context:
space:
mode:
Diffstat (limited to 'internal/node/secondary/secondary_test.go')
-rw-r--r--internal/node/secondary/secondary_test.go138
1 files changed, 138 insertions, 0 deletions
diff --git a/internal/node/secondary/secondary_test.go b/internal/node/secondary/secondary_test.go
new file mode 100644
index 0000000..164bdf6
--- /dev/null
+++ b/internal/node/secondary/secondary_test.go
@@ -0,0 +1,138 @@
+package secondary
+
+import (
+ "context"
+ "fmt"
+ "testing"
+
+ mocksClient "git.sigsum.org/log-go/internal/mocks/client"
+ mocksDB "git.sigsum.org/log-go/internal/mocks/db"
+ "git.sigsum.org/sigsum-go/pkg/merkle"
+ "git.sigsum.org/sigsum-go/pkg/types"
+ "github.com/golang/mock/gomock"
+)
+
+var (
+ testConfig = Config{
+ LogID: fmt.Sprintf("%x", merkle.HashFn([]byte("logid"))[:]),
+ TreeID: 0,
+ Prefix: "testonly",
+ Deadline: 10,
+ }
+)
+
+// TestHandlers checks that the expected internal handlers are configured
+func TestIntHandlers(t *testing.T) {
+ endpoints := map[types.Endpoint]bool{
+ types.EndpointGetTreeHeadToCosign: false,
+ }
+ node := Secondary{
+ Config: testConfig,
+ }
+ for _, handler := range node.InternalHTTPHandlers() {
+ if _, ok := endpoints[handler.Endpoint]; !ok {
+ t.Errorf("got unexpected endpoint: %s", handler.Endpoint)
+ }
+ endpoints[handler.Endpoint] = true
+ }
+ for endpoint, ok := range endpoints {
+ if !ok {
+ t.Errorf("endpoint %s is not configured", endpoint)
+ }
+ }
+}
+
+func TestFetchLeavesFromPrimary(t *testing.T) {
+ for _, tbl := range []struct {
+ desc string
+ // client.GetUnsignedTreeHead()
+ primaryTHRet types.TreeHead
+ primaryTHErr error
+ // db.GetTreeHead()
+ trillianTHRet *types.TreeHead
+ trillianTHErr error
+ // client.GetLeaves()
+ primaryGetLeavesRet types.Leaves
+ primaryGetLeavesErr error
+ // db.AddSequencedLeaves()
+ trillianAddLeavesExp bool
+ trillianAddLeavesErr error
+ }{
+ {
+ desc: "no tree head from primary",
+ primaryTHErr: fmt.Errorf("mocked error"),
+ },
+ {
+ desc: "no tree head from trillian",
+ primaryTHRet: types.TreeHead{},
+ trillianTHErr: fmt.Errorf("mocked error"),
+ },
+ {
+ desc: "error fetching leaves",
+ primaryTHRet: types.TreeHead{TreeSize: 6},
+ trillianTHRet: &types.TreeHead{TreeSize: 5}, // 6-5 => 1 expected GetLeaves
+ primaryGetLeavesErr: fmt.Errorf("mocked error"),
+ },
+ {
+ desc: "error adding leaves",
+ primaryTHRet: types.TreeHead{TreeSize: 6},
+ trillianTHRet: &types.TreeHead{TreeSize: 5}, // 6-5 => 1 expected GetLeaves
+ primaryGetLeavesRet: types.Leaves{
+ types.Leaf{},
+ },
+ trillianAddLeavesErr: fmt.Errorf("mocked error"),
+ },
+ {
+ desc: "success",
+ primaryTHRet: types.TreeHead{TreeSize: 10},
+ trillianTHRet: &types.TreeHead{TreeSize: 5},
+ primaryGetLeavesRet: types.Leaves{
+ types.Leaf{},
+ },
+ trillianAddLeavesExp: true,
+ },
+ } {
+ func() {
+ ctrl := gomock.NewController(t)
+ defer ctrl.Finish()
+
+ primaryClient := mocksClient.NewMockClient(ctrl)
+ primaryClient.EXPECT().GetUnsignedTreeHead(gomock.Any()).Return(tbl.primaryTHRet, tbl.primaryTHErr)
+
+ trillianClient := mocksDB.NewMockClient(ctrl)
+ if tbl.trillianTHErr != nil || tbl.trillianTHRet != nil {
+ trillianClient.EXPECT().GetTreeHead(gomock.Any()).Return(tbl.trillianTHRet, tbl.trillianTHErr)
+ }
+
+ if tbl.primaryGetLeavesErr != nil || tbl.primaryGetLeavesRet != nil {
+ primaryClient.EXPECT().GetLeaves(gomock.Any(), gomock.Any()).Return(tbl.primaryGetLeavesRet, tbl.primaryGetLeavesErr)
+ if tbl.trillianAddLeavesExp {
+ for i := tbl.trillianTHRet.TreeSize; i < tbl.primaryTHRet.TreeSize-1; i++ {
+ primaryClient.EXPECT().GetLeaves(gomock.Any(), gomock.Any()).Return(tbl.primaryGetLeavesRet, tbl.primaryGetLeavesErr)
+ }
+ }
+ }
+
+ if tbl.trillianAddLeavesErr != nil || tbl.trillianAddLeavesExp {
+ trillianClient.EXPECT().AddSequencedLeaves(gomock.Any(), gomock.Any(), gomock.Any()).Return(tbl.trillianAddLeavesErr)
+ if tbl.trillianAddLeavesExp {
+ for i := tbl.trillianTHRet.TreeSize; i < tbl.primaryTHRet.TreeSize-1; i++ {
+ trillianClient.EXPECT().AddSequencedLeaves(gomock.Any(), gomock.Any(), gomock.Any()).Return(tbl.trillianAddLeavesErr)
+ }
+ }
+ }
+
+ node := Secondary{
+ Config: testConfig,
+ Primary: primaryClient,
+ TrillianClient: trillianClient,
+ }
+
+ node.fetchLeavesFromPrimary(context.Background())
+
+ // NOTE: We are not verifying that
+ // AddSequencedLeaves() is being called with
+ // the right data.
+ }()
+ }
+}