github.com/myafeier/fabric@v1.0.1-0.20170722181825-3a4b1f2bce86/core/chaincode/shim/handler.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 shim
    18  
    19  import (
    20  	"errors"
    21  	"fmt"
    22  	"sync"
    23  
    24  	"github.com/golang/protobuf/proto"
    25  	pb "github.com/hyperledger/fabric/protos/peer"
    26  	"github.com/looplab/fsm"
    27  )
    28  
    29  // PeerChaincodeStream interface for stream between Peer and chaincode instance.
    30  type PeerChaincodeStream interface {
    31  	Send(*pb.ChaincodeMessage) error
    32  	Recv() (*pb.ChaincodeMessage, error)
    33  	CloseSend() error
    34  }
    35  
    36  type nextStateInfo struct {
    37  	msg      *pb.ChaincodeMessage
    38  	sendToCC bool
    39  }
    40  
    41  func (handler *Handler) triggerNextState(msg *pb.ChaincodeMessage, send bool) {
    42  	handler.nextState <- &nextStateInfo{msg, send}
    43  }
    44  
    45  // Handler handler implementation for shim side of chaincode.
    46  type Handler struct {
    47  	sync.RWMutex
    48  	//shim to peer grpc serializer. User only in serialSend
    49  	serialLock sync.Mutex
    50  	To         string
    51  	ChatStream PeerChaincodeStream
    52  	FSM        *fsm.FSM
    53  	cc         Chaincode
    54  	// Multiple queries (and one transaction) with different txids can be executing in parallel for this chaincode
    55  	// responseChannel is the channel on which responses are communicated by the shim to the chaincodeStub.
    56  	responseChannel map[string]chan pb.ChaincodeMessage
    57  	nextState       chan *nextStateInfo
    58  }
    59  
    60  func shorttxid(txid string) string {
    61  	if len(txid) < 8 {
    62  		return txid
    63  	}
    64  	return txid[0:8]
    65  }
    66  
    67  //serialSend serializes msgs so gRPC will be happy
    68  func (handler *Handler) serialSend(msg *pb.ChaincodeMessage) error {
    69  	handler.serialLock.Lock()
    70  	defer handler.serialLock.Unlock()
    71  
    72  	err := handler.ChatStream.Send(msg)
    73  
    74  	return err
    75  }
    76  
    77  //serialSendAsync serves the same purpose as serialSend (serializ msgs so gRPC will
    78  //be happy). In addition, it is also asynchronous so send-remoterecv--localrecv loop
    79  //can be nonblocking. Only errors need to be handled and these are handled by
    80  //communication on supplied error channel. A typical use will be a non-blocking or
    81  //nil channel
    82  func (handler *Handler) serialSendAsync(msg *pb.ChaincodeMessage, errc chan error) {
    83  	go func() {
    84  		err := handler.serialSend(msg)
    85  		if errc != nil {
    86  			errc <- err
    87  		}
    88  	}()
    89  }
    90  
    91  func (handler *Handler) createChannel(txid string) (chan pb.ChaincodeMessage, error) {
    92  	handler.Lock()
    93  	defer handler.Unlock()
    94  	if handler.responseChannel == nil {
    95  		return nil, fmt.Errorf("[%s]Cannot create response channel", shorttxid(txid))
    96  	}
    97  	if handler.responseChannel[txid] != nil {
    98  		return nil, fmt.Errorf("[%s]Channel exists", shorttxid(txid))
    99  	}
   100  	c := make(chan pb.ChaincodeMessage)
   101  	handler.responseChannel[txid] = c
   102  	return c, nil
   103  }
   104  
   105  func (handler *Handler) sendChannel(msg *pb.ChaincodeMessage) error {
   106  	handler.Lock()
   107  	defer handler.Unlock()
   108  	if handler.responseChannel == nil {
   109  		return fmt.Errorf("[%s]Cannot send message response channel", shorttxid(msg.Txid))
   110  	}
   111  	if handler.responseChannel[msg.Txid] == nil {
   112  		return fmt.Errorf("[%s]sendChannel does not exist", shorttxid(msg.Txid))
   113  	}
   114  
   115  	chaincodeLogger.Debugf("[%s]before send", shorttxid(msg.Txid))
   116  	handler.responseChannel[msg.Txid] <- *msg
   117  	chaincodeLogger.Debugf("[%s]after send", shorttxid(msg.Txid))
   118  
   119  	return nil
   120  }
   121  
   122  //sends a message and selects
   123  func (handler *Handler) sendReceive(msg *pb.ChaincodeMessage, c chan pb.ChaincodeMessage) (pb.ChaincodeMessage, error) {
   124  	errc := make(chan error, 1)
   125  	handler.serialSendAsync(msg, errc)
   126  
   127  	//the serialsend above will send an err or nil
   128  	//the select filters that first error(or nil)
   129  	//and continues to wait for the response
   130  	//it is possible that the response triggers first
   131  	//in which case the errc obviously worked and is
   132  	//ignored
   133  	for {
   134  		select {
   135  		case err := <-errc:
   136  			if err == nil {
   137  				continue
   138  			}
   139  			//would have been logged, return false
   140  			return pb.ChaincodeMessage{}, err
   141  		case outmsg, val := <-c:
   142  			if !val {
   143  				return pb.ChaincodeMessage{}, fmt.Errorf("unexpected failure on receive")
   144  			}
   145  			return outmsg, nil
   146  		}
   147  	}
   148  }
   149  
   150  func (handler *Handler) deleteChannel(txid string) {
   151  	handler.Lock()
   152  	defer handler.Unlock()
   153  	if handler.responseChannel != nil {
   154  		delete(handler.responseChannel, txid)
   155  	}
   156  }
   157  
   158  // NewChaincodeHandler returns a new instance of the shim side handler.
   159  func newChaincodeHandler(peerChatStream PeerChaincodeStream, chaincode Chaincode) *Handler {
   160  	v := &Handler{
   161  		ChatStream: peerChatStream,
   162  		cc:         chaincode,
   163  	}
   164  	v.responseChannel = make(map[string]chan pb.ChaincodeMessage)
   165  	v.nextState = make(chan *nextStateInfo)
   166  
   167  	// Create the shim side FSM
   168  	v.FSM = fsm.NewFSM(
   169  		"created",
   170  		fsm.Events{
   171  			{Name: pb.ChaincodeMessage_REGISTERED.String(), Src: []string{"created"}, Dst: "established"},
   172  			{Name: pb.ChaincodeMessage_READY.String(), Src: []string{"established"}, Dst: "ready"},
   173  			{Name: pb.ChaincodeMessage_ERROR.String(), Src: []string{"init"}, Dst: "established"},
   174  			{Name: pb.ChaincodeMessage_RESPONSE.String(), Src: []string{"init"}, Dst: "init"},
   175  			{Name: pb.ChaincodeMessage_INIT.String(), Src: []string{"ready"}, Dst: "ready"},
   176  			{Name: pb.ChaincodeMessage_TRANSACTION.String(), Src: []string{"ready"}, Dst: "ready"},
   177  			{Name: pb.ChaincodeMessage_RESPONSE.String(), Src: []string{"ready"}, Dst: "ready"},
   178  			{Name: pb.ChaincodeMessage_ERROR.String(), Src: []string{"ready"}, Dst: "ready"},
   179  			{Name: pb.ChaincodeMessage_COMPLETED.String(), Src: []string{"init"}, Dst: "ready"},
   180  			{Name: pb.ChaincodeMessage_COMPLETED.String(), Src: []string{"ready"}, Dst: "ready"},
   181  		},
   182  		fsm.Callbacks{
   183  			"before_" + pb.ChaincodeMessage_REGISTERED.String():  func(e *fsm.Event) { v.beforeRegistered(e) },
   184  			"after_" + pb.ChaincodeMessage_RESPONSE.String():     func(e *fsm.Event) { v.afterResponse(e) },
   185  			"after_" + pb.ChaincodeMessage_ERROR.String():        func(e *fsm.Event) { v.afterError(e) },
   186  			"before_" + pb.ChaincodeMessage_INIT.String():        func(e *fsm.Event) { v.beforeInit(e) },
   187  			"before_" + pb.ChaincodeMessage_TRANSACTION.String(): func(e *fsm.Event) { v.beforeTransaction(e) },
   188  		},
   189  	)
   190  	return v
   191  }
   192  
   193  // beforeRegistered is called to handle the REGISTERED message.
   194  func (handler *Handler) beforeRegistered(e *fsm.Event) {
   195  	if _, ok := e.Args[0].(*pb.ChaincodeMessage); !ok {
   196  		e.Cancel(fmt.Errorf("Received unexpected message type"))
   197  		return
   198  	}
   199  	chaincodeLogger.Debugf("Received %s, ready for invocations", pb.ChaincodeMessage_REGISTERED)
   200  }
   201  
   202  // handleInit handles request to initialize chaincode.
   203  func (handler *Handler) handleInit(msg *pb.ChaincodeMessage) {
   204  	// The defer followed by triggering a go routine dance is needed to ensure that the previous state transition
   205  	// is completed before the next one is triggered. The previous state transition is deemed complete only when
   206  	// the beforeInit function is exited. Interesting bug fix!!
   207  	go func() {
   208  		var nextStateMsg *pb.ChaincodeMessage
   209  
   210  		send := true
   211  
   212  		defer func() {
   213  			handler.triggerNextState(nextStateMsg, send)
   214  		}()
   215  
   216  		errFunc := func(err error, payload []byte, ce *pb.ChaincodeEvent, errFmt string, args ...string) *pb.ChaincodeMessage {
   217  			if err != nil {
   218  				// Send ERROR message to chaincode support and change state
   219  				if payload == nil {
   220  					payload = []byte(err.Error())
   221  				}
   222  				chaincodeLogger.Errorf(errFmt, args)
   223  				return &pb.ChaincodeMessage{Type: pb.ChaincodeMessage_ERROR, Payload: payload, Txid: msg.Txid, ChaincodeEvent: ce}
   224  			}
   225  			return nil
   226  		}
   227  		// Get the function and args from Payload
   228  		input := &pb.ChaincodeInput{}
   229  		unmarshalErr := proto.Unmarshal(msg.Payload, input)
   230  		if nextStateMsg = errFunc(unmarshalErr, nil, nil, "[%s]Incorrect payload format. Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_ERROR.String()); nextStateMsg != nil {
   231  			return
   232  		}
   233  
   234  		// Call chaincode's Run
   235  		// Create the ChaincodeStub which the chaincode can use to callback
   236  		stub := new(ChaincodeStub)
   237  		err := stub.init(handler, msg.Txid, input, msg.Proposal)
   238  		if nextStateMsg = errFunc(err, nil, stub.chaincodeEvent, "[%s]Init get error response [%s]. Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_ERROR.String()); nextStateMsg != nil {
   239  			return
   240  		}
   241  
   242  		res := handler.cc.Init(stub)
   243  		chaincodeLogger.Debugf("[%s]Init get response status: %d", shorttxid(msg.Txid), res.Status)
   244  
   245  		if res.Status >= ERROR {
   246  			err = fmt.Errorf("%s", res.Message)
   247  			if nextStateMsg = errFunc(err, []byte(res.Message), stub.chaincodeEvent, "[%s]Init get error response [%s]. Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_ERROR.String()); nextStateMsg != nil {
   248  				return
   249  			}
   250  		}
   251  
   252  		resBytes, err := proto.Marshal(&res)
   253  		if nextStateMsg = errFunc(err, nil, stub.chaincodeEvent, "[%s]Init marshal response error [%s]. Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_ERROR.String()); nextStateMsg != nil {
   254  			return
   255  		}
   256  
   257  		// Send COMPLETED message to chaincode support and change state
   258  		nextStateMsg = &pb.ChaincodeMessage{Type: pb.ChaincodeMessage_COMPLETED, Payload: resBytes, Txid: msg.Txid, ChaincodeEvent: stub.chaincodeEvent}
   259  		chaincodeLogger.Debugf("[%s]Init succeeded. Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_COMPLETED)
   260  	}()
   261  }
   262  
   263  // beforeInit will initialize the chaincode if entering init from established.
   264  func (handler *Handler) beforeInit(e *fsm.Event) {
   265  	chaincodeLogger.Debugf("Entered state %s", handler.FSM.Current())
   266  	msg, ok := e.Args[0].(*pb.ChaincodeMessage)
   267  	if !ok {
   268  		e.Cancel(fmt.Errorf("Received unexpected message type"))
   269  		return
   270  	}
   271  	chaincodeLogger.Debugf("[%s]Received %s, initializing chaincode", shorttxid(msg.Txid), msg.Type.String())
   272  	if msg.Type.String() == pb.ChaincodeMessage_INIT.String() {
   273  		// Call the chaincode's Run function to initialize
   274  		handler.handleInit(msg)
   275  	}
   276  }
   277  
   278  // handleTransaction Handles request to execute a transaction.
   279  func (handler *Handler) handleTransaction(msg *pb.ChaincodeMessage) {
   280  	// The defer followed by triggering a go routine dance is needed to ensure that the previous state transition
   281  	// is completed before the next one is triggered. The previous state transition is deemed complete only when
   282  	// the beforeInit function is exited. Interesting bug fix!!
   283  	go func() {
   284  		//better not be nil
   285  		var nextStateMsg *pb.ChaincodeMessage
   286  
   287  		send := true
   288  
   289  		defer func() {
   290  			handler.triggerNextState(nextStateMsg, send)
   291  		}()
   292  
   293  		errFunc := func(err error, ce *pb.ChaincodeEvent, errStr string, args ...string) *pb.ChaincodeMessage {
   294  			if err != nil {
   295  				payload := []byte(err.Error())
   296  				chaincodeLogger.Errorf(errStr, args)
   297  				return &pb.ChaincodeMessage{Type: pb.ChaincodeMessage_ERROR, Payload: payload, Txid: msg.Txid, ChaincodeEvent: ce}
   298  			}
   299  			return nil
   300  		}
   301  
   302  		// Get the function and args from Payload
   303  		input := &pb.ChaincodeInput{}
   304  		unmarshalErr := proto.Unmarshal(msg.Payload, input)
   305  		if nextStateMsg = errFunc(unmarshalErr, nil, "[%s]Incorrect payload format. Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_ERROR.String()); nextStateMsg != nil {
   306  			return
   307  		}
   308  
   309  		// Call chaincode's Run
   310  		// Create the ChaincodeStub which the chaincode can use to callback
   311  		stub := new(ChaincodeStub)
   312  		err := stub.init(handler, msg.Txid, input, msg.Proposal)
   313  		if nextStateMsg = errFunc(err, stub.chaincodeEvent, "[%s]Transaction execution failed. Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_ERROR.String()); nextStateMsg != nil {
   314  			return
   315  		}
   316  
   317  		res := handler.cc.Invoke(stub)
   318  
   319  		// Endorser will handle error contained in Response.
   320  		resBytes, err := proto.Marshal(&res)
   321  		if nextStateMsg = errFunc(err, stub.chaincodeEvent, "[%s]Transaction execution failed. Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_ERROR.String()); nextStateMsg != nil {
   322  			return
   323  		}
   324  
   325  		// Send COMPLETED message to chaincode support and change state
   326  		chaincodeLogger.Debugf("[%s]Transaction completed. Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_COMPLETED)
   327  		nextStateMsg = &pb.ChaincodeMessage{Type: pb.ChaincodeMessage_COMPLETED, Payload: resBytes, Txid: msg.Txid, ChaincodeEvent: stub.chaincodeEvent}
   328  	}()
   329  }
   330  
   331  // beforeTransaction will execute chaincode's Run if coming from a TRANSACTION event.
   332  func (handler *Handler) beforeTransaction(e *fsm.Event) {
   333  	msg, ok := e.Args[0].(*pb.ChaincodeMessage)
   334  	if !ok {
   335  		e.Cancel(fmt.Errorf("Received unexpected message type"))
   336  		return
   337  	}
   338  	chaincodeLogger.Debugf("[%s]Received %s, invoking transaction on chaincode(Src:%s, Dst:%s)", shorttxid(msg.Txid), msg.Type.String(), e.Src, e.Dst)
   339  	if msg.Type.String() == pb.ChaincodeMessage_TRANSACTION.String() {
   340  		// Call the chaincode's Run function to invoke transaction
   341  		handler.handleTransaction(msg)
   342  	}
   343  }
   344  
   345  // afterResponse is called to deliver a response or error to the chaincode stub.
   346  func (handler *Handler) afterResponse(e *fsm.Event) {
   347  	msg, ok := e.Args[0].(*pb.ChaincodeMessage)
   348  	if !ok {
   349  		e.Cancel(fmt.Errorf("Received unexpected message type"))
   350  		return
   351  	}
   352  
   353  	if err := handler.sendChannel(msg); err != nil {
   354  		chaincodeLogger.Errorf("[%s]error sending %s (state:%s): %s", shorttxid(msg.Txid), msg.Type, handler.FSM.Current(), err)
   355  	} else {
   356  		chaincodeLogger.Debugf("[%s]Received %s, communicated (state:%s)", shorttxid(msg.Txid), msg.Type, handler.FSM.Current())
   357  	}
   358  }
   359  
   360  func (handler *Handler) afterError(e *fsm.Event) {
   361  	msg, ok := e.Args[0].(*pb.ChaincodeMessage)
   362  	if !ok {
   363  		e.Cancel(fmt.Errorf("Received unexpected message type"))
   364  		return
   365  	}
   366  
   367  	/* TODO- revisit. This may no longer be needed with the serialized/streamlined messaging model
   368  	 * There are two situations in which the ERROR event can be triggered:
   369  	 * 1. When an error is encountered within handleInit or handleTransaction - some issue at the chaincode side; In this case there will be no responseChannel and the message has been sent to the validator.
   370  	 * 2. The chaincode has initiated a request (get/put/del state) to the validator and is expecting a response on the responseChannel; If ERROR is received from validator, this needs to be notified on the responseChannel.
   371  	 */
   372  	if err := handler.sendChannel(msg); err == nil {
   373  		chaincodeLogger.Debugf("[%s]Error received from validator %s, communicated(state:%s)", shorttxid(msg.Txid), msg.Type, handler.FSM.Current())
   374  	}
   375  }
   376  
   377  // TODO: Implement method to get and put entire state map and not one key at a time?
   378  // handleGetState communicates with the validator to fetch the requested state information from the ledger.
   379  func (handler *Handler) handleGetState(key string, txid string) ([]byte, error) {
   380  	// Create the channel on which to communicate the response from validating peer
   381  	var respChan chan pb.ChaincodeMessage
   382  	var err error
   383  	if respChan, err = handler.createChannel(txid); err != nil {
   384  		return nil, err
   385  	}
   386  
   387  	defer handler.deleteChannel(txid)
   388  
   389  	// Send GET_STATE message to validator chaincode support
   390  	payload := []byte(key)
   391  	msg := &pb.ChaincodeMessage{Type: pb.ChaincodeMessage_GET_STATE, Payload: payload, Txid: txid}
   392  	chaincodeLogger.Debugf("[%s]Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_GET_STATE)
   393  
   394  	var responseMsg pb.ChaincodeMessage
   395  
   396  	if responseMsg, err = handler.sendReceive(msg, respChan); err != nil {
   397  		return nil, errors.New(fmt.Sprintf("[%s]error sending GET_STATE %s", shorttxid(txid), err))
   398  	}
   399  
   400  	if responseMsg.Type.String() == pb.ChaincodeMessage_RESPONSE.String() {
   401  		// Success response
   402  		chaincodeLogger.Debugf("[%s]GetState received payload %s", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_RESPONSE)
   403  		return responseMsg.Payload, nil
   404  	}
   405  	if responseMsg.Type.String() == pb.ChaincodeMessage_ERROR.String() {
   406  		// Error response
   407  		chaincodeLogger.Errorf("[%s]GetState received error %s", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_ERROR)
   408  		return nil, errors.New(string(responseMsg.Payload[:]))
   409  	}
   410  
   411  	// Incorrect chaincode message received
   412  	return nil, errors.New(fmt.Sprintf("[%s]Incorrect chaincode message %s received. Expecting %s or %s", shorttxid(responseMsg.Txid), responseMsg.Type, pb.ChaincodeMessage_RESPONSE, pb.ChaincodeMessage_ERROR))
   413  }
   414  
   415  // handlePutState communicates with the validator to put state information into the ledger.
   416  func (handler *Handler) handlePutState(key string, value []byte, txid string) error {
   417  	// Check if this is a transaction
   418  	chaincodeLogger.Debugf("[%s]Inside putstate", shorttxid(txid))
   419  
   420  	//we constructed a valid object. No need to check for error
   421  	payloadBytes, _ := proto.Marshal(&pb.PutStateInfo{Key: key, Value: value})
   422  
   423  	// Create the channel on which to communicate the response from validating peer
   424  	var respChan chan pb.ChaincodeMessage
   425  	var err error
   426  	if respChan, err = handler.createChannel(txid); err != nil {
   427  		return err
   428  	}
   429  
   430  	defer handler.deleteChannel(txid)
   431  
   432  	// Send PUT_STATE message to validator chaincode support
   433  	msg := &pb.ChaincodeMessage{Type: pb.ChaincodeMessage_PUT_STATE, Payload: payloadBytes, Txid: txid}
   434  	chaincodeLogger.Debugf("[%s]Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_PUT_STATE)
   435  
   436  	var responseMsg pb.ChaincodeMessage
   437  
   438  	if responseMsg, err = handler.sendReceive(msg, respChan); err != nil {
   439  		return errors.New(fmt.Sprintf("[%s]error sending PUT_STATE %s", msg.Txid, err))
   440  	}
   441  
   442  	if responseMsg.Type.String() == pb.ChaincodeMessage_RESPONSE.String() {
   443  		// Success response
   444  		chaincodeLogger.Debugf("[%s]Received %s. Successfully updated state", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_RESPONSE)
   445  		return nil
   446  	}
   447  
   448  	if responseMsg.Type.String() == pb.ChaincodeMessage_ERROR.String() {
   449  		// Error response
   450  		chaincodeLogger.Errorf("[%s]Received %s. Payload: %s", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_ERROR, responseMsg.Payload)
   451  		return errors.New(string(responseMsg.Payload[:]))
   452  	}
   453  
   454  	// Incorrect chaincode message received
   455  	return errors.New(fmt.Sprintf("[%s]Incorrect chaincode message %s received. Expecting %s or %s", shorttxid(responseMsg.Txid), responseMsg.Type, pb.ChaincodeMessage_RESPONSE, pb.ChaincodeMessage_ERROR))
   456  }
   457  
   458  // handleDelState communicates with the validator to delete a key from the state in the ledger.
   459  func (handler *Handler) handleDelState(key string, txid string) error {
   460  	// Create the channel on which to communicate the response from validating peer
   461  	var respChan chan pb.ChaincodeMessage
   462  	var err error
   463  	if respChan, err = handler.createChannel(txid); err != nil {
   464  		return err
   465  	}
   466  
   467  	defer handler.deleteChannel(txid)
   468  
   469  	// Send DEL_STATE message to validator chaincode support
   470  	payload := []byte(key)
   471  	msg := &pb.ChaincodeMessage{Type: pb.ChaincodeMessage_DEL_STATE, Payload: payload, Txid: txid}
   472  	chaincodeLogger.Debugf("[%s]Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_DEL_STATE)
   473  
   474  	var responseMsg pb.ChaincodeMessage
   475  
   476  	if responseMsg, err = handler.sendReceive(msg, respChan); err != nil {
   477  		return errors.New(fmt.Sprintf("[%s]error sending DEL_STATE %s", shorttxid(msg.Txid), pb.ChaincodeMessage_DEL_STATE))
   478  	}
   479  
   480  	if responseMsg.Type.String() == pb.ChaincodeMessage_RESPONSE.String() {
   481  		// Success response
   482  		chaincodeLogger.Debugf("[%s]Received %s. Successfully deleted state", msg.Txid, pb.ChaincodeMessage_RESPONSE)
   483  		return nil
   484  	}
   485  	if responseMsg.Type.String() == pb.ChaincodeMessage_ERROR.String() {
   486  		// Error response
   487  		chaincodeLogger.Errorf("[%s]Received %s. Payload: %s", msg.Txid, pb.ChaincodeMessage_ERROR, responseMsg.Payload)
   488  		return errors.New(string(responseMsg.Payload[:]))
   489  	}
   490  
   491  	// Incorrect chaincode message received
   492  	return errors.New(fmt.Sprintf("[%s]Incorrect chaincode message %s received. Expecting %s or %s", shorttxid(responseMsg.Txid), responseMsg.Type, pb.ChaincodeMessage_RESPONSE, pb.ChaincodeMessage_ERROR))
   493  }
   494  
   495  func (handler *Handler) handleGetStateByRange(startKey, endKey string, txid string) (*pb.QueryResponse, error) {
   496  	// Create the channel on which to communicate the response from validating peer
   497  	var respChan chan pb.ChaincodeMessage
   498  	var err error
   499  	if respChan, err = handler.createChannel(txid); err != nil {
   500  		return nil, err
   501  	}
   502  
   503  	defer handler.deleteChannel(txid)
   504  
   505  	// Send GET_STATE_BY_RANGE message to validator chaincode support
   506  	//we constructed a valid object. No need to check for error
   507  	payloadBytes, _ := proto.Marshal(&pb.GetStateByRange{StartKey: startKey, EndKey: endKey})
   508  
   509  	msg := &pb.ChaincodeMessage{Type: pb.ChaincodeMessage_GET_STATE_BY_RANGE, Payload: payloadBytes, Txid: txid}
   510  	chaincodeLogger.Debugf("[%s]Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_GET_STATE_BY_RANGE)
   511  
   512  	var responseMsg pb.ChaincodeMessage
   513  	if responseMsg, err = handler.sendReceive(msg, respChan); err != nil {
   514  		return nil, errors.New(fmt.Sprintf("[%s]error sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_GET_STATE_BY_RANGE))
   515  	}
   516  
   517  	if responseMsg.Type.String() == pb.ChaincodeMessage_RESPONSE.String() {
   518  		// Success response
   519  		chaincodeLogger.Debugf("[%s]Received %s. Successfully got range", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_RESPONSE)
   520  
   521  		rangeQueryResponse := &pb.QueryResponse{}
   522  		if err = proto.Unmarshal(responseMsg.Payload, rangeQueryResponse); err != nil {
   523  			return nil, errors.New(fmt.Sprintf("[%s]GetStateByRangeResponse unmarshall error", shorttxid(responseMsg.Txid)))
   524  		}
   525  
   526  		return rangeQueryResponse, nil
   527  	}
   528  	if responseMsg.Type.String() == pb.ChaincodeMessage_ERROR.String() {
   529  		// Error response
   530  		chaincodeLogger.Errorf("[%s]Received %s", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_ERROR)
   531  		return nil, errors.New(string(responseMsg.Payload[:]))
   532  	}
   533  
   534  	// Incorrect chaincode message received
   535  	return nil, errors.New(fmt.Sprintf("Incorrect chaincode message %s received. Expecting %s or %s", responseMsg.Type, pb.ChaincodeMessage_RESPONSE, pb.ChaincodeMessage_ERROR))
   536  }
   537  
   538  func (handler *Handler) handleQueryStateNext(id, txid string) (*pb.QueryResponse, error) {
   539  	// Create the channel on which to communicate the response from validating peer
   540  	var respChan chan pb.ChaincodeMessage
   541  	var err error
   542  	if respChan, err = handler.createChannel(txid); err != nil {
   543  		return nil, err
   544  	}
   545  
   546  	defer handler.deleteChannel(txid)
   547  
   548  	// Send QUERY_STATE_NEXT message to validator chaincode support
   549  	//we constructed a valid object. No need to check for error
   550  	payloadBytes, _ := proto.Marshal(&pb.QueryStateNext{Id: id})
   551  
   552  	msg := &pb.ChaincodeMessage{Type: pb.ChaincodeMessage_QUERY_STATE_NEXT, Payload: payloadBytes, Txid: txid}
   553  	chaincodeLogger.Debugf("[%s]Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_QUERY_STATE_NEXT)
   554  
   555  	var responseMsg pb.ChaincodeMessage
   556  
   557  	if responseMsg, err = handler.sendReceive(msg, respChan); err != nil {
   558  		return nil, errors.New(fmt.Sprintf("[%s]error sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_QUERY_STATE_NEXT))
   559  	}
   560  
   561  	if responseMsg.Type.String() == pb.ChaincodeMessage_RESPONSE.String() {
   562  		// Success response
   563  		chaincodeLogger.Debugf("[%s]Received %s. Successfully got range", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_RESPONSE)
   564  
   565  		queryResponse := &pb.QueryResponse{}
   566  		if err = proto.Unmarshal(responseMsg.Payload, queryResponse); err != nil {
   567  			return nil, errors.New(fmt.Sprintf("[%s]unmarshall error", shorttxid(responseMsg.Txid)))
   568  		}
   569  
   570  		return queryResponse, nil
   571  	}
   572  	if responseMsg.Type.String() == pb.ChaincodeMessage_ERROR.String() {
   573  		// Error response
   574  		chaincodeLogger.Errorf("[%s]Received %s", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_ERROR)
   575  		return nil, errors.New(string(responseMsg.Payload[:]))
   576  	}
   577  
   578  	// Incorrect chaincode message received
   579  	return nil, errors.New(fmt.Sprintf("Incorrect chaincode message %s received. Expecting %s or %s", responseMsg.Type, pb.ChaincodeMessage_RESPONSE, pb.ChaincodeMessage_ERROR))
   580  }
   581  
   582  func (handler *Handler) handleQueryStateClose(id, txid string) (*pb.QueryResponse, error) {
   583  	// Create the channel on which to communicate the response from validating peer
   584  	var respChan chan pb.ChaincodeMessage
   585  	var err error
   586  	if respChan, err = handler.createChannel(txid); err != nil {
   587  		return nil, err
   588  	}
   589  
   590  	defer handler.deleteChannel(txid)
   591  
   592  	// Send QUERY_STATE_CLOSE message to validator chaincode support
   593  	//we constructed a valid object. No need to check for error
   594  	payloadBytes, _ := proto.Marshal(&pb.QueryStateClose{Id: id})
   595  
   596  	msg := &pb.ChaincodeMessage{Type: pb.ChaincodeMessage_QUERY_STATE_CLOSE, Payload: payloadBytes, Txid: txid}
   597  	chaincodeLogger.Debugf("[%s]Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_QUERY_STATE_CLOSE)
   598  
   599  	var responseMsg pb.ChaincodeMessage
   600  
   601  	if responseMsg, err = handler.sendReceive(msg, respChan); err != nil {
   602  		return nil, errors.New(fmt.Sprintf("[%s]error sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_QUERY_STATE_CLOSE))
   603  	}
   604  
   605  	if responseMsg.Type.String() == pb.ChaincodeMessage_RESPONSE.String() {
   606  		// Success response
   607  		chaincodeLogger.Debugf("[%s]Received %s. Successfully got range", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_RESPONSE)
   608  
   609  		queryResponse := &pb.QueryResponse{}
   610  		if err = proto.Unmarshal(responseMsg.Payload, queryResponse); err != nil {
   611  			return nil, errors.New(fmt.Sprintf("[%s]unmarshall error", shorttxid(responseMsg.Txid)))
   612  		}
   613  
   614  		return queryResponse, nil
   615  	}
   616  	if responseMsg.Type.String() == pb.ChaincodeMessage_ERROR.String() {
   617  		// Error response
   618  		chaincodeLogger.Errorf("[%s]Received %s", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_ERROR)
   619  		return nil, errors.New(string(responseMsg.Payload[:]))
   620  	}
   621  
   622  	// Incorrect chaincode message received
   623  	return nil, errors.New(fmt.Sprintf("Incorrect chaincode message %s received. Expecting %s or %s", responseMsg.Type, pb.ChaincodeMessage_RESPONSE, pb.ChaincodeMessage_ERROR))
   624  }
   625  
   626  func (handler *Handler) handleGetQueryResult(query string, txid string) (*pb.QueryResponse, error) {
   627  	// Create the channel on which to communicate the response from validating peer
   628  	var respChan chan pb.ChaincodeMessage
   629  	var err error
   630  	if respChan, err = handler.createChannel(txid); err != nil {
   631  		return nil, err
   632  	}
   633  
   634  	defer handler.deleteChannel(txid)
   635  
   636  	// Send GET_QUERY_RESULT message to validator chaincode support
   637  	//we constructed a valid object. No need to check for error
   638  	payloadBytes, _ := proto.Marshal(&pb.GetQueryResult{Query: query})
   639  
   640  	msg := &pb.ChaincodeMessage{Type: pb.ChaincodeMessage_GET_QUERY_RESULT, Payload: payloadBytes, Txid: txid}
   641  	chaincodeLogger.Debugf("[%s]Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_GET_QUERY_RESULT)
   642  
   643  	var responseMsg pb.ChaincodeMessage
   644  
   645  	if responseMsg, err = handler.sendReceive(msg, respChan); err != nil {
   646  		return nil, errors.New(fmt.Sprintf("[%s]error sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_GET_QUERY_RESULT))
   647  	}
   648  
   649  	if responseMsg.Type.String() == pb.ChaincodeMessage_RESPONSE.String() {
   650  		// Success response
   651  		chaincodeLogger.Debugf("[%s]Received %s. Successfully got range", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_RESPONSE)
   652  
   653  		executeQueryResponse := &pb.QueryResponse{}
   654  		if err = proto.Unmarshal(responseMsg.Payload, executeQueryResponse); err != nil {
   655  			return nil, errors.New(fmt.Sprintf("[%s]unmarshall error", shorttxid(responseMsg.Txid)))
   656  		}
   657  
   658  		return executeQueryResponse, nil
   659  	}
   660  	if responseMsg.Type.String() == pb.ChaincodeMessage_ERROR.String() {
   661  		// Error response
   662  		chaincodeLogger.Errorf("[%s]Received %s", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_ERROR)
   663  		return nil, errors.New(string(responseMsg.Payload[:]))
   664  	}
   665  
   666  	// Incorrect chaincode message received
   667  	return nil, errors.New(fmt.Sprintf("Incorrect chaincode message %s received. Expecting %s or %s", responseMsg.Type, pb.ChaincodeMessage_RESPONSE, pb.ChaincodeMessage_ERROR))
   668  }
   669  
   670  func (handler *Handler) handleGetHistoryForKey(key string, txid string) (*pb.QueryResponse, error) {
   671  	// Create the channel on which to communicate the response from validating peer
   672  	var respChan chan pb.ChaincodeMessage
   673  	var err error
   674  	if respChan, err = handler.createChannel(txid); err != nil {
   675  		return nil, err
   676  	}
   677  
   678  	defer handler.deleteChannel(txid)
   679  
   680  	// Send GET_HISTORY_FOR_KEY message to validator chaincode support
   681  	//we constructed a valid object. No need to check for error
   682  	payloadBytes, _ := proto.Marshal(&pb.GetHistoryForKey{Key: key})
   683  
   684  	msg := &pb.ChaincodeMessage{Type: pb.ChaincodeMessage_GET_HISTORY_FOR_KEY, Payload: payloadBytes, Txid: txid}
   685  	chaincodeLogger.Debugf("[%s]Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_GET_HISTORY_FOR_KEY)
   686  
   687  	var responseMsg pb.ChaincodeMessage
   688  
   689  	if responseMsg, err = handler.sendReceive(msg, respChan); err != nil {
   690  		return nil, errors.New(fmt.Sprintf("[%s]error sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_GET_HISTORY_FOR_KEY))
   691  	}
   692  
   693  	if responseMsg.Type.String() == pb.ChaincodeMessage_RESPONSE.String() {
   694  		// Success response
   695  		chaincodeLogger.Debugf("[%s]Received %s. Successfully got range", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_RESPONSE)
   696  
   697  		getHistoryForKeyResponse := &pb.QueryResponse{}
   698  		if err = proto.Unmarshal(responseMsg.Payload, getHistoryForKeyResponse); err != nil {
   699  			return nil, errors.New(fmt.Sprintf("[%s]unmarshall error", shorttxid(responseMsg.Txid)))
   700  		}
   701  
   702  		return getHistoryForKeyResponse, nil
   703  	}
   704  	if responseMsg.Type.String() == pb.ChaincodeMessage_ERROR.String() {
   705  		// Error response
   706  		chaincodeLogger.Errorf("[%s]Received %s", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_ERROR)
   707  		return nil, errors.New(string(responseMsg.Payload[:]))
   708  	}
   709  
   710  	// Incorrect chaincode message received
   711  	return nil, errors.New(fmt.Sprintf("Incorrect chaincode message %s received. Expecting %s or %s", responseMsg.Type, pb.ChaincodeMessage_RESPONSE, pb.ChaincodeMessage_ERROR))
   712  }
   713  
   714  func (handler *Handler) createResponse(status int32, payload []byte) pb.Response {
   715  	return pb.Response{Status: status, Payload: payload}
   716  }
   717  
   718  // handleInvokeChaincode communicates with the validator to invoke another chaincode.
   719  func (handler *Handler) handleInvokeChaincode(chaincodeName string, args [][]byte, txid string) pb.Response {
   720  	//we constructed a valid object. No need to check for error
   721  	payloadBytes, _ := proto.Marshal(&pb.ChaincodeSpec{ChaincodeId: &pb.ChaincodeID{Name: chaincodeName}, Input: &pb.ChaincodeInput{Args: args}})
   722  
   723  	// Create the channel on which to communicate the response from validating peer
   724  	var respChan chan pb.ChaincodeMessage
   725  	var err error
   726  	if respChan, err = handler.createChannel(txid); err != nil {
   727  		return handler.createResponse(ERROR, []byte(err.Error()))
   728  	}
   729  
   730  	defer handler.deleteChannel(txid)
   731  
   732  	// Send INVOKE_CHAINCODE message to validator chaincode support
   733  	msg := &pb.ChaincodeMessage{Type: pb.ChaincodeMessage_INVOKE_CHAINCODE, Payload: payloadBytes, Txid: txid}
   734  	chaincodeLogger.Debugf("[%s]Sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_INVOKE_CHAINCODE)
   735  
   736  	var responseMsg pb.ChaincodeMessage
   737  
   738  	if responseMsg, err = handler.sendReceive(msg, respChan); err != nil {
   739  		return handler.createResponse(ERROR, []byte(fmt.Sprintf("[%s]error sending %s", shorttxid(msg.Txid), pb.ChaincodeMessage_INVOKE_CHAINCODE)))
   740  	}
   741  
   742  	if responseMsg.Type.String() == pb.ChaincodeMessage_RESPONSE.String() {
   743  		// Success response
   744  		chaincodeLogger.Debugf("[%s]Received %s. Successfully invoked chaincode", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_RESPONSE)
   745  		respMsg := &pb.ChaincodeMessage{}
   746  		if err = proto.Unmarshal(responseMsg.Payload, respMsg); err != nil {
   747  			return handler.createResponse(ERROR, []byte(err.Error()))
   748  		}
   749  		if respMsg.Type == pb.ChaincodeMessage_COMPLETED {
   750  			// Success response
   751  			chaincodeLogger.Debugf("[%s]Received %s. Successfully invoed chaincode", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_RESPONSE)
   752  			res := &pb.Response{}
   753  			if err = proto.Unmarshal(respMsg.Payload, res); err != nil {
   754  				return handler.createResponse(ERROR, []byte(err.Error()))
   755  			}
   756  			return *res
   757  		}
   758  		chaincodeLogger.Errorf("[%s]Received %s. Error from chaincode", shorttxid(responseMsg.Txid), respMsg.Type.String())
   759  		return handler.createResponse(ERROR, responseMsg.Payload)
   760  	}
   761  	if responseMsg.Type.String() == pb.ChaincodeMessage_ERROR.String() {
   762  		// Error response
   763  		chaincodeLogger.Errorf("[%s]Received %s.", shorttxid(responseMsg.Txid), pb.ChaincodeMessage_ERROR)
   764  		return handler.createResponse(ERROR, responseMsg.Payload)
   765  	}
   766  
   767  	// Incorrect chaincode message received
   768  	return handler.createResponse(ERROR, []byte(fmt.Sprintf("[%s]Incorrect chaincode message %s received. Expecting %s or %s", shorttxid(responseMsg.Txid), responseMsg.Type, pb.ChaincodeMessage_RESPONSE, pb.ChaincodeMessage_ERROR)))
   769  }
   770  
   771  // handleMessage message handles loop for shim side of chaincode/validator stream.
   772  func (handler *Handler) handleMessage(msg *pb.ChaincodeMessage) error {
   773  	if msg.Type == pb.ChaincodeMessage_KEEPALIVE {
   774  		// Received a keep alive message, we don't do anything with it for now
   775  		// and it does not touch the state machine
   776  		return nil
   777  	}
   778  	chaincodeLogger.Debugf("[%s]Handling ChaincodeMessage of type: %s(state:%s)", shorttxid(msg.Txid), msg.Type, handler.FSM.Current())
   779  	if handler.FSM.Cannot(msg.Type.String()) {
   780  		err := errors.New(fmt.Sprintf("[%s]Chaincode handler FSM cannot handle message (%s) with payload size (%d) while in state: %s", msg.Txid, msg.Type.String(), len(msg.Payload), handler.FSM.Current()))
   781  		handler.serialSend(&pb.ChaincodeMessage{Type: pb.ChaincodeMessage_ERROR, Payload: []byte(err.Error()), Txid: msg.Txid})
   782  		return err
   783  	}
   784  	err := handler.FSM.Event(msg.Type.String(), msg)
   785  	return filterError(err)
   786  }
   787  
   788  // filterError filters the errors to allow NoTransitionError and CanceledError to not propagate for cases where embedded Err == nil.
   789  func filterError(errFromFSMEvent error) error {
   790  	if errFromFSMEvent != nil {
   791  		if noTransitionErr, ok := errFromFSMEvent.(*fsm.NoTransitionError); ok {
   792  			if noTransitionErr.Err != nil {
   793  				// Only allow NoTransitionError's, all others are considered true error.
   794  				return errFromFSMEvent
   795  			}
   796  		}
   797  		if canceledErr, ok := errFromFSMEvent.(*fsm.CanceledError); ok {
   798  			if canceledErr.Err != nil {
   799  				// Only allow NoTransitionError's, all others are considered true error.
   800  				return canceledErr
   801  				//t.Error("expected only 'NoTransitionError'")
   802  			}
   803  			chaincodeLogger.Debugf("Ignoring CanceledError: %s", canceledErr)
   804  		}
   805  	}
   806  	return nil
   807  }