github.com/adnan-c/fabric_e2e_couchdb@v0.6.1-preview.0.20170228180935-21ce6b23cf91/core/deliverservice/blocksprovider/blocksprovider_test.go (about)

     1  /*
     2  Copyright IBM Corp. 2017 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  package blocksprovider
    17  
    18  import (
    19  	"sync"
    20  	"testing"
    21  	"time"
    22  
    23  	"github.com/hyperledger/fabric/core/deliverservice/mocks"
    24  	"github.com/hyperledger/fabric/protos/common"
    25  	"github.com/hyperledger/fabric/protos/orderer"
    26  	"github.com/stretchr/testify/assert"
    27  )
    28  
    29  // Used to generate a simple test case to initialize delivery
    30  // from given block sequence number.
    31  func makeTestCase(ledgerHeight uint64) func(*testing.T) {
    32  	return func(t *testing.T) {
    33  		gossipServiceAdapter := &mocks.MockGossipServiceAdapter{}
    34  		deliverer := &mocks.MockBlocksDeliverer{Pos: ledgerHeight}
    35  		deliverer.MockRecv = mocks.MockRecv
    36  
    37  		provider := &blocksProviderImpl{
    38  			chainID: "***TEST_CHAINID***",
    39  			gossip:  gossipServiceAdapter,
    40  			client:  deliverer,
    41  		}
    42  
    43  		provider.RequestBlocks(&mocks.MockLedgerInfo{ledgerHeight})
    44  
    45  		var wg sync.WaitGroup
    46  		wg.Add(1)
    47  
    48  		ready := make(chan struct{})
    49  		go func() {
    50  			provider.DeliverBlocks()
    51  			wg.Done()
    52  			// Send notification
    53  			ready <- struct{}{}
    54  		}()
    55  
    56  		time.Sleep(time.Duration(10) * time.Millisecond)
    57  		provider.Stop()
    58  
    59  		select {
    60  		case <-ready:
    61  			{
    62  				// Check that all blocks received eventually get gossiped and locally committed
    63  				assert.True(t, deliverer.RecvCnt == gossipServiceAdapter.AddPayloadsCnt)
    64  				assert.True(t, deliverer.RecvCnt == gossipServiceAdapter.GossipCallsCnt)
    65  				return
    66  			}
    67  		case <-time.After(time.Duration(1) * time.Second):
    68  			{
    69  				t.Fatal("Test hasn't finished in timely manner, failing.")
    70  			}
    71  		}
    72  	}
    73  }
    74  
    75  /*
    76     Test to check whenever blocks provider starts calling new blocks from the
    77     oldest and that eventually it terminates after the Stop method has been called.
    78  */
    79  func TestBlocksProviderImpl_GetBlockFromTheOldest(t *testing.T) {
    80  	makeTestCase(uint64(0))(t)
    81  }
    82  
    83  /*
    84     Test to check whenever blocks provider starts calling new blocks from the
    85     oldest and that eventually it terminates after the Stop method has been called.
    86  */
    87  func TestBlocksProviderImpl_GetBlockFromSpecified(t *testing.T) {
    88  	makeTestCase(uint64(101))(t)
    89  }
    90  
    91  func TestBlocksProvider_CheckTerminationDeliveryResponseStatus(t *testing.T) {
    92  
    93  	tmp := struct{ mocks.MockBlocksDeliverer }{}
    94  
    95  	// Making mocked Recv() function to return DeliverResponse_Status to force block
    96  	// provider to fail and exit, cheking that in that case to block was actually
    97  	// delivered.
    98  	tmp.MockRecv = func(mock *mocks.MockBlocksDeliverer) (*orderer.DeliverResponse, error) {
    99  		return &orderer.DeliverResponse{
   100  			Type: &orderer.DeliverResponse_Status{
   101  				Status: common.Status_SUCCESS,
   102  			},
   103  		}, nil
   104  	}
   105  
   106  	gossipServiceAdapter := &mocks.MockGossipServiceAdapter{}
   107  	provider := &blocksProviderImpl{
   108  		chainID: "***TEST_CHAINID***",
   109  		gossip:  gossipServiceAdapter,
   110  		client:  &tmp,
   111  	}
   112  
   113  	provider.RequestBlocks(&mocks.MockLedgerInfo{0})
   114  
   115  	var wg sync.WaitGroup
   116  	wg.Add(1)
   117  
   118  	ready := make(chan struct{})
   119  	go func() {
   120  		provider.DeliverBlocks()
   121  		wg.Done()
   122  		// Send notification
   123  		ready <- struct{}{}
   124  	}()
   125  
   126  	time.Sleep(time.Duration(10) * time.Millisecond)
   127  	provider.Stop()
   128  
   129  	select {
   130  	case <-ready:
   131  		{
   132  			assert.Equal(t, int32(1), tmp.RecvCnt)
   133  			// No payload should commit locally
   134  			assert.Equal(t, int32(0), gossipServiceAdapter.AddPayloadsCnt)
   135  			// No payload should be transfered to other peers
   136  			assert.Equal(t, int32(0), gossipServiceAdapter.GossipCallsCnt)
   137  			return
   138  		}
   139  	case <-time.After(time.Duration(1) * time.Second):
   140  		{
   141  			t.Fatal("Test hasn't finished in timely manner, failing.")
   142  		}
   143  	}
   144  }