资讯详情

资讯详情

Fabric 1.4.4联盟链手动搭建全流程:从证书到链码调用

Fabric 1.4.4 是我带过不少入门项目后依然觉得最适合“从零讲清楚联盟链”的一个版本。它虽然是 2019 年的 LTS但模块边界非常干净身份怎么生成、排序服务怎么启动、通道怎么创建、链码怎么装上去每一层都能单独拆开看。这篇文章不吹概念直接按我实际操作过的路径走一遍先讲清楚为什么要选这个版本再准备环境然后用官方脚本快速验证最后手动把网络组建起来。想自己动手跑通一条联盟链的人按这篇文章的顺序来基本不会卡。1. 项目整体思路与版本选型1.1 先搞清楚联盟链到底在“联盟”什么很多第一次接触 Fabric 的人最容易混淆的点是它跟比特币、以太坊这类公链根本不是一回事。公链的核心是“任何人不经许可就能加入”而联盟链的核心恰好相反——每个成员都要经过审批才能进入网络节点的身份是可管理的。放到实际场景里类比联盟链就像几家合作公司共用一个带权限的档案室。每家公司在档案室里都有自己的独立柜子但有一个公共台账记录所有柜子的变更情况。约定达成之后任何公司单独去改公共台账都是不被承认的必须按照规定流程提交、背书、排序、落账。这种模型天然适合金融结算、供应链溯源、政务协同这类需要多方共享数据但又不想把数据完全公开的业务。Fabric 把这种模型拆成了几个明确的模块Peer 节点负责存储账本副本执行链码相当于智能合约在交易中承担背书和校验的角色。Orderer 节点只负责把收到的交易排成有顺序的区块不保存业务状态也不执行链码。MSP 与证书体系给每一个组织、每一个节点签发身份证书。谁有权限做什么事全部由证书决定。Channel通道一条通道就是一个隔离的账本空间。两个组织在通道 A 里交换数据通道 B 里的成员完全看不到。这种“身份 通道 排序 链码”的骨架是后续所有操作的基础。后面的手动搭建本质上就是把这四个东西一步步生成出来。1.2 为什么入门优先选 1.4.4 而不是新版本我经常被问到一个问题“现在 Fabric 都到 2.x / 3.x 了怎么还让我用 1.4.4”答案很实在1.4.4 是最典型的 LTS 版本同时它保留了 Fabric 设计上最直白的一套节点和通道概念。新版本加入了更多治理、隐私和生命周期管理的抽象逻辑更强但对新手来说反而是额外负担。1.4.4 的链码生命周期非常简单安装后直接实例化一条命令就能看到效果。这对理解账本、背书策略、通道关系远比新版本里那套需要多轮审批的流程更友好。另外从工程实际看很多存量系统至今仍然跑在 1.4.x 上企业里的生产网络、供应链平台大量是基于这套版本设计出来的。把 1.4.4 的运作原理吃透再去看 2.x 的“链码生命周期管理”“私有数据”“状态级校验”几乎是无缝衔接的。看完版本定位接下来就要动手做环境准备。这一步是最枯燥但也最决定成败的我见过太多人卡在环境不对浪费一整天。2. 环境准备与核心工具链2.1 宿主机准备Docker、内存、磁盘一个都不能少Fabric 网络本身不是一个单机程序而是一组容器化的服务节点。所以宿主机必须先具备以下条件Docker与 docker-composeFabric 官方教程基于 Docker 容器运行版本建议 Docker 18.06 以上核心是能正常拉取镜像。内存最低 4GB强烈建议 6GB 以上。同时起 Peer、Orderer、CLI 这几个容器再加上链码容器内存不足会出现莫名其妙的启动失败。磁盘空间镜像和构建缓存加起来至少准备 15GBFabric 相关镜像每个大约 300-700MB链码编译还会产生额外的镜像层。我在实际环境里遇到过内存只有 3GB 的家用机器跑一个双组织网络Peer 进程频繁被杀日志却只显示“Killed”。遇到这种问题优先加内存而不是去调配置。在你开始拉取代码之前建议先做一个最简单的检查docker info能看到正常的容器信息再继续。否则后面所有错误都会让人怀疑人生。2.2 下载二进制工具使用 bootstrap.sh 或手动拉取Fabric 官方提供了一键脚本bootstrap.sh会同时做三件事拉取 fabric-samples 代码仓库、下载对应版本的二进制工具到本地bin目录、拉取 Docker 镜像。完整命令一般是curl -sSL https://bit.ly/2ysbOFE -o bootstrap.sh chmod x bootstrap.sh ./bootstrap.sh 1.4.4如果不指定版本脚本默认拉取当前最新版本这对想要 1.4.4 的人来说是坑一定记得加版本参数。脚本执行完成后项目的bin目录里会出现几个关键文件cryptogen、configtxgen、peer、orderer。如果你下载的是官方二进制包也要把bin目录手动加入 PATH。我在实际部署中更建议从网速稳定的镜像源拉取 fabric-samples然后单独下载对应版本的二进制文件。因为 bootstrap.sh 虽然方便但对网络波动比较敏感容易在拉镜像阶段中断。拉取完成后可以用这个命令确认版本对不对configtxgen --version只要显示configtxgen的版本是1.4.4说明工具链没问题。经常有人在这里拿到 1.4.4 的镜像却配了 1.4.3 的二进制工具结果生成创世块时直接报错后面我会单独讲这个坑。2.3 三个核心工具的分工逻辑在手动搭建之前必须先理解这三个工具各自负责什么。很多人搞混了对象后面操作就全乱套工具作用我习惯的理解方式cryptogen根据组织定义文件生成全部证书和 MSP 目录相当于给参加联盟的每个公司、每台设备办“工作证”configtxgen根据通道配置模板生成创世块、通道交易文件和锚点更新文件相当于制定“公司章程”和“议会开会规则”并把规则写成文件peer负责创建通道、加入通道、安装链码、调用链码相当于“现场执行人员”所有与账本相关的手续都由它完成这三个工具都是从命令行操作的输入的都是文件路径不同的是它们所代表的权限cryptogen偏离线管理configtxgen偏配置管理而peer是在网络真正跑起来之后与运行中的节点交互。2.4 configtx.yaml 里你需要关注的核心字段configtx.yaml是一份很容易被忽略但极其重要的文件。它定义了网络中有哪些组织、每个组织的 MSP 路径、通道的排序规则、区块大小和出块策略。在第一次搭建网络时我不建议一头扎进去研究所有字段你需要重点理解这几个Organizations定义组织名称、MSP ID、MSP 目录位置。注意 MSP ID 必须与证书目录里的组织名称严格一致否则 Peer 启动时无法识别身份。Capabilities定义通道能力版本。1.4.4 的V1_4_3能力值是最常用的不同版本混合会出现兼容性问题。Orderer 配置块OrdererType默认是solo单节点排序生产环境如果用 Raft字段会多出Consensus和EtcdRaft的配置。新手阶段用 solo 把流程跑通是最省心的。Channel 配置块Profiles部分是模板入口一条 Profile 对应一个完整的通道定义组合。关于区块参数常用配置参考如下参数常见值说明BatchTimeout2s超过这个时间未达成批量也会强制出块MaxMessageCount500每个区块内最大交易数量AbsoluteMaxBytes98 MB单个区块最大体积PreferredMaxBytes512 KB据说最常被使用的目标区块尺寸这些值在你手动修改时不需要精确调优唯一要提醒的是BatchTimeout如果设得太短交易还没攒够就会频繁出块容易造成账本碎片化设得太长又会让交易确认延迟变高。2 秒属于比较折中的选择。3. 用官方脚本快速验证环境3.1 运行 first-network 示例环境准备无误后最稳妥的验证方式就是直接跑官方示例。在 fabric-samples 的first-network目录下执行cd fabric-samples/first-network ./byfn.sh generate ./byfn.sh upbyfn.sh generate的作用是调用 crypto-config.yaml 和 configtx.yaml把证书和通道配置文件生成到crypto-config和channel-artifacts目录里。byfn.sh up则会按照 docker-compose 编排文件启动两个组织共四个 Peer 节点、一个 Orderer、一个 CLI 容器并自动完成建通道、加入通道、安装链码、实例化的全部流程。如果一切正常命令最后会输出类似这样的结果 Channel successfully joined Chaincode instantiation is successful All GOOD, BYFN execution completed 3.2 验证链码调用结果脚本跑完后网络已经可用了但最好亲自调一次链码验证。进入 CLI 容器docker exec -it cli bash然后执行转账调用peer chaincode invoke -o orderer.example.com:7050 \ --tls true --cafile /opt/hyperledger/fabric/peer/orderer/tls/tlscacerts/tls-localhost-7050-ca-orderer.pem \ -C mychannel -n mycc \ -c {Args:[invoke,a,b,10]}再查询一下 a 的余额peer chaincode query -C mychannel -n mycc -c {Args:[query,a]}如果查询结果从初始的100变为了90说明整条交易链路已经打通。这里的“打通”不仅是容器起来了而是背书节点执行了链码逻辑交易被排序服务打包成了区块账本状态发生了实际变更。跑通脚本之后很多人会直接开始改配置做自己的网络但我建议再往下走一步把官方脚本做的事情手做一遍。只有手做一遍你才会真正理解第一步到第二步之间哪些是自动化的“障眼法”哪些是网络成立的真实条件。4. 手动搭建第一个网络不依赖脚本亲手组建4.1 设计一个最小但完整的网络手动搭建并不是把官方脚本删掉重写而是把它的核心步骤拆开一步一步执行。我这里设计一个最小可行的网络一个 Orderer 节点、两个 Peer 节点分别属于 Org1 和 Org2、一个 CLI 工具容器。为什么需要两个组织因为联盟链的背书策略里通常要有OR (Org1MSP.peer,Org2MSP.peer)只有一家组织参与就不叫联盟链了。生产环境里组织数往往更多但两个组织已经能完整表达“多成员”这个核心语义。这里放一个最简单的crypto-config.yaml结构OrdererOrgs: - Name: Orderer Domain: example.com Specs: - Hostname: orderer PeerOrgs: - Name: Org1 Domain: org1.example.com EnableNodeOUs: true Template: Count: 1 Users: Count: 1 - Name: Org2 Domain: org2.example.com EnableNodeOUs: true Template: Count: 1 Users: Count: 1Template.Count: 1代表每个组织生成一个 Peer 节点Users.Count: 1代表额外生成一个普通用户身份除了默认的 admin 之外。初学者经常忽略EnableNodeOUs: true这个字段是后续 Fabric 区分节点身份peer/orderer/client的基础。没有它很多权限校验会走不通。4.2 生成证书和密钥材料确认crypto-config.yaml无误后执行cryptogen generate --config./crypto-config.yaml --output./crypto-config/命令执行完crypto-config目录下会按组织生成完整的证书树crypto-config/ ├── ordererOrganizations/ │ └── example.com/ │ ├── ca/ │ ├── msp/ │ ├── orderers/ │ └── tlsca/ ├── peerOrganizations/ │ ├── org1.example.com/ │ │ ├── ca/ │ │ ├── msp/ │ │ ├── peers/ │ │ ├── tlsca/ │ │ └── users/ │ └── org2.example.com/这一步是整个网络的安全根基。生成的msp目录里存放的是该组织在通道级别使用的身份tls证书用于节点之间的安全通信。证书是后续所有权限判断的依据所以crypto-config目录一定不要提交到公开仓库也不要随意删除删了网络里所有节点就变成“没有身份证的人”。4.3 用 configtxgen 生成创世块和通道配置接下来编写configtx.yaml。这里给的是一个最小可用版本的关键结构我故意略去部分重复的组织定义你在实际操作时可以直接参考官方first-network里的同名文件来补齐细节。先定义组织和排序者配置Organizations: - OrdererOrg Name: OrdererOrg ID: OrdererMSP MSPDir: crypto-config/ordererOrganizations/example.com/msp - Org1 Name: Org1MSP ID: Org1MSP MSPDir: crypto-config/peerOrganizations/org1.example.com/msp AnchorPeers: - Host: peer0.org1.example.com Port: 7051 - Org2 Name: Org2MSP ID: Org2MSP MSPDir: crypto-config/peerOrganizations/org2.example.com/msp AnchorPeers: - Host: peer0.org2.example.com Port: 7051 Orderer: OrdererDefaults OrdererType: solo Addresses: - orderer.example.com:7050 BatchTimeout: 2s BatchSize: MaxMessageCount: 500 AbsoluteMaxBytes: 98 MB PreferredMaxBytes: 512 KB Organizations: - *OrdererOrg Profiles: TwoOrgsOrdererGenesis: Orderer: : *OrdererDefaults Organizations: - *OrdererOrg Consortiums: SampleConsortium: Organizations: - *Org1 - *Org2 TwoOrgsChannel: Consortium: SampleConsortium Application: Organizations: - *Org1 - *Org2有了这个文件依次执行三条命令mkdir channel-artifacts configtxgen -profile TwoOrgsOrdererGenesis \ -channelID byfn-sys-channel \ -outputBlock ./channel-artifacts/genesis.block configtxgen -profile TwoOrgsChannel \ -outputCreateChannelTx ./channel-artifacts/channel.tx \ -channelID mychannel configtxgen -profile TwoOrgsChannel \ -outputAnchorPeersUpdate ./channel-artifacts/Org1MSPanchors.tx \ -channelID mychannel -asOrg Org1MSP configtxgen -profile TwoOrgsChannel \ -outputAnchorPeersUpdate ./channel-artifacts/Org2MSPanchors.tx \ -channelID mychannel -asOrg Org2MSP这里的核心逻辑要理解清楚创世块是排序服务的第一个区块它包含联盟里所有组织的信息相当于“网络成立的公告”。channel.tx是创建业务通道时的初始配置交易它定义了通道里存在哪些组织但内容比创世块简单。锚点更新文件用于在通道内部广播“我这个组织的 peer 在哪里”相当于告诉通道里的其他成员“我就是这个组织的联络点”。每次执行configtxgen都可能出现大量日志输出看到Generating genesis block或者Writing new channel tx就说明成功了。如果中途报错优先检查MSPDir路径是否与cryptogen生成的实际路径一致。4.4 编写并启动 docker-compose 服务证书和配置产出后需要把它变成运行中的服务节点。这一环节要比前几步复杂因为你不仅要给每个节点配置容器还要把证书目录挂载进容器对应位置。一个最小化的docker-compose-cli.yaml需要包含四类服务orderer.example.com排序服务节点peer0.org1.example.compeer0.org2.example.com两个组织的 peercli命令行工具容器便于执行 peer 命令关键挂载配置这样写services: orderer.example.com: image: hyperledger/fabric-orderer:1.4.4 container_name: orderer.example.com environment: - ORDERER_GENERAL_LOGLEVELdebug - ORDERER_GENERAL_LISTENADDRESS0.0.0.0 - ORDERER_GENERAL_GENESISMETHODfile - ORDERER_GENERAL_GENESISFILE/var/hyperledger/orderer/orderer.genesis.block - ORDERER_GENERAL_LOCALMSPIDOrdererMSP - ORDERER_GENERAL_LOCALMSPDIR/var/hyperledger/orderer/msp - ORDERER_GENERAL_TLS_ENABLEDtrue - ORDERER_GENERAL_TLS_PRIVATEKEY/var/hyperledger/orderer/tls/server.key - ORDERER_GENERAL_TLS_CERTIFICATE/var/hyperledger/orderer/tls/server.crt - ORDERER_GENERAL_TLS_ROOTCAS[/var/hyperledger/orderer/tls/ca.crt] working_dir: /opt/gopath/src/github.com/hyperledger/fabric volumes: - ./channel-artifacts/genesis.block:/var/hyperledger/orderer/orderer.genesis.block - ./crypto-config/ordererOrganizations/example.com/orderers/orderer.example.com/msp:/var/hyperledger/orderer/msp - ./crypto-config/ordererOrganizations/example.com/orderers/orderer.example.com/tls:/var/hyperledger/orderer/tlsPeer 节点的配置逻辑类似以 Org1 为例peer0.org1.example.com: image: hyperledger/fabric-peer:1.4.4 container_name: peer0.org1.example.com environment: - CORE_VM_ENDPOINTunix:///host/var/run/docker.sock - CORE_PEER_IDpeer0.org1.example.com - CORE_PEER_ADDRESSpeer0.org1.example.com:7051 - CORE_PEER_LOCALMSPIDOrg1MSP - CORE_PEER_MSPCONFIGPATH/etc/hyperledger/fabric/msp - CORE_PEER_TLS_ENABLEDtrue - CORE_PEER_TLS_ROOTCERT_FILE/etc/hyperledger/fabric/tls/ca.crt - CORE_PEER_TLS_CERT_FILE/etc/hyperledger/fabric/tls/server.crt - CORE_PEER_TLS_KEY_FILE/etc/hyperledger/fabric/tls/server.key volumes: - /var/run/:/host/var/run/ - ./crypto-config/peerOrganizations/org1.example.com/peers/peer0.org1.example.com/msp:/etc/hyperledger/fabric/msp - ./crypto-config/peerOrganizations/org1.example.com/peers/peer0.org1.example.com/tls:/etc/hyperledger/fabric/tls启动全部服务docker-compose -f docker-compose-cli.yaml up -d执行以后用docker ps检查容器状态。正常状态下所有容器都要是Up状态。如果某个 Peer 反复重启大概率是证书路径挂载错了直接看容器日志定位docker logs peer0.org1.example.com日志里会明确告诉你 MSP 目录里的config.yaml是否存在、TLS 证书是否找到、创世块是否能解析。这是工厂里先看日志再猜问题的典型思路比盲目改配置有效得多。4.5 创建通道、加入通道容器起来后进入 CLI 容器开始执行“现场操作”docker exec -it cli bashCLI 容器内部已经预置了组织相关的环境变量但你要明确自己现在操作的是哪个组织。默认 CLI 容器绑定的是 Org1使用 Org2 操作时需要切换环境变量。首先创建通道peer channel create \ -o orderer.example.com:7050 \ -c mychannel \ -f ./channel-artifacts/channel.tx \ --tls true \ --cafile /opt/hyperledger/fabric/peer/orderer/tls/tlscacerts/tls-localhost-7050-ca-orderer.pem这条命令会向 Orderer 提交通道创建请求返回一个mychannel.block文件。这个文件就是通道的创世区块后续加入通道必须依赖它。然后 Org1 的 peer 加入通道peer channel join -b mychannel.block切换到 Org2 的上下文后重复操作通常是设置这些环境变量CORE_PEER_LOCALMSPIDOrg2MSP CORE_PEER_ADDRESSpeer0.org2.example.com:7051 CORE_PEER_MSPCONFIGPATH/opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/users/Adminorg2.example.com/msp CORE_PEER_TLS_ROOTCERT_FILE/opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/peers/peer0.org2.example.com/tls/ca.crt再看一下已加入的通道peer channel list输出里出现mychannel才算真正加入成功。这里有一个操作上的重点通道创建只需要一次但加入动作必须是每个组织的 peer 分别执行。如果某个组织不执行 join它在这个通道里就没有账本副本自然也无法参与背书。4.6 安装并实例化链码通道创建好只是有了“场地”真正产生业务逻辑的是链码。一段链码相当于办公室里的业务规则里面写了 a、b 两个账户各有多少余额转账时怎么改状态。首先把示例链码复制到 CLI 容器的 GOPATH 路径下Fabric 1.4.4 默认使用 Go 链码。先在宿主机把链码文件放到fabric-samples/chaincode/chaincode_example02/go/下然后安装peer chaincode install -n mycc -v 1.0 \ -p github.com/chaincode/chaincode_example02/go/Org1 执行完安装后还要切换到 Org2 的环境变量再安装一次。因为在实际网络中背书节点必须能拿到链码否则它无法参与链码调用。接下来在 Org1 上发起实例化peer chaincode instantiate \ -o orderer.example.com:7050 \ --tls true \ --cafile /opt/hyperledger/fabric/peer/orderer/tls/tlscacerts/tls-localhost-7050-ca-orderer.pem \ -C mychannel \ -n mycc \ -v 1.0 \ -c {Args:[init,a,100,b,200]} \ -P OR (Org1MSP.peer,Org2MSP.peer)这条命令才真正把链码启动起来并初始化了账本状态。里面的-P参数是背书策略意思是“只要有 Org1 或 Org2 任一组织的 peer 背书这笔交易就有效”。实例化会触发链码容器构建。第一次会比较慢因为要编译 Go 代码并生成对应镜像。此时可以观察docker ps如果你看到类似dev-peer0.org1.example.com-mycc-1.0的容器说明链码已经成功启动。4.7 转账调用与结果验证链码实例化成功后就可以和前面快速验证时一样执行转账peer chaincode invoke \ -o orderer.example.com:7050 \ --tls true \ --cafile /opt/hyperledger/fabric/peer/orderer/tls/tlscacerts/tls-localhost-7050-ca-orderer.pem \ -C mychannel -n mycc \ -c {Args:[invoke,a,b,10]}然后分别查询两个组织的 Peer 是否都拿到了同样的结果peer chaincode query -C mychannel -n mycc -c {Args:[query,a]}如果输出90且 Org2 的 Peer 查询结果相同说明账本已经在这个通道内的所有 Peer 上完成了状态同步。走到这一步一条“从零到链码可调用”的联盟链就已经完整搭起来了。整个过程回顾起来其实就四件事申请身份、写配置、起节点、部署链码。5. 常见问题与排查技巧实录5.1 版本不一致导致的“疑难杂症”这是排第一位的坑。fabric-samples 仓库、二进制工具、Docker 镜像三者版本必须严格对齐。我只用官方一套操作做示例但现实中很多人是自己分开下载的容易遇到configtxgen生成创世块时报无法识别V1_4_3能力或者 Peer 启动后日志里出现unknown capability。排查方法是统一检查三个地方configtxgen --version docker images | grep fabric镜像标签必须全部包含1.4.4。如果镜像版本是latest实际可能是 2.x二进制却是 1.4.4网络根本立不起来。我见过一个典型案例宿主机上同时存在 1.4.4 和 2.2 两套 fabric-samples 目录结果 CLI 容器映射的路径指向了 2.2 的 crypto-config启动后 MSP 目录结构完全不同Peer 一直报找不到组织的admincerts。排查到最后只是因为路径变量写错了。5.2 镜像拉取慢或失败网络原因导致 Docker Hub 镜像拉取中断是入门时最崩溃的问题之一。几个可行方案先尝试在本地配置可信的镜像加速器地址再docker pull hyperledger/fabric-peer:1.4.4等逐个拉取。重点拉取这些镜像fabric-peer、fabric-orderer、fabric-ccenv、fabric-tools。其中fabric-ccenv是链码容器的基础镜像很多人会漏掉它。确认镜像都拉取成功后再运行docker-compose up而不是让脚本自己边拉边启动。有一个经验值得分享直接在docker-compose里写镜像版本不要用latest这样可以避开后期缓存错乱的问题。1.4.4 的镜像名统一是hyperledger/fabric-*:1.4.4写清楚比什么都稳。5.3 链码 instantiate 一直报错链码实例化失败是所有 Fabric 新手都会遇到的高频问题。错误信息五花八门但归纳起来大多数是这几种症状原因解决思路chaincode registration failed链码容器没有启动或编译失败观察dev-peer...容器日志常见是 Go 代码路径错误chaincode already exists上一次实例化失败但中间状态未清理使用peer chaincode package打包并尝试新版本号或手动清理相关容器Error: endorsement failure背书策略要求多个组织但只有一个组织装了链码检查 Org2 是否执行了 install 命令Error: could not assemble transactionOrderer 与 Peer 之间 TLS 配置不一致核对 CA 文件路径单个阶地使用 root CA 而不是组织 CA我习惯的做法是遇到 instantiate 失败先看链码容器日志再清理干净重新来。不要反复修改同一版本号重试因为 Fabric 对重复实例化的状态处理会让问题越搞越乱。手动清理时可以用docker rm -f $(docker ps -aq --filter namedev-peer)删除所有链码容器后再重新安装、实例化通常能解决大半问题。5.4 端口占用与网络残留Fabric 默认使用不少端口Orderer 的 7050Peer 的 7051 和 7053CLI 的 7053 等。如果你之前跑过其它区块链框架或者同机的 Docker 容器占用了这些端口会直接导致节点启动失败。清理时不要简单 kill 进程而是把整套 Docker 资源重置干净docker-compose -f docker-compose-cli.yaml down -v docker rm -f $(docker ps -aq) docker network prune -f-v很关键它会删除容器挂在的卷。否则你可能费力清掉容器但旧数据卷还带着上个网络的创世块残留启动后新的 Peer 会拿到完全不一致的配置。5.5 操作顺序与配置速查最后补一张我常用的操作顺序速查表接近“抄作业”的参考。做一次完整网络部署时每一步的关键确认点都在里面序号操作关键确认点1生成证书两个组织的 MSP 目录是否都有 ca/tls/msp2生成创世块日志是否显示Successfully generated genesis block3生成 channel.tx日志是否显示Writing new channel tx4启动容器docker ps全部Up5创建通道返回mychannel.block6加入通道peer channel list显示 mychannel7安装链码两个组织都执行了 install8实例化链码出现dev-peer...容器9转账验证query 结果为 90这张表如果每一步都能对得上说明你的第一个 Fabric 网络已经从“跑通”升级到了“理解”。我自己的实际操作体会是Fabric 初期的“陡峭感”大多来自环境、版本和证书路径而不是链码本身。只要把 crypto-config.yaml 和 configtx.yaml 这两份文件吃透再把 docker-compose 的挂载目录跟磁盘实际目录对照一遍后面所有问题基本都是顺藤摸瓜的事。这个 1.4.4 的网络搭完建议你再自己改一改组织数量、换一换链码逻辑甚至试一下启用 CouchDB 作为状态数据库。把这条链路玩熟了再看新版本里的私有数据和新的链码生命周期你会发现底子已经完全够用。
觉得有用,分享给同行:

为您的企业打造数字门面

稳重轻奢商务风格,端正雅致视觉,长效耐看不易过时。

立即咨询 →