Skip to content

Commit

Permalink
[FAB-4533] Use context cancellations in deliveryservice
Browse files Browse the repository at this point in the history
This addresses FAB-4503 and FAB-4489
The reason for the CI failures is that apparently,
closing the underlying gRPC connection doesn't always make Recv() return.

The solution is to use context.WithCancel and use the cancel function
when Disconnect or Close are called and not only close the gRPC stream.

Change-Id: Ia255467345dc6178764a2eb4f1e51167b914eebd
Signed-off-by: Yacov Manevich <yacovm@il.ibm.com>
  • Loading branch information
yacovm committed Jun 10, 2017
1 parent 4eb5815 commit b5f3790
Show file tree
Hide file tree
Showing 2 changed files with 8 additions and 7 deletions.
13 changes: 8 additions & 5 deletions core/deliverservice/client.go
Original file line number Diff line number Diff line change
Expand Up @@ -139,13 +139,14 @@ func (bc *broadcastClient) connect() error {
logger.Error("Failed obtaining connection:", err)
return err
}
abc, err := bc.createClient(conn).Deliver(context.Background())
ctx, cf := context.WithCancel(context.Background())
abc, err := bc.createClient(conn).Deliver(ctx)
if err != nil {
logger.Error("Connection to ", endpoint, "established but was unable to create gRPC stream:", err)
conn.Close()
return err
}
err = bc.afterConnect(conn, abc)
err = bc.afterConnect(conn, abc, cf)
if err == nil {
return nil
}
Expand All @@ -155,9 +156,9 @@ func (bc *broadcastClient) connect() error {
return err
}

func (bc *broadcastClient) afterConnect(conn *grpc.ClientConn, abc orderer.AtomicBroadcast_DeliverClient) error {
func (bc *broadcastClient) afterConnect(conn *grpc.ClientConn, abc orderer.AtomicBroadcast_DeliverClient, cf context.CancelFunc) error {
bc.Lock()
bc.conn = &connection{ClientConn: conn}
bc.conn = &connection{ClientConn: conn, cancel: cf}
bc.BlocksDeliverer = abc
if bc.shouldStop() {
bc.Unlock()
Expand Down Expand Up @@ -219,13 +220,15 @@ func (bc *broadcastClient) Disconnect() {
}

type connection struct {
*grpc.ClientConn
sync.Once
*grpc.ClientConn
cancel context.CancelFunc
}

func (c *connection) Close() error {
var err error
c.Once.Do(func() {
c.cancel()
err = c.ClientConn.Close()
})
return err
Expand Down
2 changes: 0 additions & 2 deletions core/deliverservice/client_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -471,7 +471,6 @@ func testGreenPath(t *testing.T, bdc blocksDelivererConsumer) {
}

func TestCloseWhileRecv(t *testing.T) {
t.Skip()
// Scenario: Recv is being called and after a while,
// the connection is closed.
// The Recv should return immediately in such a case
Expand Down Expand Up @@ -600,7 +599,6 @@ func TestProductionUsage(t *testing.T) {
}

func TestDisconnect(t *testing.T) {
t.Skip()
// Scenario: spawn 2 ordering service instances
// and a client.
// Have the client try to Recv() from one of them,
Expand Down

0 comments on commit b5f3790

Please sign in to comment.