github.com/hechain20/hechain@v0.0.0-20220316014945-b544036ba106/core/scc/inprocstream.go (about)

     1  /*
     2  Copyright hechain. All Rights Reserved.
     3  
     4  SPDX-License-Identifier: Apache-2.0
     5  */
     6  
     7  package scc
     8  
     9  import (
    10  	"errors"
    11  	"fmt"
    12  	"sync"
    13  
    14  	pb "github.com/hyperledger/fabric-protos-go/peer"
    15  )
    16  
    17  // SendPanicFailure
    18  type SendPanicFailure string
    19  
    20  func (e SendPanicFailure) Error() string {
    21  	return fmt.Sprintf("send failure %s", string(e))
    22  }
    23  
    24  // PeerChaincodeStream interface for stream between Peer and chaincode instance.
    25  type inProcStream struct {
    26  	recv      <-chan *pb.ChaincodeMessage
    27  	send      chan<- *pb.ChaincodeMessage
    28  	closeOnce sync.Once
    29  }
    30  
    31  func newInProcStream(recv <-chan *pb.ChaincodeMessage, send chan<- *pb.ChaincodeMessage) *inProcStream {
    32  	return &inProcStream{recv: recv, send: send}
    33  }
    34  
    35  func (s *inProcStream) Send(msg *pb.ChaincodeMessage) (err error) {
    36  	// send may happen on a closed channel when the system is
    37  	// shutting down. Just catch the exception and return error
    38  	defer func() {
    39  		if r := recover(); r != nil {
    40  			err = SendPanicFailure(fmt.Sprintf("%s", r))
    41  			return
    42  		}
    43  	}()
    44  	s.send <- msg
    45  	return
    46  }
    47  
    48  func (s *inProcStream) Recv() (*pb.ChaincodeMessage, error) {
    49  	msg, ok := <-s.recv
    50  	if !ok {
    51  		return nil, errors.New("channel is closed")
    52  	}
    53  	return msg, nil
    54  }
    55  
    56  func (s *inProcStream) CloseSend() error {
    57  	s.closeOnce.Do(func() { close(s.send) })
    58  	return nil
    59  }