区块链入坑[1]--浅析Smart Contract,BlockChain的概念与ChainCode的编写

1.浅析基于区块链的智能合约(Smart Contract)

智能合约

在了解智能合约和传统合约之前我们先来了解合约(Contract)这个词本身,“合同(或合约),是双方当事人基于意思表示合致而成立的法律行为,为私法自治的主要表现。”在现在的日常生活中合约常常是由人或者指定的机构来代为执行的,这就是传统合约。

“智能合约(Smart contract)"这个概念由计算机科学家、加密学家尼克萨博(NickSzabo) 在1993年提出并且在1994年完成了《智能合约》论文。该论文成为了智能合约的开山之作。作为一位通过给比特币打下基础而受到广泛赞誉的密码学家,尼克萨博为智能合约下的定义:“A smart contract is a set of promises defined in digital form, including agreements on which contract participants can execute these commitments.。

传统合约其实也在演化,尤其是网购这种行为已经智能合约,所谓的"智能"就是脱离了人和机构,交由计算机去管理和执行的自动行为。 以网购为例,我们来了解智能合约的显著特征。下面假设 买家A通过淘宝Alipay卖家B买价值为100$的东西,那么计算机所执行的操作逻辑如下(LaTeX作图):
在这里插入图片描述
本质上是如下的单一关系(Word作图0.0)
传统合约
在这其中,支付宝(Alipay)是合约状态的判定者,钱的由支付宝保管,交易受支付宝监管。支付宝是合约的判定者和执行者,双方的资产转移,查询也全部由支付宝完成。

交易的状态判定和资产转移全部交给计算机重复地自动地执行,这就是典型的智能合约

这样的智能合约有很多隐患。我们不妨将合约判定者推广到支付宝以外的各个银行,交易机构甚至是日常生活中,只要中介机构的判断一方出现问题,你并没有收到东西,但是中介机构作假说判定卖家已经完成交易,你的钱已经被转走,那就可以破坏整个交易的公平性。或者交易机构的处理不够及时也能够造成损失。

之前所提到的大佬,加密学家萨博 就认为这种仅仅依靠第三方担保的信用机制是不可靠的,
经过一番思考他认为所有的交易合同都没有必要通过第三方完成,只要合同的条款可以用编程语言来表达,让计算机自动处理就行了。这样就避免了合同执行中的尔虞我诈,还节约了大量的交易成本。
然而这个想法也只是一个雏形,在他所处的90年代还没有数字资产,也没有很强大的计算机加密手段提出。这使得他的这种思想并不能很好地实践,而仅仅是用在了构建自动售货机、自动售票机的交易模式上。他缺少四样东西:

  1. 分布式的网络结构,能够避免第三方机构一家独大的网络结构。
  2. 在上述网络结构中,用以流通的数字话的,能够在计算机中记录的货币。
  3. 对上述数字化的货币唯一地,透明的加密手段。
  4. 网络结构中还要有传统的背书机构来记录全部交易。

而区块链的出现,使得萨博在90年代提出的超越时代的构想有了变为现实的能力。

基于区块链的智能合约

我们来想想区块链的特征:

  • DApp去中心化,使得参与交易者可以自证而不依赖第三方中介机构来背书。
  • 唯一性的数字货币。
  • 交易不可篡改,哈希以及系列编码手段使得交易记录唯一且不可被篡改。
  • 共识信任,通过技术来背书而不依赖机构。
  • 开放性以及过程透明,除了加密过的信息,其余的数据和应用都是可追溯,公开透明的。

Σ(っ °Д °;)っ这,这不就是…

是的,你会发现,这些特性完美地契合了萨博在90s的构想 (๑•̀ㅂ•́)و✧。
智能合约一旦上链,就没有了像之前依赖一方信任机构时各种各样的安全风险,并且变得透明,可追溯。

同样对上述买家A卖家B的交易,如果网购使用基于区块链的智能合约来完成,则你会发现缺少了Alipay,取而代之的是各式节点,流程图如下:(在线作图0.0)
智能合约
买家卖家双方,应用程序和管理员全部通过Peer节点来同步信息,Peer节点一手拿着账本(Ledger),一手拿着合约(ChainCode)。上图只是简单地描述整个过程,事实上一个Application/SDK会连接多个Peer节点和Order节点,网络图也更加复杂,并且Peer节点所持有的账本也有可能会是多项。

  1. Peer节点知道全部的规则并且管理所有参与者的资产。但是Peer在收到买卖双方信息之后并不直接记录到账本里面,而是返回一个结果响应并且保持账本数据。
  2. 当买卖双方收到足够的结果响应或者达到足够的时长之后,这些批量的数据将会打包发给Orderer,Orderer来对收到的数据进行排序,所有交易的排序是严格的,Orderer生成的区块也是不可篡改的,具有唯一性。生成区块之后将会分发给各个Peer。
  3. 各个Peer对照自己记录的结果响应和从[2]收到的区块,如果验证通过,那么再去检查账本的状态与合约是否一致:一致则交易有效,Peer节点更新账本状态;不一致则交易无效但是失败的交易还是会被保存,因为失败的交易所对应的区块也是唯一的,需要保存下来以保证基本的交易是否合法。

从上述的过程中就可以明白只要大多数的节点没有崩坏,那么交易就是安全的,而不像传统节点那样依赖中介机构一方的数据;并且由于Orderer和Peer节点定时以及定量地去检查交易的状态,使得交易的执行也是及时的。智能合约中更多地是P2P的交易,这使得很多交易可以透明,安全地完成而不需要第三方去监管。

2.链码以及案例sacc (ChainCode)

从上述对于上链过后的智能合约的简单描述中也可以知晓ChainCode负责的是P2P用户之间已经协商好的规则,也就是合约本身的内容,这个关键的规则应该被提前写入智能合约中。那么我们来分析ChainCode应该去完成的基本内容:

  1. 首先ChainCode应该有一个Init函数来初始化交易双方的资产和状态,或者Init函数只是返回初始化成功的信息。
  2. ChainCode应该有add,delete或者类似的能够增删账户数据的函数。
  3. ChainCode应该有query函数来询问现有账户的数据。
  4. 此外各个函数的报错信息应该完善。

yaml文件&区块链的结构

在区块链的开放当中我们使用的是yaml文件,百科出门右转度娘-YAML
yaml =“Yet Another Markup Language” 从英文解释可以看出yaml仍然是一种标志语言。它要比json方便,同时简洁而强大。话不多说,直接上fabric中的自带yaml配置文件docker-compose-simple.yaml(节选其中Orderer部分):

  orderer:
    container_name: orderer
    image: hyperledger/fabric-orderer
    environment:
      - FABRIC_LOGGING_SPEC=debug
      - ORDERER_GENERAL_LISTENADDRESS=orderer
      - ORDERER_GENERAL_GENESISMETHOD=file
    working_dir: /opt/gopath/src/github.com/hyperledger/fabric
    ports:
      - 7050:7050
  1. yaml中对象使用来表示,并且可以复用
  2. yaml中数组结构使用-来表示,子成员则在之后缩进

那么上述文件对应的JS代码应该如下:

order: 
{
   
container_name:'orderer'
image:'hyperledger/fabric-orderer'}
environment:['FABRIC_LOGGING_SPEC=debug',
      		'ORDERER_GENERAL_LISTENADDRESS=orderer',
      		'ORDERER_GENERAL_GENESISMETHOD=file']
working_dir: '/opt/gopath/src/github.com/hyperledger/fabric'
ports:'7050:7050'
}

docker-compose-simple.yaml中,我们可以看到基本的结构为
Orderer,Peer,Cli,ChainCode四个部分。
也可以打开docker-compose-base.yaml查看记录的区块链的基础结构为
两个Org联盟Org1和Org2,各个联盟里面有包含两个Peer节点Peer1和Peer2,同时还各自包含一个Orderer。
类似的文件有很多,例如负责通信的docker-compose-base.ca和各个connection文件,基本上fabric里所有的关于结构的配置文件全部都是yaml完成的。在跑源码之前可以先去查看这些文件。

使用开发模式测试链码

我们需要开三个Terminal来完成client,chaincode的测试。
yaml文件记录了区块链中的Org,Peer,Orderer以及相关结构的具体信息所以我们先
Terminal 1中启动 docker-compose-simple.yaml

docker-compose -f docker-compose-simple.yaml up

//结果如下:
Creating orderer ... done
Creating peer    ... done
Creating cli       ... done
Creating chaincode ... done
Attaching to orderer, peer, cli, chaincode
peer         | 2019-05-04 10:48:34.210 UTC [viperutil] getKeysRecursively -> DEBU 001 Found map[string]interface{
   } value for peer.BCCSP
orderer      | 2019-05-04 10:48:33.111 UTC [localconfig] completeInitialization -> INFO 001 Kafka.Version unset, setting to 0.10.2.0
peer         | 2019-05-04 10:48:34.211 UTC [viperutil] unmarshalJSON -> DEBU 002 Unmarshal JSON: value cannot be unmarshalled: invalid character 'S' looking for beginning of value
peer         | 2019-05-04 10:48:34.211 UTC [viperutil] getKeysRecursively -> DEBU 003 Found real value for peer.BCCSP.Default se

记得一定要检查oderer,peer,cli,chaincode(这个对于不同的项目,结构不同,以自己的yaml中的结构为准)有没有初始化成功,因为会输出很长的文字,所以不太容易直接看是否允许成功,lz第一次的时候就是peer失败了,但是没有仔细看,结果后面一路报错QAQ。
使用docker ps查看进程:

docker ps

//结果如下:
CONTAINER ID         COMMAND        CREATED    STATUS       PORTS                                                             NAMES
c7b0d0a23a54        hyperledger/fabric-ccenv     "/bin/bash -c 'sleep…"                                                       chaincode
589f8cd7b518        hyperledger/fabric-tools     "/bin/bash -c ./scri…"                                                       cli
ceeaaf3e5913        hyperledger/fabric-peer      "peer node start --p…"     0.0.0.0:7051->7051/tcp, 0.0.0.0:7053->7053/tcp    peer
d340752b0409        hyperledger/fabric-orderer   "orderer"                   0.0.0.0:7050->7050/tcp                           orderer

Terminal 2中输入 以下命令进入chaincode端口:

docker exec -it chaincode bash

进入go脚本sacc的文件夹,编译我们的go脚本:

go build

执行刚刚编译好的sacc:(看到starting up…卡着不动就是正常运行了)

CORE_PEER_ADDRESS=peer:7052 CORE_CHAINCODE_ID_NAME=mycc:0 ./sacc

//结果如下:(starting up代表开始运作,之后这个端口会一直记录chaincode的状态)
2019-05-04 10:55:51.401 UTC [shim] SetupChaincodeLogging -> INFO 001 Chaincode log level not provided; defaulting to: INFO
2019-05-04 10:55:51.402 UTC [shim] SetupChaincodeLogging -> INFO 002 Chaincode (build level: ) starting up ...

这里时常会有报错:

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值