pkg/client/channel支持訪問Fabric網絡上的通道。channel客戶端實例提供與指定通道上的Peer節點進行交互的處理函數。channel客戶端能夠在指定通道上查詢鏈碼,執行鏈碼以及註冊或註銷鏈碼事件。若是應用程序須要與Fabric網絡的多條通道進行交互,須要爲每條通道建立一個單獨的通道客戶端實例。
官方文檔:
https://godoc.org/github.com/hyperledger/fabric-sdk-go/pkg/client/channelgit
channel使用流程以下:
A、準備通道客戶端上下文
B、建立通道客戶端
C、執行鏈碼
D、查詢鏈碼
channel使用示例以下:github
c, err := New(mockChannelProvider("mychannel")) if err != nil { fmt.Println("failed to create client") } response, err := c.Query(Request{ChaincodeID: "testCC", Fcn: "invoke", Args: [][]byte{[]byte("query"), []byte("data")}}) if err != nil { fmt.Printf("failed to query chaincode: %s\n", err) } fmt.Println(string(response.Payload)) // output: // abc
// Request 包含查詢和執行一個調用交易的參數 type Request struct { ChaincodeID string Fcn string Args [][]byte TransientMap map[string][]byte // InvocationChai包含元數據,某些選擇服務實現使用元數據來選擇知足調用鏈中全部鏈碼的背書 // 策略的背書節點 // Each chaincode may also be associated with a set of private data collection names // which are used by some Selection Services (e.g. Fabric Selection) to exclude endorsers // that do NOT have read access to the collections. // The invoked chaincode (specified by ChaincodeID) may optionally be added to the invocation // chain along with any collections, otherwise it may be omitted. InvocationChain []*fab.ChaincodeCall } //Response包含執行和查詢一個調用交易的響應參數 type Response struct { Proposal *fab.TransactionProposal Responses []*fab.TransactionProposalResponse TransactionID fab.TransactionID TxValidationCode pb.TxValidationCode ChaincodeStatus int32 Payload []byte }
type Client struct { context context.Channel membership fab.ChannelMembership eventService fab.EventService greylist *greylist.Filter clientTally // nolint }
通道客戶端支持訪問Fabric網絡上的通道。爲了與特定通道的Peer節點進行交互,通道客戶端實例提供了一個處理程序。 若是應用程序須要與多個通道進行交互,應該爲每一個通道建立一個單獨的通道客戶端實例。 通道客戶端只支持非管理功能。正則表達式
type ClientOption func(*Client) error func New(channelProvider context.ChannelProvider, opts ...ClientOption) (*Client, error)
返回通道Client實例。通道客戶端能夠在特定通道上查詢鏈碼,執行鏈碼以及註冊/註銷鏈碼事件。
使用示例:網絡
ctx := mockChannelProvider("mychannel") c, err := New(ctx) if err != nil { fmt.Println(err) } if c != nil { fmt.Println("channel client created") } else { fmt.Println("channel client is nil") } // output: // channel client created
func (cc *Client) Execute(request Request, options ...RequestOption) (Response, error)
使用請求和可選的請求選項進行準備並執行事務。
參數:
request包含必備鏈碼ID和函數的相關信息
options包含可選的請求選項
返回Peer的提案回覆
使用示例:ide
c, err := New(mockChannelProvider("mychannel")) if err != nil { fmt.Println("failed to create client") } _, err = c.Execute(Request{ChaincodeID: "testCC", Fcn: "invoke", Args: [][]byte{[]byte("move"), []byte("a"), []byte("b"), []byte("1")}}) if err != nil { fmt.Println(err.Error()) } fmt.Println("Chaincode transaction completed") // output: // Chaincode transaction completed
func (cc *Client) InvokeHandler(handler invoke.Handler, request Request, options ...RequestOption) (Response, error)
InvokeHandler使用提供的請求和可選請求選項來調用處理程序
參數:
handler爲要調用的處理程序
request包含必備的鏈碼ID和函數的相關信息
options包含可選的請求選項
返回Peer的提案回覆
使用示例:函數
c, err := New(mockChannelProvider("mychannel")) if err != nil { fmt.Println("failed to create client") } response, err := c.InvokeHandler(&exampleHandler{}, Request{ChaincodeID: "testCC", Fcn: "invoke", Args: [][]byte{[]byte("query"), []byte("data")}}) if err != nil { fmt.Printf("failed to query chaincode: %s\n", err) } fmt.Println(string(response.Payload)) // output: // custom
func (cc *Client) Query(request Request, options ...RequestOption) (Response, error)
使用request 和可選請求選項options查詢鏈碼。
參數:
request包含必備鏈碼ID和函數的相關信息
options包含可選的請求選項
返回值:Peer的提案回覆
使用示例:code
c, err := New(mockChannelProvider("mychannel")) if err != nil { fmt.Println("failed to create client") } response, err := c.Query(Request{ChaincodeID: "testCC", Fcn: "invoke", Args: [][]byte{[]byte("query"), []byte("b")}}) if err != nil { fmt.Printf("failed to query chaincode: %s\n", err) } if len(response.Payload) > 0 { fmt.Println("chaincode query success") } // output: // chaincode query success
func (cc *Client) RegisterChaincodeEvent(chainCodeID string, eventFilter string) (fab.Registration, <-chan *fab.CCEvent, error)
註冊鏈碼事件。當再也不須要註冊時,必須調用取消註冊。
參數:
chaincodeID接收事件的鏈碼的鏈碼ID
eventFilter用於接收事件的鏈碼事件過濾器(正則表達式)
返回註冊和用於接收事件的通道。調用註銷事件時,通道將關閉。
使用示例:對象
c, err := New(mockChannelProvider("mychannel")) if err != nil { fmt.Println("failed to create client") } registration, _, err := c.RegisterChaincodeEvent("examplecc", "event123") if err != nil { fmt.Println("failed to register chaincode event") } defer c.UnregisterChaincodeEvent(registration) fmt.Println("chaincode event registered successfully") // output: // chaincode event registered successfully
func (cc *Client) UnregisterChaincodeEvent(registration fab.Registration)
刪除給定的鏈碼事件註冊並關閉事件通道。
參數:
registration是從RegisterChaincodeEvent方法返回的註冊句柄排序
type requestOptions struct { Targets []fab.Peer // targets TargetFilter fab.TargetFilter TargetSorter fab.TargetSorter Retry retry.Opts BeforeRetry retry.BeforeRetryHandler Timeouts map[fab.TimeoutType]time.Duration //timeout options for channel client operations ParentContext reqContext.Context //parent grpc context for channel client operations (query, execute, invokehandler) CCFilter invoke.CCFilter } // RequestOption func for each Opts argument type RequestOption func(ctx context.Client, opts *requestOptions) error
func WithBeforeRetry(beforeRetry retry.BeforeRetryHandler) RequestOption
指定在重試前調用的函數func WithChaincodeFilter(ccFilter invoke.CCFilter) RequestOption
添加一個鏈碼過濾器,用於計算額外的背書節點func WithParentContext(parentContext reqContext.Context) RequestOption
WithParentContext封裝了grpc父上下文func WithRetry(retryOpt retry.Opts) RequestOption
WithRetry生成用於配置重試的選項func WithTargetEndpoints(keys ...string) RequestOption
WithTargetEndpoints容許爲請求的覆蓋目標Peer節點。目標Peer節點由名稱或URL指定,SDK將建立底層的Peer節點對象。func WithTargetFilter(filter fab.TargetFilter) RequestOption
WithTargetFilter指定每一個請求的目標Peer節點的過濾器func WithTargets(targets ...fab.Peer) RequestOption
WithTargets容許爲請求覆蓋目標Peer節點func WithTimeout(timeoutType fab.TimeoutType, timeout time.Duration) RequestOption
WithTimeout封裝了超時類型的鍵值對func WithTargetSorter(sorter fab.TargetSorter) RequestOption
指定每一個請求的排序節點接口
ctx := sdk.ChannelContext(channelName, fabsdk.WithOrg(org), fabsdk.WithUser(user)) cli, err := channel.New(ctx) if err != nil { return channel.Response{}, err } // 狀態的查詢 resp,err := cli.Query(channel.Request{ ChaincodeID: chaincodeName, Fcn: fcn, Args: args, }, channel.WithTargetEndpoints("peer0.org1.example.com"))