github.com/true-sqn/fabric@v2.1.1+incompatible/docs/source/build_network.rst (about) 1 Building Your First Network 2 =========================== 3 4 .. note:: The Build your first network (BYFN) tutorial has been deprecated. If 5 you are getting started with Hyperledger Fabric and would like to deploy 6 a basic network, see :doc:`test_network`. If you are deploying Fabric 7 in production, see the guide for :doc:`deployment_guide_overview`. 8 9 The build your first network (BYFN) scenario provisions a sample Hyperledger 10 Fabric network consisting of two organizations, each maintaining two peer 11 nodes. It also will deploy a Raft ordering service by default. 12 13 Install prerequisites 14 --------------------- 15 16 Before we begin, if you haven't already done so, you may wish to check that 17 you have all the :doc:`prereqs` installed on the platform(s) on which you'll be 18 developing blockchain applications and/or operating Hyperledger Fabric. 19 20 You will also need to :doc:`install`. You will notice that there are a number of 21 samples included in the ``fabric-samples`` repository. We will be using the 22 ``first-network`` sample. Let's open that sub-directory now. 23 24 .. code:: bash 25 26 cd fabric-samples/first-network 27 28 .. note:: The supplied commands in this documentation **MUST** be run from your 29 ``first-network`` sub-directory of the ``fabric-samples`` repository 30 clone. If you elect to run the commands from a different location, 31 the various provided scripts will be unable to find the binaries. 32 33 Want to run it now? 34 ------------------- 35 36 We provide a fully annotated script --- ``byfn.sh`` --- that leverages these Docker 37 images to quickly bootstrap a Hyperledger Fabric network that by default is 38 comprised of four peers representing two different organizations, and a Raft ordering 39 service. It will also launch a container to run a scripted execution that will join 40 peers to a channel, deploy a chaincode and drive execution of transactions 41 against the deployed chaincode. 42 43 Here's the help text for the ``byfn.sh`` script: 44 45 .. code:: bash 46 47 Usage: 48 byfn.sh <mode> [-c <channel name>] [-t <timeout>] [-d <delay>] [-f <docker-compose-file>] [-s <dbtype>] [-l <language>] [-o <consensus-type>] [-i <imagetag>] [-v]" 49 <mode> - one of 'up', 'down', 'restart', 'generate' or 'upgrade'" 50 - 'up' - bring up the network with docker-compose up" 51 - 'down' - clear the network with docker-compose down" 52 - 'restart' - restart the network" 53 - 'generate' - generate required certificates and genesis block" 54 - 'upgrade' - upgrade the network from version 1.3.x to 1.4.0" 55 -c <channel name> - channel name to use (defaults to \"mychannel\")" 56 -t <timeout> - CLI timeout duration in seconds (defaults to 10)" 57 -d <delay> - delay duration in seconds (defaults to 3)" 58 -f <docker-compose-file> - specify which docker-compose file use (defaults to docker-compose-cli.yaml)" 59 -s <dbtype> - the database backend to use: goleveldb (default) or couchdb" 60 -l <language> - the chaincode language: golang (default), javascript, or java" 61 -a - launch certificate authorities (no certificate authorities are launched by default) 62 -n - do not deploy chaincode (abstore chaincode is deployed by default) 63 -i <imagetag> - the tag to be used to launch the network (defaults to \"latest\")" 64 -v - verbose mode" 65 byfn.sh -h (print this message)" 66 67 Typically, one would first generate the required certificates and 68 genesis block, then bring up the network. e.g.:" 69 70 byfn.sh generate -c mychannel" 71 byfn.sh up -c mychannel -s couchdb" 72 byfn.sh up -c mychannel -s couchdb -i 1.4.0" 73 byfn.sh up -l javascript" 74 byfn.sh down -c mychannel" 75 byfn.sh upgrade -c mychannel" 76 77 Taking all defaults:" 78 byfn.sh generate" 79 byfn.sh up" 80 byfn.sh down" 81 82 If you choose not to supply a flag, the script will use default values. 83 84 Generate Network Artifacts 85 ^^^^^^^^^^^^^^^^^^^^^^^^^^ 86 87 Ready to give it a go? Okay then! Execute the following command: 88 89 .. code:: bash 90 91 ./byfn.sh generate 92 93 You will see a brief description as to what will occur, along with a yes/no command line 94 prompt. Respond with a ``y`` or hit the return key to execute the described action. 95 96 .. code:: bash 97 98 Generating certs and genesis block for channel 'mychannel' with CLI timeout of '10' seconds and CLI delay of '3' seconds 99 Continue? [Y/n] y 100 proceeding ... 101 /Users/xxx/dev/fabric-samples/bin/cryptogen 102 103 ########################################################## 104 ##### Generate certificates using cryptogen tool ######### 105 ########################################################## 106 org1.example.com 107 2017-06-12 21:01:37.334 EDT [bccsp] GetDefault -> WARN 001 Before using BCCSP, please call InitFactories(). Falling back to bootBCCSP. 108 ... 109 110 /Users/xxx/dev/fabric-samples/bin/configtxgen 111 ########################################################## 112 ######### Generating Orderer Genesis block ############## 113 ########################################################## 114 2017-06-12 21:01:37.558 EDT [common/configtx/tool] main -> INFO 001 Loading configuration 115 2017-06-12 21:01:37.562 EDT [msp] getMspConfig -> INFO 002 intermediate certs folder not found at [/Users/xxx/dev/byfn/crypto-config/ordererOrganizations/example.com/msp/intermediatecerts]. Skipping.: [stat /Users/xxx/dev/byfn/crypto-config/ordererOrganizations/example.com/msp/intermediatecerts: no such file or directory] 116 ... 117 2017-06-12 21:01:37.588 EDT [common/configtx/tool] doOutputBlock -> INFO 00b Generating genesis block 118 2017-06-12 21:01:37.590 EDT [common/configtx/tool] doOutputBlock -> INFO 00c Writing genesis block 119 120 ################################################################# 121 ### Generating channel configuration transaction 'channel.tx' ### 122 ################################################################# 123 2017-06-12 21:01:37.634 EDT [common/configtx/tool] main -> INFO 001 Loading configuration 124 2017-06-12 21:01:37.644 EDT [common/configtx/tool] doOutputChannelCreateTx -> INFO 002 Generating new channel configtx 125 2017-06-12 21:01:37.645 EDT [common/configtx/tool] doOutputChannelCreateTx -> INFO 003 Writing new channel tx 126 127 ################################################################# 128 ####### Generating anchor peer update for Org1MSP ########## 129 ################################################################# 130 2017-06-12 21:01:37.674 EDT [common/configtx/tool] main -> INFO 001 Loading configuration 131 2017-06-12 21:01:37.678 EDT [common/configtx/tool] doOutputAnchorPeersUpdate -> INFO 002 Generating anchor peer update 132 2017-06-12 21:01:37.679 EDT [common/configtx/tool] doOutputAnchorPeersUpdate -> INFO 003 Writing anchor peer update 133 134 ################################################################# 135 ####### Generating anchor peer update for Org2MSP ########## 136 ################################################################# 137 2017-06-12 21:01:37.700 EDT [common/configtx/tool] main -> INFO 001 Loading configuration 138 2017-06-12 21:01:37.704 EDT [common/configtx/tool] doOutputAnchorPeersUpdate -> INFO 002 Generating anchor peer update 139 2017-06-12 21:01:37.704 EDT [common/configtx/tool] doOutputAnchorPeersUpdate -> INFO 003 Writing anchor peer update 140 141 This first step generates all of the certificates and keys for our various 142 network entities, the ``genesis block`` used to bootstrap the ordering service, 143 and a collection of configuration transactions required to configure a 144 :ref:`Channel`. 145 146 Bring Up the Network 147 ^^^^^^^^^^^^^^^^^^^^ 148 149 Next, you can bring the network up with one of the following commands: 150 151 .. code:: bash 152 153 ./byfn.sh up 154 155 The above command will compile Go chaincode images and spin up the corresponding 156 containers. Go is the default chaincode language, however there is also support 157 for `Node.js <https://hyperledger.github.io/fabric-chaincode-node/>`_ and `Java <https://hyperledger.github.io/fabric-chaincode-java/>`_ 158 chaincode. If you'd like to run through this tutorial with node chaincode, pass 159 the following command instead: 160 161 .. code:: bash 162 163 # we use the -l flag to specify the chaincode language 164 # forgoing the -l flag will default to "golang" 165 166 ./byfn.sh up -l javascript 167 168 .. note:: For more information on the Node.js shim, please refer to its 169 `documentation <https://hyperledger.github.io/fabric-chaincode-node/master/api/fabric-shim.ChaincodeInterface.html>`_. 170 171 .. note:: For more information on the Java shim, please refer to its 172 `documentation <https://hyperledger.github.io/fabric-chaincode-java/{BRANCH}/api/org/hyperledger/fabric/shim/Chaincode.html>`_. 173 174 Тo make the sample run with Java chaincode, you have to specify ``-l java`` as follows: 175 176 .. code:: bash 177 178 ./byfn.sh up -l java 179 180 .. note:: Do not run both of these commands. Only one language can be tried unless 181 you bring down and recreate the network between. 182 183 You will be prompted as to whether you wish to continue or abort. 184 Respond with a ``y`` or hit the return key: 185 186 .. code:: bash 187 188 Starting for channel 'mychannel' with CLI timeout of '10' seconds and CLI delay of '3' seconds 189 Continue? [Y/n] 190 proceeding ... 191 Creating network "net_byfn" with the default driver 192 Creating peer0.org1.example.com 193 Creating peer1.org1.example.com 194 Creating peer0.org2.example.com 195 Creating orderer.example.com 196 Creating peer1.org2.example.com 197 Creating cli 198 199 200 ____ _____ _ ____ _____ 201 / ___| |_ _| / \ | _ \ |_ _| 202 \___ \ | | / _ \ | |_) | | | 203 ___) | | | / ___ \ | _ < | | 204 |____/ |_| /_/ \_\ |_| \_\ |_| 205 206 Channel name : mychannel 207 Creating channel... 208 209 The logs will continue from there. This will launch all of the containers, and 210 then drive a complete end-to-end application scenario. Upon successful 211 completion, it should report the following in your terminal window: 212 213 .. code:: bash 214 215 Query Result: 90 216 2017-05-16 17:08:15.158 UTC [main] main -> INFO 008 Exiting..... 217 ===================== Query successful on peer1.org2 on channel 'mychannel' ===================== 218 219 ===================== All GOOD, BYFN execution completed ===================== 220 221 222 _____ _ _ ____ 223 | ____| | \ | | | _ \ 224 | _| | \| | | | | | 225 | |___ | |\ | | |_| | 226 |_____| |_| \_| |____/ 227 228 You can scroll through these logs to see the various transactions. If you don't 229 get this result, then jump down to the :ref:`Troubleshoot` section and let's see 230 whether we can help you discover what went wrong. 231 232 Bring Down the Network 233 ^^^^^^^^^^^^^^^^^^^^^^ 234 235 Finally, let's bring it all down so we can explore the network setup one step 236 at a time. The following will kill your containers, remove the crypto material 237 and four artifacts, and delete the chaincode images from your Docker Registry: 238 239 .. code:: bash 240 241 ./byfn.sh down 242 243 Once again, you will be prompted to continue, respond with a ``y`` or hit the return key: 244 245 .. code:: bash 246 247 Stopping with channel 'mychannel' and CLI timeout of '10' 248 Continue? [Y/n] y 249 proceeding ... 250 WARNING: The CHANNEL_NAME variable is not set. Defaulting to a blank string. 251 WARNING: The TIMEOUT variable is not set. Defaulting to a blank string. 252 Removing network net_byfn 253 468aaa6201ed 254 ... 255 Untagged: dev-peer1.org2.example.com-mycc-1.0:latest 256 Deleted: sha256:ed3230614e64e1c83e510c0c282e982d2b06d148b1c498bbdcc429e2b2531e91 257 ... 258 259 If you'd like to learn more about the underlying tooling and bootstrap mechanics, 260 continue reading. In these next sections we'll walk through the various steps 261 and requirements to build a fully-functional Hyperledger Fabric network. 262 263 .. note:: The manual steps outlined below assume that the ``FABRIC_LOGGING_SPEC`` in 264 the ``cli`` container is set to ``DEBUG``. You can set this by modifying 265 the ``docker-compose-cli.yaml`` file in the ``first-network`` directory. 266 e.g. 267 268 .. code:: 269 270 cli: 271 container_name: cli 272 image: hyperledger/fabric-tools:$IMAGE_TAG 273 tty: true 274 stdin_open: true 275 environment: 276 - GOPATH=/opt/gopath 277 - CORE_VM_ENDPOINT=unix:///host/var/run/docker.sock 278 - FABRIC_LOGGING_SPEC=DEBUG 279 #- FABRIC_LOGGING_SPEC=INFO 280 281 Crypto Generator 282 ---------------- 283 284 We will use the ``cryptogen`` tool to generate the cryptographic material 285 (x509 certs and signing keys) for our various network entities. These certificates are 286 representative of identities, and they allow for sign/verify authentication to 287 take place as our entities communicate and transact. 288 289 How does it work? 290 ^^^^^^^^^^^^^^^^^ 291 292 Cryptogen consumes a file --- ``crypto-config.yaml`` --- that contains the network 293 topology and allows us to generate a set of certificates and keys for both the 294 Organizations and the components that belong to those Organizations. Each 295 Organization is provisioned a unique root certificate (``ca-cert``) that binds 296 specific components (peers and orderers) to that Org. By assigning each 297 Organization a unique CA certificate, we are mimicking a typical network where 298 a participating :ref:`Member` would use its own Certificate Authority. 299 Transactions and communications within Hyperledger Fabric are signed by an 300 entity's private key (``keystore``), and then verified by means of a public 301 key (``signcerts``). 302 303 You will notice a ``count`` variable within this file. We use this to specify 304 the number of peers per Organization; in our case there are two peers per Org. 305 We won't delve into the minutiae of `x.509 certificates and public key 306 infrastructure <https://en.wikipedia.org/wiki/Public_key_infrastructure>`_ 307 right now. If you're interested, you can peruse these topics on your own time. 308 309 After we run the ``cryptogen`` tool, the generated certificates and keys will be 310 saved to a folder titled ``crypto-config``. Note that the ``crypto-config.yaml`` 311 file lists five orderers as being tied to the orderer organization. While the 312 ``cryptogen`` tool will create certificates for all five of these orderers. These orderers 313 will be used in a etcdraft ordering service implementation and be used to create the 314 system channel and ``mychannel``. 315 316 Configuration Transaction Generator 317 ----------------------------------- 318 319 The ``configtxgen`` tool is used to create four configuration artifacts: 320 321 * orderer ``genesis block``, 322 * channel ``configuration transaction``, 323 * and two ``anchor peer transactions`` - one for each Peer Org. 324 325 Please see :doc:`commands/configtxgen` for a complete description of this tool's functionality. 326 327 The orderer block is the :ref:`Genesis-Block` for the ordering service, and the 328 channel configuration transaction file is broadcast to the orderer at :ref:`Channel` creation 329 time. The anchor peer transactions, as the name might suggest, specify each 330 Org's :ref:`Anchor-Peer` on this channel. 331 332 How does it work? 333 ^^^^^^^^^^^^^^^^^ 334 335 Configtxgen consumes a file - ``configtx.yaml`` - that contains the definitions 336 for the sample network. There are three members - one Orderer Org (``OrdererOrg``) 337 and two Peer Orgs (``Org1`` & ``Org2``) each managing and maintaining two peer nodes. 338 This file also specifies a consortium - ``SampleConsortium`` - consisting of our 339 two Peer Orgs. Pay specific attention to the "Profiles" section at the bottom of 340 this file. You will notice that we have several unique profiles. A few are worth 341 noting: 342 343 * ``SampleMultiNodeEtcdRaft``: generates the genesis block for a Raft ordering 344 service. Only used if you issue the ``-o`` flag and specify ``etcdraft``. 345 346 * ``TwoOrgsChannel``: generates the genesis block for our channel, ``mychannel``. 347 348 These headers are important, as we will pass them in as arguments when we create 349 our artifacts. 350 351 .. note:: Notice that our ``SampleConsortium`` is defined in 352 the system-level profile and then referenced by 353 our channel-level profile. Channels exist within 354 the purview of a consortium, and all consortia 355 must be defined in the scope of the network at 356 large. 357 358 This file also contains two additional specifications that are worth 359 noting. Firstly, we specify the anchor peers for each Peer Org 360 (``peer0.org1.example.com`` & ``peer0.org2.example.com``). Secondly, we point to 361 the location of the MSP directory for each member, in turn allowing us to store the 362 root certificates for each Org in the orderer genesis block. This is a critical 363 concept. Now any network entity communicating with the ordering service can have 364 its digital signature verified. 365 366 Run the tools 367 ------------- 368 369 You can manually generate the certificates/keys and the various configuration 370 artifacts using the ``configtxgen`` and ``cryptogen`` commands. Alternately, 371 you could try to adapt the byfn.sh script to accomplish your objectives. 372 373 Manually generate the artifacts 374 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 375 376 You can refer to the ``generateCerts`` function in the byfn.sh script for the 377 commands necessary to generate the certificates that will be used for your 378 network configuration as defined in the ``crypto-config.yaml`` file. However, 379 for the sake of convenience, we will also provide a reference here. 380 381 First let's run the ``cryptogen`` tool. Our binary is in the ``bin`` 382 directory, so we need to provide the relative path to where the tool resides. 383 384 .. code:: bash 385 386 ../bin/cryptogen generate --config=./crypto-config.yaml 387 388 You should see the following in your terminal: 389 390 .. code:: bash 391 392 org1.example.com 393 org2.example.com 394 395 The certs and keys (i.e. the MSP material) will be output into a directory - ``crypto-config`` - 396 at the root of the ``first-network`` directory. 397 398 Next, we need to tell the ``configtxgen`` tool where to look for the 399 ``configtx.yaml`` file that it needs to ingest. We will tell it look in our 400 present working directory: 401 402 .. code:: bash 403 404 export FABRIC_CFG_PATH=$PWD 405 406 Then, we'll invoke the ``configtxgen`` tool to create the orderer genesis block: 407 408 .. code:: bash 409 410 ../bin/configtxgen -profile SampleMultiNodeEtcdRaft -channelID byfn-sys-channel -outputBlock ./channel-artifacts/genesis.block 411 412 .. note:: The orderer genesis block and the subsequent artifacts we are about to create 413 will be output into the ``channel-artifacts`` directory at the root of the 414 ``first-network`` directory. The `channelID` in the above command is the 415 name of the system channel. 416 417 .. _createchanneltx: 418 419 Create a Channel Configuration Transaction 420 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 421 422 Next, we need to create the channel transaction artifact. Be sure to replace ``$CHANNEL_NAME`` or 423 set ``CHANNEL_NAME`` as an environment variable that can be used throughout these instructions: 424 425 .. code:: bash 426 427 # The channel.tx artifact contains the definitions for our sample channel 428 429 export CHANNEL_NAME=mychannel && ../bin/configtxgen -profile TwoOrgsChannel -outputCreateChannelTx ./channel-artifacts/channel.tx -channelID $CHANNEL_NAME 430 431 Note that the ``TwoOrgsChannel`` profile will use the ordering service 432 configuration you specified when creating the genesis block for the network. 433 434 You should see an output similar to the following in your terminal: 435 436 .. code:: bash 437 438 2017-10-26 19:24:05.324 EDT [common/tools/configtxgen] main -> INFO 001 Loading configuration 439 2017-10-26 19:24:05.329 EDT [common/tools/configtxgen] doOutputChannelCreateTx -> INFO 002 Generating new channel configtx 440 2017-10-26 19:24:05.329 EDT [common/tools/configtxgen] doOutputChannelCreateTx -> INFO 003 Writing new channel tx 441 442 Next, we will define the anchor peer for Org1 on the channel that we are 443 constructing. Again, be sure to replace ``$CHANNEL_NAME`` or set the environment 444 variable for the following commands. The terminal output will mimic that of the 445 channel transaction artifact: 446 447 .. code:: bash 448 449 ../bin/configtxgen -profile TwoOrgsChannel -outputAnchorPeersUpdate ./channel-artifacts/Org1MSPanchors.tx -channelID $CHANNEL_NAME -asOrg Org1MSP 450 451 Now, we will define the anchor peer for Org2 on the same channel: 452 453 .. code:: bash 454 455 ../bin/configtxgen -profile TwoOrgsChannel -outputAnchorPeersUpdate ./channel-artifacts/Org2MSPanchors.tx -channelID $CHANNEL_NAME -asOrg Org2MSP 456 457 Start the network 458 ----------------- 459 460 .. note:: If you ran the ``byfn.sh`` example above previously, be sure that you 461 have brought down the test network before you proceed (see 462 `Bring Down the Network`_). 463 464 We will leverage a script to spin up our network. The 465 docker-compose file references the images that we have previously downloaded, 466 and bootstraps the orderer with our previously generated ``genesis.block``. 467 468 We want to go through the commands manually in order to expose the 469 syntax and functionality of each call. 470 471 First let's start our network: 472 473 .. code:: bash 474 475 docker-compose -f docker-compose-cli.yaml -f docker-compose-etcdraft2.yaml up -d 476 477 If you want to see the realtime logs for your network, then do not supply the ``-d`` flag. 478 If you let the logs stream, then you will need to open a second terminal to execute the CLI calls. 479 480 .. _peerenvvars: 481 482 Create & Join Channel 483 ^^^^^^^^^^^^^^^^^^^^^ 484 485 Recall that we created the channel configuration transaction using the 486 ``configtxgen`` tool in the :ref:`createchanneltx` section, above. You can 487 repeat that process to create additional channel configuration transactions, 488 using the same or different profiles in the ``configtx.yaml`` that you pass 489 to the ``configtxgen`` tool. Then you can repeat the process defined in this 490 section to establish those other channels in your network. 491 492 We will enter the CLI container using the ``docker exec`` command: 493 494 .. code:: bash 495 496 docker exec -it cli bash 497 498 If successful you should see the following: 499 500 .. code:: bash 501 502 bash-5.0# 503 504 For the following CLI commands against ``peer0.org1.example.com`` to work, we need 505 to preface our commands with the four environment variables given below. These 506 variables for ``peer0.org1.example.com`` are baked into the CLI container, 507 therefore we can operate without passing them. **HOWEVER**, if you want to send 508 calls to other peers or the orderer, keep the CLI container defaults targeting 509 ``peer0.org1.example.com``, but override the environment variables as seen in the 510 example below when you make any CLI calls: 511 512 .. code:: bash 513 514 # Environment variables for PEER0 515 516 CORE_PEER_MSPCONFIGPATH=/opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org1.example.com/users/Admin@org1.example.com/msp 517 CORE_PEER_ADDRESS=peer0.org1.example.com:7051 518 CORE_PEER_LOCALMSPID="Org1MSP" 519 CORE_PEER_TLS_ROOTCERT_FILE=/opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org1.example.com/peers/peer0.org1.example.com/tls/ca.crt 520 521 Next, we are going to pass in the generated channel configuration transaction 522 artifact that we created in the :ref:`createchanneltx` section (we called 523 it ``channel.tx``) to the orderer as part of the create channel request. 524 525 We specify our channel name with the ``-c`` flag and our channel configuration 526 transaction with the ``-f`` flag. In this case it is ``channel.tx``, however 527 you can mount your own configuration transaction with a different name. Once again 528 we will set the ``CHANNEL_NAME`` environment variable within our CLI container so that 529 we don't have to explicitly pass this argument. Channel names must be all lower 530 case, less than 250 characters long and match the regular expression 531 ``[a-z][a-z0-9.-]*``. 532 533 .. code:: bash 534 535 export CHANNEL_NAME=mychannel 536 537 # the channel.tx file is mounted in the channel-artifacts directory within your CLI container 538 # as a result, we pass the full path for the file 539 # we also pass the path for the orderer ca-cert in order to verify the TLS handshake 540 # be sure to export or replace the $CHANNEL_NAME variable appropriately 541 542 peer channel create -o orderer.example.com:7050 -c $CHANNEL_NAME -f ./channel-artifacts/channel.tx --tls --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem 543 544 .. note:: Notice the ``--cafile`` that we pass as part of this command. It is 545 the local path to the orderer's root cert, allowing us to verify the 546 TLS handshake. 547 548 This command returns a genesis block - ``<CHANNEL_NAME.block>`` - which we will use to join the channel. 549 It contains the configuration information specified in ``channel.tx`` If you have not 550 made any modifications to the default channel name, then the command will return you a 551 proto titled ``mychannel.block``. 552 553 .. note:: You will remain in the CLI container for the remainder of 554 these manual commands. You must also remember to preface all commands 555 with the corresponding environment variables when targeting a peer other than 556 ``peer0.org1.example.com``. 557 558 Now let's join ``peer0.org1.example.com`` to the channel. 559 560 .. code:: bash 561 562 # By default, this joins ``peer0.org1.example.com`` only 563 # the <CHANNEL_NAME.block> was returned by the previous command 564 # if you have not modified the channel name, you will join with mychannel.block 565 # if you have created a different channel name, then pass in the appropriately named block 566 567 peer channel join -b mychannel.block 568 569 You can make other peers join the channel as necessary by making appropriate 570 changes in the four environment variables we used in the :ref:`peerenvvars` 571 section, above. 572 573 Rather than join every peer, we will simply join ``peer0.org2.example.com`` so that 574 we can properly update the anchor peer definitions in our channel. Since we are 575 overriding the default environment variables baked into the CLI container, this full 576 command will be the following: 577 578 .. code:: bash 579 580 CORE_PEER_MSPCONFIGPATH=/opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/users/Admin@org2.example.com/msp CORE_PEER_ADDRESS=peer0.org2.example.com:9051 CORE_PEER_LOCALMSPID="Org2MSP" 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 join -b mychannel.block 581 582 Alternatively, you could choose to set these environment variables individually 583 rather than passing in the entire string. Once they've been set, you simply need 584 to issue the ``peer channel join`` command again and the CLI container will act 585 on behalf of ``peer0.org2.example.com``. 586 587 Update the anchor peers 588 ^^^^^^^^^^^^^^^^^^^^^^^ 589 590 The following commands are channel updates and they will propagate to the definition 591 of the channel. In essence, we adding additional configuration information on top 592 of the channel's genesis block. Note that we are not modifying the genesis block, but 593 simply adding deltas into the chain that will define the anchor peers. 594 595 Update the channel definition to define the anchor peer for Org1 as ``peer0.org1.example.com``: 596 597 .. code:: bash 598 599 peer channel update -o orderer.example.com:7050 -c $CHANNEL_NAME -f ./channel-artifacts/Org1MSPanchors.tx --tls --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem 600 601 Now update the channel definition to define the anchor peer for Org2 as ``peer0.org2.example.com``. 602 Identically to the ``peer channel join`` command for the Org2 peer, we will need to 603 preface this call with the appropriate environment variables. 604 605 .. code:: bash 606 607 CORE_PEER_MSPCONFIGPATH=/opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/users/Admin@org2.example.com/msp CORE_PEER_ADDRESS=peer0.org2.example.com:9051 CORE_PEER_LOCALMSPID="Org2MSP" 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 update -o orderer.example.com:7050 -c $CHANNEL_NAME -f ./channel-artifacts/Org2MSPanchors.tx --tls --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem 608 609 .. _install-define-chaincode: 610 611 Install and define a chaincode 612 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 613 614 .. note:: We will utilize a simple existing chaincode. To learn how to write 615 your own chaincode, see the :doc:`chaincode4ade` tutorial. 616 617 .. note:: These instructions use the Fabric chaincode lifecycle introduced in 618 the v2.0 release. If you would like to use the previous lifecycle to 619 install and instantiate a chaincode, visit the v1.4 version of the 620 `Building your first network tutorial <https://hyperledger-fabric.readthedocs.io/en/release-1.4/build_network.html>`__. 621 622 Applications interact with the blockchain ledger through ``chaincode``. 623 Therefore we need to install a chaincode on every peer that will execute and 624 endorse our transactions. However, before we can interact with our chaincode, 625 the members of the channel need to agree on a chaincode definition that 626 establishes chaincode governance. 627 628 We need to package the chaincode before it can be installed on our peers. For 629 each package you create, you need to provide a chaincode package label as a 630 description of the chaincode. Use the following commands to package a sample 631 Go, Node.js or Java chaincode. 632 633 **Go** 634 635 .. code:: bash 636 637 # before packaging Go chaincode, vendoring Go dependencies is required like the following commands. 638 cd /opt/gopath/src/github.com/hyperledger/fabric-samples/chaincode/abstore/go 639 GO111MODULE=on go mod vendor 640 cd - 641 642 # this packages a Go chaincode. 643 # make note of the --lang flag to indicate "golang" chaincode 644 # for Go chaincode --path takes the relative path from $GOPATH/src 645 # The --label flag is used to create the package label 646 peer lifecycle chaincode package mycc.tar.gz --path github.com/hyperledger/fabric-samples/chaincode/abstore/go/ --lang golang --label mycc_1 647 648 **Node.js** 649 650 .. code:: bash 651 652 # this packages a Node.js chaincode 653 # make note of the --lang flag to indicate "node" chaincode 654 # for node chaincode --path takes the absolute path to the Node.js chaincode 655 # The --label flag is used to create the package label 656 peer lifecycle chaincode package mycc.tar.gz --path /opt/gopath/src/github.com/hyperledger/fabric-samples/chaincode/abstore/javascript/ --lang node --label mycc_1 657 658 **Java** 659 660 .. code:: bash 661 662 # this packages a java chaincode 663 # make note of the --lang flag to indicate "java" chaincode 664 # for java chaincode --path takes the absolute path to the Java chaincode 665 # The --label flag is used to create the package label 666 peer lifecycle chaincode package mycc.tar.gz --path /opt/gopath/src/github.com/hyperledger/fabric-samples/chaincode/abstore/java/ --lang java --label mycc_1 667 668 Each of the above commands will create a chaincode package named ``mycc.tar.gz``, 669 which we can use to install the chaincode on our peers. Issue the following 670 command to install the package on peer0 of Org1. 671 672 .. code:: bash 673 674 # this command installs a chaincode package on your peer 675 peer lifecycle chaincode install mycc.tar.gz 676 677 A successful install command will return a chaincode package identifier. You 678 should see output similar to the following: 679 680 .. code:: bash 681 682 2019-03-13 13:48:53.691 UTC [cli.lifecycle.chaincode] submitInstallProposal -> INFO 001 Installed remotely: response:<status:200 payload:"\nEmycc_1:3a8c52d70c36313cfebbaf09d8616e7a6318ababa01c7cbe40603c373bcfe173" > 683 2019-03-13 13:48:53.691 UTC [cli.lifecycle.chaincode] submitInstallProposal -> INFO 002 Chaincode code package identifier: mycc_1:3a8c52d70c36313cfebbaf09d8616e7a6318ababa01c7cbe40603c373bcfe173 684 685 You can also find the chaincode package identifier by querying your peer for 686 information about the packages you have installed. 687 688 .. code:: bash 689 690 # this returns the details of the chaincode packages installed on your peers 691 peer lifecycle chaincode queryinstalled 692 693 The command above will return the same package identifier as the install command. 694 You should see output similar to the following: 695 696 .. code:: bash 697 698 Get installed chaincodes on peer: 699 Package ID: mycc_1:3a8c52d70c36313cfebbaf09d8616e7a6318ababa01c7cbe40603c373bcfe173, Label: mycc_1 700 701 We are going to need the package ID for future commands, so let's go ahead and 702 save it as an environment variable. Paste the package ID returned by the 703 `peer lifecycle chaincode queryinstalled` command into the command below. The 704 package ID may not be the same for all users, so you need to complete this step 705 using the package ID returned from your console. 706 707 .. code:: bash 708 709 # Save the package ID as an environment variable. 710 711 CC_PACKAGE_ID=mycc_1:3a8c52d70c36313cfebbaf09d8616e7a6318ababa01c7cbe40603c373bcfe173 712 713 The endorsement policy of ``mycc`` will be set to require endorsements from a 714 peer in both Org1 and Org2. Therefore, we also need to install the chaincode on 715 a peer in Org2. 716 717 Modify the following four environment variables to issue the install command 718 as Org2: 719 720 .. code:: bash 721 722 # Environment variables for PEER0 in Org2 723 724 CORE_PEER_MSPCONFIGPATH=/opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/users/Admin@org2.example.com/msp 725 CORE_PEER_ADDRESS=peer0.org2.example.com:9051 726 CORE_PEER_LOCALMSPID="Org2MSP" 727 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 728 729 Now install the chaincode package onto peer0 of Org2. The following command 730 will install the chaincode and return same identifier as the install command we 731 issued as Org1. 732 733 .. code:: bash 734 735 # this installs a chaincode package on your peer 736 peer lifecycle chaincode install mycc.tar.gz 737 738 After you install the package, you need to approve a chaincode definition 739 for your organization. The chaincode definition includes the important 740 parameters of chaincode governance, including the chaincode name and version. 741 The definition also includes the package identifier used to associate the 742 chaincode package installed on your peers with a chaincode definition approved 743 by your organization. 744 745 Because we set the environment variables to operate as Org2, we can use the 746 following command to approve a definition of the ``mycc`` chaincode for 747 Org2. The approval is distributed to peers within each organization, so 748 the command does not need to target every peer within an organization. 749 750 .. code:: bash 751 752 # this approves a chaincode definition for your org 753 # make note of the --package-id flag that provides the package ID 754 # use the --init-required flag to request the ``Init`` function be invoked to initialize the chaincode 755 peer lifecycle chaincode approveformyorg --channelID $CHANNEL_NAME --name mycc --version 1.0 --init-required --package-id $CC_PACKAGE_ID --sequence 1 --tls true --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem 756 757 We could have provided a ``--signature-policy`` or ``--channel-config-policy`` 758 argument to the command above to set the chaincode endorsement policy. The 759 endorsement policy specifies how many peers belonging to different channel 760 members need to validate a transaction against a given chaincode. Because we did 761 not set a policy, the definition of ``mycc`` will use the default endorsement 762 policy, which requires that a transaction be endorsed by a majority of channel 763 members present when the transaction is submitted. This implies that if new 764 organizations are added to or removed from the channel, the endorsement policy 765 is updated automatically to require more or fewer endorsements. In this tutorial, 766 the default policy will require an endorsement from a peer belonging to Org1 767 **AND** Org2 (i.e. two endorsements). See the :doc:`endorsement-policies` 768 documentation for more details on policy implementation. 769 770 All organizations need to agree on the definition before they can use the 771 chaincode. Modify the following four environment variables to operate as Org1: 772 773 .. code:: bash 774 775 # Environment variables for PEER0 776 777 CORE_PEER_MSPCONFIGPATH=/opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org1.example.com/users/Admin@org1.example.com/msp 778 CORE_PEER_ADDRESS=peer0.org1.example.com:7051 779 CORE_PEER_LOCALMSPID="Org1MSP" 780 CORE_PEER_TLS_ROOTCERT_FILE=/opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org1.example.com/peers/peer0.org1.example.com/tls/ca.crt 781 782 You can now approve a definition for the ``mycc`` chaincode as Org1. Chaincode is 783 approved at the organization level. You can issue the command once even if you 784 have multiple peers. 785 786 .. code:: bash 787 788 # this defines a chaincode for your org 789 # make note of the --package-id flag that provides the package ID 790 # use the --init-required flag to request the Init function be invoked to initialize the chaincode 791 peer lifecycle chaincode approveformyorg --channelID $CHANNEL_NAME --name mycc --version 1.0 --init-required --package-id $CC_PACKAGE_ID --sequence 1 --tls true --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem 792 793 Once a sufficient number of channel members have approved a chaincode definition, 794 one member can commit the definition to the channel. By default a majority of 795 channel members need to approve a definition before it can be committed. It is 796 possible to check whether the chaincode definition is ready to be committed and 797 view the current approvals by organization by issuing the following query: 798 799 .. code:: bash 800 801 # the flags used for this command are identical to those used for approveformyorg 802 # except for --package-id which is not required since it is not stored as part of 803 # the definition 804 peer lifecycle chaincode checkcommitreadiness --channelID $CHANNEL_NAME --name mycc --version 1.0 --init-required --sequence 1 --tls true --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem --output json 805 806 The command will produce as output a JSON map showing if the organizations in the 807 channel have approved the chaincode definition provided in the checkcommitreadiness 808 command. In this case, given that both organizations have approved, we obtain: 809 810 .. code:: bash 811 812 { 813 "Approvals": { 814 "Org1MSP": true, 815 "Org2MSP": true 816 } 817 } 818 819 Since both channel members have approved the definition, we can now commit it to 820 the channel using the following command. You can issue this command as either 821 Org1 or Org2. Note that the transaction targets peers in Org1 and Org2 to 822 collect endorsements. 823 824 .. code:: bash 825 826 # this commits the chaincode definition to the channel 827 peer lifecycle chaincode commit -o orderer.example.com:7050 --channelID $CHANNEL_NAME --name mycc --version 1.0 --sequence 1 --init-required --tls true --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem --peerAddresses peer0.org1.example.com:7051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org1.example.com/peers/peer0.org1.example.com/tls/ca.crt --peerAddresses peer0.org2.example.com:9051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/peers/peer0.org2.example.com/tls/ca.crt 828 829 Invoking the chaincode 830 ^^^^^^^^^^^^^^^^^^^^^^ 831 832 After a chaincode definition has been committed to a channel, we are ready to 833 invoke the chaincode and start interacting with the ledger. We requested the 834 execution of the ``Init`` function in the chaincode definition using the 835 ``--init-required`` flag. As a result, we need to pass the ``--isInit`` flag to 836 its first invocation and supply the arguments to the ``Init`` function. Issue the 837 following command to initialize the chaincode and put the initial data on the 838 ledger. 839 840 .. code:: bash 841 842 # be sure to set the -C and -n flags appropriately 843 # use the --isInit flag if you are invoking an Init function 844 peer chaincode invoke -o orderer.example.com:7050 --isInit --tls true --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem -C $CHANNEL_NAME -n mycc --peerAddresses peer0.org1.example.com:7051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org1.example.com/peers/peer0.org1.example.com/tls/ca.crt --peerAddresses peer0.org2.example.com:9051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/peers/peer0.org2.example.com/tls/ca.crt -c '{"Args":["Init","a","100","b","100"]}' --waitForEvent 845 846 The first invoke will start the chaincode container. We may need to wait for the 847 container to start. Node.js images will take longer. 848 849 Query 850 ^^^^^ 851 852 Let's query the chaincode to make sure that the container was properly started 853 and the state DB was populated. The syntax for query is as follows: 854 855 .. code:: bash 856 857 # be sure to set the -C and -n flags appropriately 858 859 peer chaincode query -C $CHANNEL_NAME -n mycc -c '{"Args":["query","a"]}' 860 861 Invoke 862 ^^^^^^ 863 864 Now let’s move ``10`` from ``a`` to ``b``. This transaction will cut a new block 865 and update the state DB. The syntax for invoke is as follows: 866 867 .. code:: bash 868 869 # be sure to set the -C and -n flags appropriately 870 peer chaincode invoke -o orderer.example.com:7050 --tls true --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem -C $CHANNEL_NAME -n mycc --peerAddresses peer0.org1.example.com:7051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org1.example.com/peers/peer0.org1.example.com/tls/ca.crt --peerAddresses peer0.org2.example.com:9051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/peers/peer0.org2.example.com/tls/ca.crt -c '{"Args":["invoke","a","b","10"]}' --waitForEvent 871 872 Query 873 ^^^^^ 874 875 Let's confirm that our previous invocation executed properly. We initialized the 876 key ``a`` with a value of ``100`` and just removed ``10`` with our previous 877 invocation. Therefore, a query against ``a`` should return ``90``. The syntax 878 for query is as follows. 879 880 .. code:: bash 881 882 # be sure to set the -C and -n flags appropriately 883 884 peer chaincode query -C $CHANNEL_NAME -n mycc -c '{"Args":["query","a"]}' 885 886 We should see the following: 887 888 .. code:: bash 889 890 Query Result: 90 891 892 Install the chaincode on an additional peer 893 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 894 895 If you want additional peers to interact with the ledger, then you will need to 896 join them to the channel and install the same chaincode package on the peers. 897 You only need to approve the chaincode definition once from your organization. 898 A chaincode container will be launched for each peer as soon as they try to 899 interact with that specific chaincode. Again, be cognizant of the fact that the 900 Node.js images will be slower to build and start upon the first invoke. 901 902 We will install the chaincode on a third peer, peer1 in Org2. Modify the 903 following four environment variables to issue the install command against peer1 904 in Org2: 905 906 .. code:: bash 907 908 # Environment variables for PEER1 in Org2 909 910 CORE_PEER_MSPCONFIGPATH=/opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/users/Admin@org2.example.com/msp 911 CORE_PEER_ADDRESS=peer1.org2.example.com:10051 912 CORE_PEER_LOCALMSPID="Org2MSP" 913 CORE_PEER_TLS_ROOTCERT_FILE=/opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/peers/peer1.org2.example.com/tls/ca.crt 914 915 Now install the ``mycc`` package on peer1 of Org2: 916 917 .. code:: bash 918 919 # this command installs a chaincode package on your peer 920 peer lifecycle chaincode install mycc.tar.gz 921 922 Query 923 ^^^^^ 924 925 Let's confirm that we can issue the query to Peer1 in Org2. We initialized the 926 key ``a`` with a value of ``100`` and just removed ``10`` with our previous 927 invocation. Therefore, a query against ``a`` should still return ``90``. 928 929 Peer1 in Org2 must first join the channel before it can respond to queries. The 930 channel can be joined by issuing the following command: 931 932 .. code:: bash 933 934 CORE_PEER_MSPCONFIGPATH=/opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/users/Admin@org2.example.com/msp CORE_PEER_ADDRESS=peer1.org2.example.com:10051 CORE_PEER_LOCALMSPID="Org2MSP" CORE_PEER_TLS_ROOTCERT_FILE=/opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/peers/peer1.org2.example.com/tls/ca.crt peer channel join -b mychannel.block 935 936 After the join command returns, the query can be issued. The syntax for query is 937 as follows. 938 939 .. code:: bash 940 941 # be sure to set the -C and -n flags appropriately 942 943 peer chaincode query -C $CHANNEL_NAME -n mycc -c '{"Args":["query","a"]}' 944 945 We should see the following: 946 947 .. code:: bash 948 949 Query Result: 90 950 951 If you received an error, it may be because it takes a few seconds for the 952 peer to join and catch up to the current blockchain height. You may 953 re-query as needed. Feel free to perform additional invokes as well. 954 955 .. _behind-scenes: 956 957 What's happening behind the scenes? 958 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 959 960 .. note:: These steps describe the scenario in which 961 ``script.sh`` is run by './byfn.sh up'. Clean your network 962 with ``./byfn.sh down`` and ensure 963 this command is active. Then use the same 964 docker-compose prompt to launch your network again 965 966 - A script - ``script.sh`` - is baked inside the CLI container. The 967 script drives the ``createChannel`` command against the supplied channel name 968 and uses the channel.tx file for channel configuration. 969 970 - The output of ``createChannel`` is a genesis block - 971 ``<your_channel_name>.block`` - which gets stored on the peers' file systems and contains 972 the channel configuration specified from channel.tx. 973 974 - The ``joinChannel`` command is exercised for all four peers, which takes as 975 input the previously generated genesis block. This command instructs the 976 peers to join ``<your_channel_name>`` and create a chain starting with ``<your_channel_name>.block``. 977 978 - Now we have a channel consisting of four peers, and two 979 organizations. This is our ``TwoOrgsChannel`` profile. 980 981 - ``peer0.org1.example.com`` and ``peer1.org1.example.com`` belong to Org1; 982 ``peer0.org2.example.com`` and ``peer1.org2.example.com`` belong to Org2 983 984 - These relationships are defined through the ``crypto-config.yaml`` and 985 the MSP path is specified in our docker compose. 986 987 - The anchor peers for Org1MSP (``peer0.org1.example.com``) and 988 Org2MSP (``peer0.org2.example.com``) are then updated. We do this by passing 989 the ``Org1MSPanchors.tx`` and ``Org2MSPanchors.tx`` artifacts to the ordering 990 service along with the name of our channel. 991 992 - A chaincode - **abstore** - is packaged and installed on ``peer0.org1.example.com`` 993 and ``peer0.org2.example.com`` 994 995 - The chaincode is then separately approved by Org1 and Org2, and then committed 996 on the channel. Since an endorsement policy was not specified, the channel's 997 default endorsement policy of a majority of organizations will get utilized, 998 meaning that any transaction must be endorsed by a peer tied to Org1 and Org2. 999 1000 - The chaincode Init is then called which starts the container for the target peer, 1001 and initializes the key value pairs associated with the chaincode. The initial 1002 values for this example are ["a","100" "b","200"]. This first invoke results 1003 in a container by the name of ``dev-peer0.org2.example.com-mycc-1.0`` starting. 1004 1005 - A query against the value of "a" is issued to ``peer0.org2.example.com``. 1006 A container for Org2 peer0 by the name of ``dev-peer0.org2.example.com-mycc-1.0`` 1007 was started when the chaincode was initialized. The result of the query is 1008 returned. No write operations have occurred, so a query against "a" will 1009 still return a value of "100". 1010 1011 - An invoke is sent to ``peer0.org1.example.com`` and ``peer0.org2.example.com`` 1012 to move "10" from "a" to "b" 1013 1014 - A query is sent to ``peer0.org2.example.com`` for the value of "a". A 1015 value of 90 is returned, correctly reflecting the previous 1016 transaction during which the value for key "a" was modified by 10. 1017 1018 - The chaincode - **abstore** - is installed on ``peer1.org2.example.com`` 1019 1020 - A query is sent to ``peer1.org2.example.com`` for the value of "a". This starts a 1021 third chaincode container by the name of ``dev-peer1.org2.example.com-mycc-1.0``. A 1022 value of 90 is returned, correctly reflecting the previous 1023 transaction during which the value for key "a" was modified by 10. 1024 1025 What does this demonstrate? 1026 ^^^^^^^^^^^^^^^^^^^^^^^^^^^ 1027 1028 Chaincode **MUST** be installed on a peer in order for it to 1029 successfully perform read/write operations against the ledger. 1030 Furthermore, a chaincode container is not started for a peer until an ``init`` or 1031 traditional transaction - read/write - is performed against that chaincode (e.g. query for 1032 the value of "a"). The transaction causes the container to start. Also, 1033 all peers in a channel maintain an exact copy of the ledger which 1034 comprises the blockchain to store the immutable, sequenced record in 1035 blocks, as well as a state database to maintain a snapshot of the current state. 1036 This includes those peers that do not have chaincode installed on them 1037 (like ``peer1.org1.example.com`` in the above example) . Finally, the chaincode is accessible 1038 after it is installed (like ``peer1.org2.example.com`` in the above example) because its 1039 definition has already been committed on the channel. 1040 1041 How do I see these transactions? 1042 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 1043 1044 Check the logs for the CLI Docker container. 1045 1046 .. code:: bash 1047 1048 docker logs -f cli 1049 1050 You should see the following output: 1051 1052 .. code:: bash 1053 1054 2017-05-16 17:08:01.366 UTC [msp] GetLocalMSP -> DEBU 004 Returning existing local MSP 1055 2017-05-16 17:08:01.366 UTC [msp] GetDefaultSigningIdentity -> DEBU 005 Obtaining default signing identity 1056 2017-05-16 17:08:01.366 UTC [msp/identity] Sign -> DEBU 006 Sign: plaintext: 0AB1070A6708031A0C08F1E3ECC80510...6D7963631A0A0A0571756572790A0161 1057 2017-05-16 17:08:01.367 UTC [msp/identity] Sign -> DEBU 007 Sign: digest: E61DB37F4E8B0D32C9FE10E3936BA9B8CD278FAA1F3320B08712164248285C54 1058 Query Result: 90 1059 2017-05-16 17:08:15.158 UTC [main] main -> INFO 008 Exiting..... 1060 ===================== Query successful on peer1.org2 on channel 'mychannel' ===================== 1061 1062 ===================== All GOOD, BYFN execution completed ===================== 1063 1064 1065 _____ _ _ ____ 1066 | ____| | \ | | | _ \ 1067 | _| | \| | | | | | 1068 | |___ | |\ | | |_| | 1069 |_____| |_| \_| |____/ 1070 1071 You can scroll through these logs to see the various transactions. 1072 1073 How can I see the chaincode logs? 1074 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 1075 1076 You can inspect the individual chaincode containers to see the separate 1077 transactions executed against each container. Use the following command to find 1078 the list of running containers to find your chaincode containers: 1079 1080 .. code:: bash 1081 1082 $ docker ps -a 1083 CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 1084 7aa7d9e199f5 dev-peer1.org2.example.com-mycc_1-27ef99cb3cbd1b545063f018f3670eddc0d54f40b2660b8f853ad2854c49a0d8-2eba360c66609a3ba78327c2c86bc3abf041c78f5a35553191a1acf1efdd5a0d "chaincode -peer.add…" About a minute ago Up About a minute dev-peer1.org2.example.com-mycc_1-27ef99cb3cbd1b545063f018f3670eddc0d54f40b2660b8f853ad2854c49a0d8 1085 82ce129c0fe6 dev-peer0.org2.example.com-mycc_1-27ef99cb3cbd1b545063f018f3670eddc0d54f40b2660b8f853ad2854c49a0d8-1297906045aa77086daba21aba47e8eef359f9498b7cb2b010dff3e2a354565a "chaincode -peer.add…" About a minute ago Up About a minute dev-peer0.org2.example.com-mycc_1-27ef99cb3cbd1b545063f018f3670eddc0d54f40b2660b8f853ad2854c49a0d8 1086 eaef1a8f7acf dev-peer0.org1.example.com-mycc_1-27ef99cb3cbd1b545063f018f3670eddc0d54f40b2660b8f853ad2854c49a0d8-00d8dbefd85a4aeb9428b7df95df9744be1325b2a60900ac7a81796e67e4280a "chaincode -peer.add…" 2 minutes ago Up 2 minutes dev-peer0.org1.example.com-mycc_1-27ef99cb3cbd1b545063f018f3670eddc0d54f40b2660b8f853ad2854c49a0d8 1087 da403175b785 hyperledger/fabric-tools:latest "/bin/bash" 4 minutes ago Up 4 minutes cli 1088 c62a8d03818f hyperledger/fabric-peer:latest "peer node start" 4 minutes ago Up 4 minutes 7051/tcp, 0.0.0.0:9051->9051/tcp peer0.org2.example.com 1089 06593c4f3e53 hyperledger/fabric-peer:latest "peer node start" 4 minutes ago Up 4 minutes 0.0.0.0:7051->7051/tcp peer0.org1.example.com 1090 4ddc928ebffe hyperledger/fabric-orderer:latest "orderer" 4 minutes ago Up 4 minutes 0.0.0.0:7050->7050/tcp orderer.example.com 1091 6d79e95ec059 hyperledger/fabric-peer:latest "peer node start" 4 minutes ago Up 4 minutes 7051/tcp, 0.0.0.0:10051->10051/tcp peer1.org2.example.com 1092 6aad6b40fd30 hyperledger/fabric-peer:latest "peer node start" 4 minutes ago Up 4 minutes 7051/tcp, 0.0.0.0:8051->8051/tcp peer1.org1.example.com 1093 1094 The chaincode containers are the images starting with `dev-peer`. You can then 1095 use the container ID to find the logs from each chaincode container. 1096 1097 .. code:: bash 1098 1099 $ docker logs 7aa7d9e199f5 1100 ABstore Init 1101 Aval = 100, Bval = 100 1102 ABstore Invoke 1103 Aval = 90, Bval = 110 1104 1105 $ docker logs eaef1a8f7acf 1106 ABstore Init 1107 Aval = 100, Bval = 100 1108 ABstore Invoke 1109 Query Response:{"Name":"a","Amount":"100"} 1110 ABstore Invoke 1111 Aval = 90, Bval = 110 1112 ABstore Invoke 1113 Query Response:{"Name":"a","Amount":"90"} 1114 1115 You can also see the peer logs to view chaincode invoke messages 1116 and block commit messages: 1117 1118 .. code:: bash 1119 1120 $ docker logs peer0.org1.example.com 1121 1122 Understanding the Docker Compose topology 1123 ----------------------------------------- 1124 1125 The BYFN sample offers us two flavors of Docker Compose files, both of which 1126 are extended from the ``docker-compose-base.yaml`` (located in the ``base`` 1127 folder). Our first flavor, ``docker-compose-cli.yaml``, provides us with a 1128 CLI container, along with an orderer, four peers. We use this file 1129 for the entirety of the instructions on this page. 1130 1131 .. note:: the remainder of this section covers a docker-compose file designed for the 1132 SDK. Refer to the `Node SDK <https://github.com/hyperledger/fabric-sdk-node>`__ 1133 repo for details on running these tests. 1134 1135 The second flavor, ``docker-compose-e2e.yaml``, is constructed to run end-to-end tests 1136 using the Node.js SDK. Aside from functioning with the SDK, its primary differentiation 1137 is that there are containers for the fabric-ca servers. As a result, we are able 1138 to send REST calls to the organizational CAs for user registration and enrollment. 1139 1140 If you want to use the ``docker-compose-e2e.yaml`` without first running the 1141 byfn.sh script, then we will need to make four slight modifications. 1142 We need to point to the private keys for our Organization's CA's. You can locate 1143 these values in your crypto-config folder. For example, to locate the private 1144 key for Org1 we would follow this path - ``crypto-config/peerOrganizations/org1.example.com/ca/``. 1145 The private key is a long hash value followed by ``_sk``. The path for Org2 1146 would be - ``crypto-config/peerOrganizations/org2.example.com/ca/``. 1147 1148 In the ``docker-compose-e2e.yaml`` update the FABRIC_CA_SERVER_TLS_KEYFILE variable 1149 for ca0 and ca1. You also need to edit the path that is provided in the command 1150 to start the ca server. You are providing the same private key twice for each 1151 CA container. 1152 1153 Using CouchDB 1154 ------------- 1155 1156 The state database can be switched from the default (goleveldb) to CouchDB. 1157 The same chaincode functions are available with CouchDB, however, there is the 1158 added ability to perform rich and complex queries against the state database 1159 data content contingent upon the chaincode data being modeled as JSON. 1160 1161 To use CouchDB instead of the default database (goleveldb), follow the same 1162 procedures outlined earlier for generating the artifacts, except when starting 1163 the network pass ``docker-compose-couch.yaml`` as well: 1164 1165 .. code:: bash 1166 1167 docker-compose -f docker-compose-cli.yaml -f docker-compose-couch.yaml -f docker-compose-etcdraft2.yaml up -d 1168 1169 **abstore** should now work using CouchDB underneath. 1170 1171 .. note:: If you choose to implement mapping of the fabric-couchdb container 1172 port to a host port, please make sure you are aware of the security 1173 implications. Mapping of the port in a development environment makes the 1174 CouchDB REST API available, and allows the 1175 visualization of the database via the CouchDB web interface (Fauxton). 1176 Production environments would likely refrain from implementing port mapping in 1177 order to restrict outside access to the CouchDB containers. 1178 1179 You can use **abstore** chaincode against the CouchDB state database 1180 using the steps outlined above, however in order to exercise the CouchDB query 1181 capabilities you will need to use a chaincode that has data modeled as JSON. 1182 The sample chaincode **marbles02** has been written to demostrate the queries 1183 you can issue from your chaincode if you are using a CouchDB database. You can 1184 locate the **marbles02** chaincode in the ``fabric/examples/chaincode/go`` 1185 directory. 1186 1187 We will follow the same process to create and join the channel as outlined in the 1188 :ref:`peerenvvars` section above. Once you have joined your peer(s) to the 1189 channel, use the following steps to interact with the **marbles02** chaincode: 1190 1191 1192 - Package and install the chaincode on ``peer0.org1.example.com``: 1193 1194 .. code:: bash 1195 1196 # before packaging Go chaincode, vendoring dependencies is required. 1197 cd /opt/gopath/src/github.com/hyperledger/fabric-samples/chaincode/marbles02/go 1198 GO111MODULE=on go mod vendor 1199 cd - 1200 1201 # package and install the Go chaincode 1202 peer lifecycle chaincode package marbles.tar.gz --path github.com/hyperledger/fabric-samples/chaincode/marbles02/go/ --lang golang --label marbles_1 1203 peer lifecycle chaincode install marbles.tar.gz 1204 1205 The install command will return a chaincode packageID that you will use to 1206 approve a chaincode definition. 1207 1208 .. code:: bash 1209 1210 2019-04-08 20:10:32.568 UTC [cli.lifecycle.chaincode] submitInstallProposal -> INFO 001 Installed remotely: response:<status:200 payload:"\nJmarbles_1:cfb623954827aef3f35868764991cc7571b445a45cfd3325f7002f14156d61ae\022\tmarbles_1" > 1211 2019-04-08 20:10:32.568 UTC [cli.lifecycle.chaincode] submitInstallProposal -> INFO 002 Chaincode code package identifier: marbles_1:cfb623954827aef3f35868764991cc7571b445a45cfd3325f7002f14156d61ae 1212 1213 - Save the packageID as an environment variable so you can pass it to future 1214 commands: 1215 1216 .. code:: bash 1217 1218 CC_PACKAGE_ID=marbles_1:3a8c52d70c36313cfebbaf09d8616e7a6318ababa01c7cbe40603c373bcfe173 1219 1220 - Approve a chaincode definition as Org1: 1221 1222 .. code:: bash 1223 1224 # be sure to modify the $CHANNEL_NAME variable accordingly for the command 1225 1226 peer lifecycle chaincode approveformyorg --channelID $CHANNEL_NAME --name marbles --version 1.0 --package-id $CC_PACKAGE_ID --sequence 1 --tls true --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem 1227 1228 - Install the chaincode on ``peer0.org2.example.com``: 1229 1230 .. code:: bash 1231 1232 CORE_PEER_MSPCONFIGPATH=/opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/users/Admin@org2.example.com/msp 1233 CORE_PEER_ADDRESS=peer0.org2.example.com:9051 1234 CORE_PEER_LOCALMSPID="Org2MSP" 1235 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 1236 peer lifecycle chaincode install marbles.tar.gz 1237 1238 - Approve a chaincode definition as Org2, and then commit the definition to the 1239 channel: 1240 1241 .. code:: bash 1242 1243 # be sure to modify the $CHANNEL_NAME variable accordingly for the command 1244 1245 peer lifecycle chaincode approveformyorg --channelID $CHANNEL_NAME --name marbles --version 1.0 --package-id $CC_PACKAGE_ID --sequence 1 --tls true --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem 1246 peer lifecycle chaincode commit -o orderer.example.com:7050 --channelID $CHANNEL_NAME --name marbles --version 1.0 --sequence 1 --tls true --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem --peerAddresses peer0.org1.example.com:7051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org1.example.com/peers/peer0.org1.example.com/tls/ca.crt --peerAddresses peer0.org2.example.com:9051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/peers/peer0.org2.example.com/tls/ca.crt 1247 1248 - We can now create some marbles. The first invoke of the chaincode will start 1249 the chaincode container. You may need to wait for the container to start. 1250 1251 .. code:: bash 1252 1253 # be sure to modify the $CHANNEL_NAME variable accordingly 1254 1255 peer chaincode invoke -o orderer.example.com:7050 --tls --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem -C $CHANNEL_NAME -n marbles --peerAddresses peer0.org1.example.com:7051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org1.example.com/peers/peer0.org1.example.com/tls/ca.crt --peerAddresses peer0.org2.example.com:9051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/peers/peer0.org2.example.com/tls/ca.crt -c '{"Args":["initMarble","marble1","blue","35","tom"]}' 1256 1257 Once the container has started, you can issue additional commands to create 1258 some marbles and move them around: 1259 1260 .. code:: bash 1261 1262 # be sure to modify the $CHANNEL_NAME variable accordingly 1263 1264 peer chaincode invoke -o orderer.example.com:7050 --tls --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem -C $CHANNEL_NAME -n marbles --peerAddresses peer0.org1.example.com:7051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org1.example.com/peers/peer0.org1.example.com/tls/ca.crt --peerAddresses peer0.org2.example.com:9051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/peers/peer0.org2.example.com/tls/ca.crt -c '{"Args":["initMarble","marble2","red","50","tom"]}' 1265 peer chaincode invoke -o orderer.example.com:7050 --tls --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem -C $CHANNEL_NAME -n marbles --peerAddresses peer0.org1.example.com:7051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org1.example.com/peers/peer0.org1.example.com/tls/ca.crt --peerAddresses peer0.org2.example.com:9051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/peers/peer0.org2.example.com/tls/ca.crt -c '{"Args":["initMarble","marble3","blue","70","tom"]}' 1266 peer chaincode invoke -o orderer.example.com:7050 --tls --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem -C $CHANNEL_NAME -n marbles --peerAddresses peer0.org1.example.com:7051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org1.example.com/peers/peer0.org1.example.com/tls/ca.crt --peerAddresses peer0.org2.example.com:9051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/peers/peer0.org2.example.com/tls/ca.crt -c '{"Args":["transferMarble","marble2","jerry"]}' 1267 peer chaincode invoke -o orderer.example.com:7050 --tls --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem -C $CHANNEL_NAME -n marbles --peerAddresses peer0.org1.example.com:7051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org1.example.com/peers/peer0.org1.example.com/tls/ca.crt --peerAddresses peer0.org2.example.com:9051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/peers/peer0.org2.example.com/tls/ca.crt -c '{"Args":["transferMarblesBasedOnColor","blue","jerry"]}' 1268 peer chaincode invoke -o orderer.example.com:7050 --tls --cafile /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/ordererOrganizations/example.com/orderers/orderer.example.com/msp/tlscacerts/tlsca.example.com-cert.pem -C $CHANNEL_NAME -n marbles --peerAddresses peer0.org1.example.com:7051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org1.example.com/peers/peer0.org1.example.com/tls/ca.crt --peerAddresses peer0.org2.example.com:9051 --tlsRootCertFiles /opt/gopath/src/github.com/hyperledger/fabric/peer/crypto/peerOrganizations/org2.example.com/peers/peer0.org2.example.com/tls/ca.crt -c '{"Args":["delete","marble1"]}' 1269 1270 - If you chose to map the CouchDB ports in docker-compose, you can now view 1271 the state database through the CouchDB web interface (Fauxton) by opening 1272 a browser and navigating to the following URL: 1273 1274 ``http://localhost:5984/_utils`` 1275 1276 You should see a database named ``mychannel`` (or your unique channel name) and 1277 the documents inside it. 1278 1279 .. note:: For the below commands, be sure to update the $CHANNEL_NAME variable appropriately. 1280 1281 You can run regular queries from the CLI (e.g. reading ``marble2``): 1282 1283 .. code:: bash 1284 1285 peer chaincode query -C $CHANNEL_NAME -n marbles -c '{"Args":["readMarble","marble2"]}' 1286 1287 The output should display the details of ``marble2``: 1288 1289 .. code:: bash 1290 1291 Query Result: {"color":"red","docType":"marble","name":"marble2","owner":"jerry","size":50} 1292 1293 You can retrieve the history of a specific marble - e.g. ``marble1``: 1294 1295 .. code:: bash 1296 1297 peer chaincode query -C $CHANNEL_NAME -n marbles -c '{"Args":["getHistoryForMarble","marble1"]}' 1298 1299 The output should display the transactions on ``marble1``: 1300 1301 .. code:: bash 1302 1303 Query Result: [{"TxId":"1c3d3caf124c89f91a4c0f353723ac736c58155325f02890adebaa15e16e6464", "Value":{"docType":"marble","name":"marble1","color":"blue","size":35,"owner":"tom"}},{"TxId":"755d55c281889eaeebf405586f9e25d71d36eb3d35420af833a20a2f53a3eefd", "Value":{"docType":"marble","name":"marble1","color":"blue","size":35,"owner":"jerry"}},{"TxId":"819451032d813dde6247f85e56a89262555e04f14788ee33e28b232eef36d98f", "Value":}] 1304 1305 You can also perform rich queries on the data content, such as querying marble fields by owner ``jerry``: 1306 1307 .. code:: bash 1308 1309 peer chaincode query -C $CHANNEL_NAME -n marbles -c '{"Args":["queryMarblesByOwner","jerry"]}' 1310 1311 The output should display the two marbles owned by ``jerry``: 1312 1313 .. code:: bash 1314 1315 Query Result: [{"Key":"marble2", "Record":{"color":"red","docType":"marble","name":"marble2","owner":"jerry","size":50}},{"Key":"marble3", "Record":{"color":"blue","docType":"marble","name":"marble3","owner":"jerry","size":70}}] 1316 1317 1318 Why CouchDB 1319 ------------- 1320 CouchDB is a kind of NoSQL solution. It is a document-oriented database where document fields are stored as key-value maps. Fields can be either a simple key-value pair, list, or map. 1321 In addition to keyed/composite-key/key-range queries which are supported by LevelDB, CouchDB also supports full data rich queries capability, such as non-key queries against the whole blockchain data, 1322 since its data content is stored in JSON format and fully queryable. Therefore, CouchDB can meet chaincode, auditing, reporting requirements for many use cases that not supported by LevelDB. 1323 1324 CouchDB can also enhance the security for compliance and data protection in the blockchain. As it is able to implement field-level security through the filtering and masking of individual attributes within a transaction, and only authorizing the read-only permission if needed. 1325 1326 A Note on Data Persistence 1327 -------------------------- 1328 1329 If data persistence is desired on the peer container or the CouchDB container, 1330 one option is to mount a directory in the docker-host into a relevant directory 1331 in the container. For example, you may add the following two lines in 1332 the peer container specification in the ``docker-compose-base.yaml`` file: 1333 1334 .. code:: bash 1335 1336 volumes: 1337 - /var/hyperledger/peer0:/var/hyperledger/production 1338 1339 For the CouchDB container, you may add the following two lines in the CouchDB 1340 container specification: 1341 1342 .. code:: bash 1343 1344 volumes: 1345 - /var/hyperledger/couchdb0:/opt/couchdb/data 1346 1347 .. _Troubleshoot: 1348 1349 Troubleshooting 1350 --------------- 1351 1352 - Always start your network fresh. Use the following command 1353 to remove artifacts, crypto, containers and chaincode images: 1354 1355 .. code:: bash 1356 1357 ./byfn.sh down 1358 1359 .. note:: You **will** see errors if you do not remove old containers 1360 and images. 1361 1362 - If you see Docker errors, first check your docker version (:doc:`prereqs`), 1363 and then try restarting your Docker process. Problems with Docker are 1364 oftentimes not immediately recognizable. For example, you may see errors 1365 resulting from an inability to access crypto material mounted within a 1366 container. 1367 1368 If they persist remove your images and start from scratch: 1369 1370 .. code:: bash 1371 1372 docker rm -f $(docker ps -aq) 1373 docker rmi -f $(docker images -q) 1374 1375 - If you see errors on your create, approve, commit, invoke or query commands, 1376 make sure you have properly updated the channel name and chaincode name. 1377 There are placeholder values in the supplied sample commands. 1378 1379 - If you see the below error: 1380 1381 .. code:: bash 1382 1383 Error: Error endorsing chaincode: rpc error: code = 2 desc = Error installing chaincode code mycc:1.0(chaincode /var/hyperledger/production/chaincodes/mycc.1.0 exits) 1384 1385 You likely have chaincode images (e.g. ``dev-peer1.org2.example.com-mycc-1.0`` or 1386 ``dev-peer0.org1.example.com-mycc-1.0``) from prior runs. Remove them and try 1387 again. 1388 1389 .. code:: bash 1390 1391 docker rmi -f $(docker images | grep dev-peer[0-9] | awk '{print $3}') 1392 1393 - If you see something similar to the following: 1394 1395 .. code:: bash 1396 1397 Error connecting: rpc error: code = 14 desc = grpc: RPC failed fast due to transport failure 1398 Error: rpc error: code = 14 desc = grpc: RPC failed fast due to transport failure 1399 1400 Make sure you are running your network against the "1.0.0" images that have 1401 been retagged as "latest". 1402 1403 - If you see the below error: 1404 1405 .. code:: bash 1406 1407 [configtx/tool/localconfig] Load -> CRIT 002 Error reading configuration: Unsupported Config Type "" 1408 panic: Error reading configuration: Unsupported Config Type "" 1409 1410 Then you did not set the ``FABRIC_CFG_PATH`` environment variable properly. The 1411 configtxgen tool needs this variable in order to locate the configtx.yaml. Go 1412 back and execute an ``export FABRIC_CFG_PATH=$PWD``, then recreate your 1413 channel artifacts. 1414 1415 - To cleanup the network, use the ``down`` option: 1416 1417 .. code:: bash 1418 1419 ./byfn.sh down 1420 1421 - If you see an error stating that you still have "active endpoints", then prune 1422 your Docker networks. This will wipe your previous networks and start you with a 1423 fresh environment: 1424 1425 .. code:: bash 1426 1427 docker network prune 1428 1429 You will see the following message: 1430 1431 .. code:: bash 1432 1433 WARNING! This will remove all networks not used by at least one container. 1434 Are you sure you want to continue? [y/N] 1435 1436 Select ``y``. 1437 1438 - If you see an error similar to the following: 1439 1440 .. code:: bash 1441 1442 /bin/bash: ./scripts/script.sh: /bin/bash^M: bad interpreter: No such file or directory 1443 1444 Ensure that the file in question (**script.sh** in this example) is encoded 1445 in the Unix format. This was most likely caused by not setting 1446 ``core.autocrlf`` to ``false`` in your Git configuration (see 1447 :ref:`windows-extras`). There are several ways of fixing this. If you have 1448 access to the vim editor for instance, open the file: 1449 1450 .. code:: bash 1451 1452 vim ./fabric-samples/first-network/scripts/script.sh 1453 1454 Then change its format by executing the following vim command: 1455 1456 .. code:: bash 1457 1458 :set ff=unix 1459 1460 .. note:: If you continue to see errors, share your logs on the 1461 **fabric-questions** channel on 1462 `Hyperledger Rocket Chat <https://chat.hyperledger.org/home>`__ 1463 or on `StackOverflow <https://stackoverflow.com/questions/tagged/hyperledger-fabric>`__. 1464 1465 .. Licensed under Creative Commons Attribution 4.0 International License 1466 https://creativecommons.org/licenses/by/4.0/