github.com/myafeier/fabric@v1.0.1-0.20170722181825-3a4b1f2bce86/orderer/common/ledger/blackbox_test.go (about)

     1  /*
     2  Copyright IBM Corp. 2016 All Rights Reserved.
     3  
     4  Licensed under the Apache License, Version 2.0 (the "License");
     5  you may not use this file except in compliance with the License.
     6  You may obtain a copy of the License at
     7  
     8                   http://www.apache.org/licenses/LICENSE-2.0
     9  
    10  Unless required by applicable law or agreed to in writing, software
    11  distributed under the License is distributed on an "AS IS" BASIS,
    12  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13  See the License for the specific language governing permissions and
    14  limitations under the License.
    15  */
    16  
    17  package ledger_test
    18  
    19  import (
    20  	"bytes"
    21  	"reflect"
    22  	"testing"
    23  
    24  	. "github.com/hyperledger/fabric/orderer/common/ledger"
    25  	cb "github.com/hyperledger/fabric/protos/common"
    26  	ab "github.com/hyperledger/fabric/protos/orderer"
    27  )
    28  
    29  type ledgerTestable interface {
    30  	Initialize() (ledgerTestFactory, error)
    31  	Name() string
    32  }
    33  
    34  type ledgerTestFactory interface {
    35  	New() (Factory, ReadWriter)
    36  	Destroy() error
    37  	Persistent() bool
    38  }
    39  
    40  var testables []ledgerTestable
    41  
    42  func allTest(t *testing.T, test func(ledgerTestFactory, *testing.T)) {
    43  	for _, lt := range testables {
    44  
    45  		t.Log("Running test for", lt.Name())
    46  
    47  		func() {
    48  			lf, err := lt.Initialize()
    49  			if err != nil {
    50  				t.Fatalf("Error initializing %s: %s", lt.Name(), err)
    51  			}
    52  			test(lf, t)
    53  			err = lf.Destroy()
    54  			if err != nil {
    55  				t.Fatalf("Error destroying %s: %s", lt.Name(), err)
    56  			}
    57  		}()
    58  
    59  		t.Log("Completed test successfully for", lt.Name())
    60  	}
    61  }
    62  
    63  func TestInitialization(t *testing.T) {
    64  	allTest(t, testInitialization)
    65  }
    66  
    67  func testInitialization(lf ledgerTestFactory, t *testing.T) {
    68  	_, li := lf.New()
    69  	if li.Height() != 1 {
    70  		t.Fatalf("Block height should be 1")
    71  	}
    72  	block := GetBlock(li, 0)
    73  	if block == nil {
    74  		t.Fatalf("Error retrieving genesis block")
    75  	}
    76  
    77  }
    78  
    79  func TestReinitialization(t *testing.T) {
    80  	allTest(t, testReinitialization)
    81  }
    82  
    83  func testReinitialization(lf ledgerTestFactory, t *testing.T) {
    84  	if !lf.Persistent() {
    85  		t.Log("Skipping test as persistence is not available for this ledger type")
    86  		return
    87  	}
    88  	olf, oli := lf.New()
    89  	aBlock := CreateNextBlock(oli, []*cb.Envelope{&cb.Envelope{Payload: []byte("My Data")}})
    90  	err := oli.Append(aBlock)
    91  	if err != nil {
    92  		t.Fatalf("Error appending block: %s", err)
    93  	}
    94  	olf.Close()
    95  
    96  	_, li := lf.New()
    97  	if li.Height() != 2 {
    98  		t.Fatalf("Block height should be 2")
    99  	}
   100  	block := GetBlock(li, 1)
   101  	if block == nil {
   102  		t.Fatalf("Error retrieving block 1")
   103  	}
   104  	if !bytes.Equal(block.Header.Hash(), aBlock.Header.Hash()) {
   105  		t.Fatalf("Block hashes did no match")
   106  	}
   107  }
   108  
   109  func TestAddition(t *testing.T) {
   110  	allTest(t, testAddition)
   111  }
   112  
   113  func testAddition(lf ledgerTestFactory, t *testing.T) {
   114  	_, li := lf.New()
   115  	genesis := GetBlock(li, 0)
   116  	if genesis == nil {
   117  		t.Fatalf("Could not retrieve genesis block")
   118  	}
   119  	prevHash := genesis.Header.Hash()
   120  
   121  	li.Append(CreateNextBlock(li, []*cb.Envelope{&cb.Envelope{Payload: []byte("My Data")}}))
   122  	if li.Height() != 2 {
   123  		t.Fatalf("Block height should be 2")
   124  	}
   125  	block := GetBlock(li, 1)
   126  	if block == nil {
   127  		t.Fatalf("Error retrieving genesis block")
   128  	}
   129  	if !bytes.Equal(block.Header.PreviousHash, prevHash) {
   130  		t.Fatalf("Block hashes did no match")
   131  	}
   132  }
   133  
   134  func TestRetrieval(t *testing.T) {
   135  	allTest(t, testRetrieval)
   136  }
   137  
   138  func testRetrieval(lf ledgerTestFactory, t *testing.T) {
   139  	_, li := lf.New()
   140  	li.Append(CreateNextBlock(li, []*cb.Envelope{&cb.Envelope{Payload: []byte("My Data")}}))
   141  	it, num := li.Iterator(&ab.SeekPosition{Type: &ab.SeekPosition_Oldest{}})
   142  	defer it.Close()
   143  	if num != 0 {
   144  		t.Fatalf("Expected genesis block iterator, but got %d", num)
   145  	}
   146  	signal := it.ReadyChan()
   147  	select {
   148  	case <-signal:
   149  	default:
   150  		t.Fatalf("Should be ready for block read")
   151  	}
   152  	block, status := it.Next()
   153  	if status != cb.Status_SUCCESS {
   154  		t.Fatalf("Expected to successfully read the genesis block")
   155  	}
   156  	if block.Header.Number != 0 {
   157  		t.Fatalf("Expected to successfully retrieve the genesis block")
   158  	}
   159  	signal = it.ReadyChan()
   160  	select {
   161  	case <-signal:
   162  	default:
   163  		t.Fatalf("Should still be ready for block read")
   164  	}
   165  	block, status = it.Next()
   166  	if status != cb.Status_SUCCESS {
   167  		t.Fatalf("Expected to successfully read the second block")
   168  	}
   169  	if block.Header.Number != 1 {
   170  		t.Fatalf("Expected to successfully retrieve the second block but got block number %d", block.Header.Number)
   171  	}
   172  }
   173  
   174  func TestBlockedRetrieval(t *testing.T) {
   175  	allTest(t, testBlockedRetrieval)
   176  }
   177  
   178  func testBlockedRetrieval(lf ledgerTestFactory, t *testing.T) {
   179  	_, li := lf.New()
   180  	it, num := li.Iterator(&ab.SeekPosition{Type: &ab.SeekPosition_Specified{Specified: &ab.SeekSpecified{Number: 1}}})
   181  	defer it.Close()
   182  	if num != 1 {
   183  		t.Fatalf("Expected block iterator at 1, but got %d", num)
   184  	}
   185  	signal := it.ReadyChan()
   186  	select {
   187  	case <-signal:
   188  		t.Fatalf("Should not be ready for block read")
   189  	default:
   190  	}
   191  	li.Append(CreateNextBlock(li, []*cb.Envelope{&cb.Envelope{Payload: []byte("My Data")}}))
   192  	select {
   193  	case <-signal:
   194  	default:
   195  		t.Fatalf("Should now be ready for block read")
   196  	}
   197  	block, status := it.Next()
   198  	if status != cb.Status_SUCCESS {
   199  		t.Fatalf("Expected to successfully read the second block")
   200  	}
   201  	if block.Header.Number != 1 {
   202  		t.Fatalf("Expected to successfully retrieve the second block")
   203  	}
   204  }
   205  
   206  func TestMultichain(t *testing.T) {
   207  	allTest(t, testMultichain)
   208  }
   209  
   210  func testMultichain(lf ledgerTestFactory, t *testing.T) {
   211  	f, _ := lf.New()
   212  	chain1 := "chain1"
   213  	chain2 := "chain2"
   214  
   215  	c1p1 := []byte("c1 payload1")
   216  	c1p2 := []byte("c1 payload2")
   217  
   218  	c2p1 := []byte("c2 payload1")
   219  
   220  	c1, err := f.GetOrCreate(chain1)
   221  	if err != nil {
   222  		t.Fatalf("Error creating chain1: %s", err)
   223  	}
   224  
   225  	c1.Append(CreateNextBlock(c1, []*cb.Envelope{&cb.Envelope{Payload: c1p1}}))
   226  	c1b1 := CreateNextBlock(c1, []*cb.Envelope{&cb.Envelope{Payload: c1p2}})
   227  	c1.Append(c1b1)
   228  
   229  	if c1.Height() != 2 {
   230  		t.Fatalf("Block height for c1 should be 2")
   231  	}
   232  
   233  	c2, err := f.GetOrCreate(chain2)
   234  	if err != nil {
   235  		t.Fatalf("Error creating chain2: %s", err)
   236  	}
   237  	c2b0 := c2.Append(CreateNextBlock(c2, []*cb.Envelope{&cb.Envelope{Payload: c2p1}}))
   238  
   239  	if c2.Height() != 1 {
   240  		t.Fatalf("Block height for c2 should be 1")
   241  	}
   242  
   243  	c1, err = f.GetOrCreate(chain1)
   244  	if err != nil {
   245  		t.Fatalf("Error retrieving chain1: %s", err)
   246  	}
   247  
   248  	if b := GetBlock(c1, 1); !reflect.DeepEqual(c1b1, b) {
   249  		t.Fatalf("Did not properly store block 1 on chain 1:")
   250  	}
   251  
   252  	c2, err = f.GetOrCreate(chain1)
   253  	if err != nil {
   254  		t.Fatalf("Error retrieving chain2: %s", err)
   255  	}
   256  
   257  	if b := GetBlock(c2, 0); reflect.DeepEqual(c2b0, b) {
   258  		t.Fatalf("Did not properly store block 1 on chain 1")
   259  	}
   260  }