Hyperledger Fabric鏈碼作為外部服務


鏈碼作為外部服務

Fabric v2.0支持鏈碼在Fabric環境外部署和執行。允許用戶管理與節點保持獨立的鏈碼運行。這種方案激勵了Fabric中的鏈碼雲部署,例如Kubernetes。代替了在每一個節點上面構建與運行鏈碼。鏈碼可以作為一個服務運行,它的生命周期將可以在Fabric環境外進行管理。這種措施利用Fabirc v2.0的外部構建和運行功能。其功能具有允許操作者通過程序構建,運行,發現鏈碼對節點進行擴展。在讀取本文內容之前,應該對外部構建與擴展較為熟悉。

在外部構建功能可以使用之前,鏈碼包內容要求指定的編程語言的源代碼進行構建並作為鏈碼二進制文件運行。新的外部構建和運行功能允許用戶有選擇地定制化構建過程。將鏈碼作為外部服務運行。構建過程允許指定鏈碼運行服務的端點信息。因此包內容可以簡單地由外部鏈碼運行服務端點信息和用於安全通信的TLS歸檔組成。TLS是可選的,但是除了簡單的測試環境以外,強烈建議所有環境都使用TLS。

接下來的部分將描述如何將鏈碼配置為外部服務:

打包鏈碼

通過Fabric V2.0版本的chaincode lifecycle,鏈碼可以被打包並以.tar.gz格式進行安裝。下面的myccpackage.tgz歸檔說明了要求的結構:

tar xvfz myccpackage.tgz
code.tar.gz
metadata.json

code.tar.gz歸檔要求

code.tar.gz歸檔必須包含鏈碼端點的連接信息。該信息將在/bin/release步驟處打包進connection.json(見下面)。在這里直接將connection.json打包進code.tar.gz,所以release步驟可以直接從這里復制。

  • address - 可以被peer節點訪問的鏈碼服務端點,必須指定以:格式。
  • dial_timeout - 等待連接完成的間隔時間,字符串類型並需要指定單位,如"10s","500ms","1m",默認為"3s".
  • tls_required - 是否使用TLS加密。如果為false則不要求使用下面四個屬性
  • client_auth_required - 如果為true則需要是定客戶端權限認證的key_path,cert_path.默認為false.
  • key_path - 秘鑰文件的路徑
  • cert_path - 證書文件的路徑
  • root_cert_path - 根證書文件路徑。

例如:

{
  "address": "your.chaincode.host.com:9999",
  "dial_timeout": "10s",
  "tls_required": true,
  "client_auth_required": "true",
  "key_path": "path/rooted/in/release/directory/key.pem",
  "cert_path": "path/rooted/in/release/directory/cert.pem",
  "root_cert_path": "path/rooted/in/release/directory/rootcert.pem"
}

TLS文件可以放在code.tar.gz歸檔的任何地方,因為.tar.gz文件夾內的文件內容將會提供給外部鏈碼構建腳本。bin/release腳本,將會將文件移動到合適的位置。

metadata.json文件要求

當使用鏈碼作為外部服務時,需要在metadata.json文件中設置type字段,為了指定使用的是外部服務,例如:

{"path":"","type":"external","label":"mycc"}

配置節點對外部鏈碼進行處理

這個過程和外部構建與擴展介紹的內容是相似的。利用這些腳本來定義外部鏈碼信息。這些腳本位於peer節點的文件系統並且可以訪問並處理peer節點處的core.yaml文件中chaincode部分定義的externalBuilders元素。

創建peer節點上的外部構建器和運行器腳本

為了配置鏈碼作為外部服務,必須使用以下腳本文件:

  • detect - 檢測metadata.json文件中type是否設置為external並接受鏈碼包。
  • build - 構建鏈碼並將構建的歸檔放置在BUILD_OUTPUT_DIR位置。腳本提取connection.json文件中的鏈碼端點信息並將code.tar.gz文件中的其他歸檔文件放置在指定位置。
  • release - 拷貝被構建的歸檔(在connection.sjon文件中)到指定位置。

注意到對於鏈碼作為外部服務,沒有要求外部構建器和運行器bin/run腳本。
腳本文件要求存在peer節點的文件夾內:

    <peer的環境下完全正確的路徑>
    └── bin
        ├── build
        ├── detect
        └── release

使peer節點的core.yaml文件包括externalBuilder

最后,為了讓peer節點能夠使用外部構建器和運行器腳本,需要修改位於peer節點的core.yaml文件中的chaincode部分,使它包括externalBuilder配置元素。

externalBuilders:
     - name: myexternal
       path: <peer的環境下完全正確的路徑> #就是上面的那個路徑

外部構建和運行的腳本文件模板

為了幫助理解在鏈碼作為外部服務時,每一個腳本需要包含哪些工作,這一部分包含bin/detect,bin/build,bin/release腳本示例。
這些例子使用jq命令對json個數數據進行轉換,可以通過運行jq --version檢查是否安裝該工具。否則,需要安裝jq或者對腳本文件進行適當的修改。

/bin/detect

bin/detect腳本的職責是決定是否使用buildpack對鏈碼包進行構建和運行。對於鏈碼作為外部服務,腳本需要檢測metadata.json文件中的type是否被設置為externalpeer節點通過兩個參數調用該腳本:

bin/detect CHAINCODE_SOURCE_DIR CHAINCODE_METADATA_DIR

一個典型的detect腳本應該包含:

#!/bin/bash

set -euo pipefail

if [ "$#" -ne 2 ]; then
    >&2 echo "Expected 2 directories got $#"
    exit 2
fi

#檢測`type`是否被設置為`external`
if [ "$(jq -r .type "$2/metadata.json")" == "external" ]; then
    exit 0
fi

exit 1

metadata.json文件應該包含以下關鍵點:

{"path":"","type":"external","label":"mycc"}

/bin/build

bin/build腳本的職責是構建,編譯,以及轉換鏈碼包內容到可以被releaserun使用的歸檔中。對於鏈碼作為外部服務,該腳本拷貝connection.json文件到BUILD_OUTPUT_DIR.peer節點通過三個參數調用該腳本:

bin/build CHAINCODE_SOURCE_DIR CHAINCODE_METADATA_DIR BUILD_OUTPUT_DIR

一個典型的build腳本應該包含:

#!/bin/bash

set -euo pipefail

if [ "$#" -ne 3 ]; then
    >&2 echo "Expected 3 directories got $#"
    exit 1
fi

SOURCE=$1
OUTPUT=$3

#檢查connection.json文件是否存在
if [ ! -f "$SOURCE/connection.json" ]  ; then
    >&2 echo "$SOURCE/connection.json not found"
    exit 1
fi

#如果需要的話在這里做更多驗證

#簡單拷貝端點信息到指定的輸出位置
cp $SOURCE/connection.json $OUTPUT/connection.json

exit 0

/bin/release

bin/release腳本的職責是為peer節點提供鏈碼元數據。對於鏈碼作為外部服務,bin/release腳本作用是為peer提供放置在RELEASE_OUTPUT_DIR位置的connection.json文件。peer節點通過兩個參數調用該腳本:

bin/release BUILD_OUTPUT_DIR RELEASE_OUTPUT_DIR

一個典型的release腳本應該包含:

#!/bin/bash

set -euo pipefail

set -x

if [ "$#" -ne 2 ]; then
    >&2 echo "Expected 2 directories got $#"
    exit 2
fi

BLD="$1"
RELEASE="$2"

#外部鏈碼期望歸檔被放置在"$RELEASE"/chaincode/server路徑下
if [ -f $BLD/connection.json ]; then
   mkdir -p "$RELEASE"/chaincode/server
   cp $BLD/connection.json "$RELEASE"/chaincode/server
   exit 0
fi

exit 1

編寫鏈碼作為外部服務運行

當前,將鏈碼作為外部服務運行模板只支持GO語言鏈碼shim.在Fabric v2.0,Go shim API添加了ChaincodeServer類型。開發者可以使用它創建鏈碼服務。InvokeQueryAPI不受影響。開發者需要寫shim.ChaincodeServerAPI,然后選擇構建鏈碼並在外部環境中運行。這里有一個簡單的鏈碼程序模板用來說明這種模式:

package main

import (
        "fmt"

        "github.com/hyperledger/fabric-chaincode-go/shim"
        pb "github.com/hyperledger/fabric-protos-go/peer"
)

// SimpleChaincode 模板簡單鏈碼實現
type SimpleChaincode struct {
}

func (s *SimpleChaincode) Init(stub shim.ChaincodeStubInterface) pb.Response {
        // 初始化代碼
}

func (s *SimpleChaincode) Invoke(stub shim.ChaincodeStubInterface) pb.Response {
        // 調用代碼
}

//NOTE - ccid 和端點信息參數很難在這里編碼說明,可以通過多種標准方式指定
func main() {
       //ccid 設計用來安裝鏈碼實例 (使用“peer lifecycle chaincode install <package>” 命令) for instance
        ccid := "mycc:fcbf8724572d42e859a7dd9a7cd8e2efb84058292017df6e3d89178b64e6c831"

        server := &shim.ChaincodeServer{
                        CCID: ccid,
                        Address: "myhost:9999"
                        CC: new(SimpleChaincode),
                        TLSProps: shim.TLSProperties{
                                Disabled: true,
                        },
                }
        err := server.Start()
        if err != nil {
                fmt.Printf("Error starting Simple chaincode: %s", err)
        }
}

將鏈碼作為外部服務運行關鍵的是使用shim.ChaincodeServer.使用的新的鏈碼服務shimAPIshim.ChaincodeServer屬性描述如下:

  • CCID(string):CCID應該匹配peer節點上的鏈碼包。CCID與被安裝的鏈碼關聯,在使用peer lifecycle chaincode install <package>CLI命令返回。這可以在安裝后使用peer lifecycle chaincode queryinstalled命令獲得。
  • Address(string):鏈碼服務的監聽地址。
  • CC(Chaincode):處理初始化和調用的鏈碼
  • TLSProps(TLSProperties):鏈碼服務的TLS屬性。
  • KaOpts(keepalive.ServerParameters):保持連接選項,默認為空

部署鏈碼

當GO語言鏈碼准備好部署后,可以通過Packageing chaincode部分解釋的內容對鏈碼進行打包。並通過chaincode lifecycle部分內容對鏈碼進行部署。

將鏈碼作為外部服務運行

根據指定的編寫鏈碼作為外部服務運行部分創建鏈碼,並選擇構建可運行的鏈碼環境如Kubernetes或者直接在peer主機上運行。

使用鏈碼作為外部服務模板,將不再要求在每一個節點上安裝鏈碼。當鏈碼端點在peer節點上部署並運行后,可以繼續正常地實例化和調用鏈碼。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM