Chaincode for Operators

What is Chaincode?

链码是一个程序,用Go、Node.js或Java编写,实现指定的接口。链码运行在安全的Docker容器中,该容器与背书节点进程隔离。链码通过应用程序提交的交易初始化和管理账本状态。

链码通常处理网络成员认同的业务逻辑,因此它可以被视为“智能合约”。由链码创建的账本更新只适用于该链码,不能被其他链码直接访问。但是,在相同的网络中,给定适当的权限,一个链码可以调用另一个链码来访问它的状态。

在接下来的部分中,我们将通过区块链网络操作者而不是应用程序开发者的视角来研究链码。链码操作者可以使用本教程学习如何使用Fabric链码生命周期在其网络上部署和管理链码。

Chaincode lifecycle

Fabric 链码生命周期是一个允许多个组织在链码在通道上使用之前,就如何操作达成一致意见的程序。本教程将讨论链码操作员如何使用Fabric生命周期来执行以下任务:

注意:在v2.0 Alpha版本中,新的Fabric链码生命周期还没有完成。具体来说,要注意Alpha发行版中的以下限制:

  • Service Discovery is not yet supported

  • Chaincodes defined with the new lifecycle are not yet discoverable via service discovery

这些限制将在Alpha发行版之后得到解决。要使用旧的生命周期模型来安装和实例化链码,请访问链码的操作员教程的v1.4版本。

Install and define a chaincode

Fabric链码生命周期要求组织同意定义链码的参数,例如名称、版本和链码背书策略。通道成员通过以下四个步骤达成协议。并不是每个通道上的组织都需要完成每个步骤。

  1. Package the chaincode: This step can be completed by one organization or by each organization.

  2. Install the chaincode on your peers: Every organization that will use the chaincode to endorse a transaction or query the ledger needs to complete this step.

  3. Approve a chaincode definition for your organization: Every organization that will use the chaincode needs to complete this step. The chaincode definition needs to be approved by a sufficient number of organizations to satisfy the channel’s LifecycleEndorsment policy (a majority, by default) before the chaincode can be started on the channel.

  4. Commit the chaincode definition to the channel: The commit transaction needs to be submitted by one organization once the required number of organizations on the channel have approved. The submitter first collects endorsements from enough peers of the organizations that have approved, and then submits the transaction to commit the chaincode definition.

本教程提供了Fabric链码生命周期操作的详细概述,而不是具体的命令。要了解关于如何使用节点的CLI来使用Fabric生命周期的更多信息,请参见在构建您的第一个网络教程或节点的生命周期命令引用中安装和定义链码。要了解关于如何使用Fabric SDK for Node.js使用Fabric生命周期的更多信息,请访问如何安装和启动链码。

Step One: Packaging the smart contract

Chaincode needs to be packaged in a tar file before it can be installed on your peers. You can package a chaincode using the Fabric peer binaries, the Node Fabric SDK, or a third party tool such as GNU tar. When you create a chaincode package, you need to provide a chaincode package label to create a succinct and human readable description of the package.

如果使用第三方工具来打包链码,则生成的文件需要采用以下格式。Fabric节点二进制文件和Fabric SDKs将自动创建这种格式的文件。

  • The chaincode needs to be packaged in a tar file, ending with a .tar.gz file extension.

  • The tar file needs to contain two files (no directory): a metadata file “Chaincode-Package-Metadata.json” and another tar containing the chaincode files.

  • “Chaincode-Package-Metadata.json” contains JSON that specifies the chaincode language, code path, and package label. You can see an example of a metadata file below:

    {"Path":"github.com/chaincode/fabcar/go","Type":"golang","Label":"fabcarv1"}
    

Step Two: Install the chaincode on your peers

你需要在每一个执行和背书交易的节点上安装链码包。无论使用CLI还是SDK,都需要使用节点管理员完成此步骤,节点管理员的签名证书位于节点MSP的admincerts文件夹中。建议组织只打包一次链码,然后在属于其组织的每个节点上安装相同的包。如果一个通道想要确保每个组织运行相同的链码,那么一个组织可以打包一个链码并用带外方式将其发送到其他通道成员。

一个成功的安装命令将返回一个链码包标识符,它是一个包标签和包的散列组合。此包标识符用于将安装在节点上的链码包与组织批准的链码定义关联起来。为下一步保存标识符。您还可以通过使用节点CLI查询安装在您的节点上的包来找到包标识符。

Step Three: Approve a chaincode definition for your organization

链码由链码定义控制。当通道成员批准链码定义时,该批准作为组织对其接受的链码参数的表决。这些经过批准的组织定义允许通道成员在链码在通道上使用之前就链码达成一致。链码定义包括以下参数,这些参数需要跨组织保持一致:

  • Name: The name that applications will use when invoking the chaincode.

  • Version: A version number or value associated with a given chaincodes package. If you upgrade the chaincode binaries, you need to change your chaincode version as well.

  • Sequence: The number of times the chaincode has been defined. This value is an integer, and is used to keep track of chaincode upgrades. For example, when you first install and approve a chaincode definition, the sequence number will be 1. When you next upgrade the chaincode, the sequence number will be incremented to 2.

  • Endorsement Policy: Which organizations need to execute and validate the transaction output. The endorsement policy can be expressed as a string passed to the CLI or the SDK, or it can reference a policy in the channel config. By default, the endorsement policy is set to Channel/Application/Endorsement, which defaults to require that a majority of organizations in the channel endorse a transaction.

  • Collection Configuration: The path to a private data collection definition file associated with your chaincode. For more information about private data collections, see the Private Data architecture reference.

  • Initialization: All chaincode need to contain an Init function that is used to initialize the chaincode. By default, this function is never executed. However, you can use the chaincode definition to request that the Init function be callable. If execution of Init is requested, fabric will ensure that Init is invoked before any other function and is only invoked once.

  • ESCC/VSCC Plugins: The name of a custom endorsement or validation plugin to be used by this chaincode.

链码定义还包括包标识符。对于希望使用链码的每个组织,这都是必需的参数。包ID不需要对所有组织都是相同的。组织可以在不安装链码包或在定义中包含标识符的情况下批准链码定义。

希望使用链码的每个通道成员都需要为其组织批准一个链码定义。此批准需要提交给排序服务,然后分发给所有节点。此批准需要由组织管理员提交,其签名证书在组织定义的MSP中作为管理证书列出。成功提交批准交易后,已批准的定义存储在一个集合中,该集合可用于组织的所有节点。因此,即使您有多个节点,也只需要为您的组织批准一次链码。

Step Four: Commit the chaincode definition to the channel

一旦有足够数量的通道成员批准了链码定义,一个组织就可以将该定义提交给通道。在使用节点的CLI将定义提交到通道之前,可以使用queryapprovalstatus命令查找哪些通道成员已经批准了该定义。提交交易提议首先发送给通道成员的节点,这些成员查询为其组织批准的链码定义,如果组织已经批准了该定义,则对其进行背书。然后将交易提交给排序服务,然后该服务将链码定义提交给通道。提交定义交易需要作为组织管理员提交,其签名证书在组织定义的MSP中作为管理证书列出。

在将定义成功提交给通道之前,需要批准该定义的组织数量由通道/应用程序/生命周期背书策略控制。默认情况下,该策略要求通道中的大多数组织认可该交易。生命周期背书策略与链码背书策略是分开的。例如,即使某链码背书策略只需要一个或两个组织的签名,大多数通道成员仍然需要根据默认策略批准链码定义。在提交通道定义时,您需要在通道中发送给足够多的节点组织,以满足您的生命周期背书策略。

组织可以在不安装链码包的情况下批准链码定义。如果组织不需要使用链码,他们可以在没有包标识符的情况下批准链码定义,以确保满足生命周期背书策略。

将链码定义提交给通道后,通道成员可以开始使用链码。链码的第一次调用将在交易提议发送给的所有节点上启动链码容器,只要这些节点已经安装了链码包。您可以使用链码定义来要求调用Init函数来启动链码。否则,通道成员可以通过调用链码中的任何交易来启动链码容器。无论是初始化函数还是其他交易的第一个调用,都受链码背书策略的约束。链码容器可能需要几分钟的时间才能启动。

Upgrade a chaincode

您可以使用与安装和启动链码相同的Fabric生命周期过程来升级链码。您可以升级链码二进制文件,或者只更新链码策略。按照以下步骤升级链码:

  1. Repackage the chaincode: You only need to complete this step if you are upgrading the chaincode binaries.

  2. Install the new chaincode package on your peers: Once again, you only need to complete this step if you are upgrading the chaincode binaries. Installing the new chaincode package will generate a package ID, which you will need to pass to the new chaincode definition. You also need to change the chaincode version.

  3. Approve a new chaincode definition: If you are upgrading the chaincode binaries, you need to update the chaincode version and the package ID in the chaincode definition. You can also update your chaincode endorsement policy without having to repackage your chaincode binaries. Channel members simply need to approve a definition with the new policy. The new definition needs to increment the sequence variable in the definition by one.

  4. Commit the definition to the channel: When a sufficient number of channel members have approved the new chaincode definition, one organization can commit the new definition to upgrade the chaincode definition to the channel. There is no separate upgrade command as part of the lifecycle process.

  5. Upgrade the chaincode container: If you updated the chaincode definition without upgrading the chaincode package, you do not need to upgrade the chaincode container. If you did upgrade the chaincode binaries, a new invoke will upgrade the chaincode container. If you requested the execution of the Init function in the chaincode definition, you need to upgrade the chaincode container by invoking the Init function again after the new definition is successfully committed.

Fabric链码生命周期使用链码定义中的序列来跟踪升级。所有通道成员都需要将序列号增加1,并批准一个新的定义来升级链码。版本参数用于跟踪链码二进制文件,只有在升级链码二进制文件时才需要更改。

Migrate to the new Fabric lifecycle

您可以通过创建一个新通道并将通道功能设置为V2_0来使用Fabric链码生命周期。您将无法使用前一个生命周期在启用V2_0功能的通道上安装、实例化或更新链码。没有对v2.0 Alpha版本的升级支持,也没有从Alpha版本到未来版本v2.x的升级支持。