以太坊研究:ETH基于POA的环境搭建
许多同学有研究POA的想法,那么今天我们尝试创建以太坊基于 POA 的环境,首先搭建环境前的准备:
1.安装 go-ethereum,下载 go 的源码
1 |
|
2.编译go
1 2 3 |
|
3.创建4个文件夹
执行完成之后再bin的目录下会生成可执行文件geth,分别命名为node1.node2.signer1.signer2.node 是普通节点,用于后期节点间发起交易,在接下来的实验中,signer1 设置为创世块指定的授权节点;signer2为后期加入信任名单授权节点,目录如下:
1 2 3 |
|
4.私有链搭建创建新账户,将启动的数据分别存在不同的文件夹中。
1 |
|
至此我们有了四个账户,四个账户分别为
1 2 3 4 5 6 7 |
|
5.初始化创世块
在 1.6 之后的以太坊中提供了初始化创世块的工具:puppeth, 请选择含有 Geth & Tools 的版本下载,如下图标红处。下载地址:https://geth.ethereum.org/downloads/ , 也可以按照上文自行编译。
puppeth 是个互动式的程序,直接启动照着指示输入相关信息。设置 Private chain 名称,假定为 poa_test,如下:
6.指定每隔 30 秒生成一个区块
我们指定了第一个 signer1 这个用户用来挖矿,指定了 node1和 signer1 开始被填充了余额。
7.按照如下步骤将生成的初始块进行导出
8.导出后的配置文件如下如所示:
9.创世块为 json 格式
我们将创世块的内容列举如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 |
|
参数解释如下:
mixhash | 与 nonce 配合用于挖矿,由上一个区块的一部分生成的 hash。注意他和 nonce 的设置需要满足以太坊的 Yellow paper, 4.3.4. Block Header Validity, (44)章节所描述的 条件。. | |
---|---|---|
nonce | nonce 就是一个 64 位随机数,用于挖矿,注意他和 mixhash 的设置需要满足以太 坊的 Yellow paper, 4.3.4. Block Header Validity, (44)章节所描述的条件。 | | |
difficulty | 设置当前区块的难度,如果难度过大,cpu 挖矿就很难,这里设置较小难度 | | |
alloc | 用来预置账号以及账号的以太币数量,因为私有链挖矿比较容易,所以我们不需要 预置有币的账号,需要的时候自己创建即可以。 | | |
coinbase | 矿工的账号,随便填 | | |
timestamp | 设置创世块的时间戳 | | |
parentHash | 上一个区块的 hash 值,因为是创世块,所以这个值是 0 | | |
extraData | 附加信息,在 POA 挖矿中 | | |
gasLimit | 该值设置对 GAS 的消耗总量限制,用来限制区块能包含的交易信息总和,因为我 们是私有链,所以填最大。 | |
10.初始化私有链
使用 geth init 指令,分别初始化 4 个节点的 datadir,比如初始化 node1 可执行:
1 |
|
初始化完成之后,在每个文件夹中会生成两个子文件夹。
其中 geth 用来存储区块链的数据信息,keystore 用来存储账户信息,启动节点,分别执行以下命令:
1 2 3 4 5 6 7 |
|
11.建立data目录
datadir先前的步骤已经在每个节点各自的目录下都建立了data目录,networkid geths之间一定都要用同一个值才可以互相通信,比如实验中的66300. Portgeths 之间通信时,监听的一个port,由于四个节点都在本机,所以这里必须指定不同的值,使用 node1 对应 3000, node2 对应 3001, signer1 对应 3002, signer2 对应 3003.
Geth 参数含义如下:
identity | 区块链的标示,随便填写,用于标示目前网络的名字 | |
---|---|---|
init | 指定创世块文件的位置,并创建初始块 | | |
datadir | 设置当前区块链网络数据存放的位置 | | |
port | 网络监听端口 | | |
rpc | 启动 rpc 通信,可以进行智能合约的部署和调试 | | |
rpcapi | 设置允许连接的 rpc 的客户端,一般为 db,eth,net,web3 | | |
networkid | 设置当前区块链的网络 ID,用于区分不同的网络,是一个数字 | | |
console | 启动命令行模式,可以在 Geth 中执行命令 | |
12.启动成功后的截图如下
因为 signer1 为挖矿节点,所以在启动的时候需要进行解锁。
13.建立节点之前的通信
目前各个节点虽然已经启动,但是各个节点之间仍然处于孤立状态。各节点启动后无法相互通信的,所以geth要连上对方的节点就必须先设置好enode://@:,复制刚刚启动node1时出现的enode信息,将[::]替换为127.0.0.1,这样就可以让其他节点加入。如上面提示的的红色提示所见, node1 的 enode 为
1 |
|
在node2,singer1,singer2的geth console界面下分别运行如下指令:
完成后,在 node1 的 geth console 输入 admin.peers 应该要看到三个节点资讯,如下:(每个id 对应其他节点的 encode 字段信息)
至此四个节点之前的关系已经初步建立。
14.开始挖矿
按照实验的设计,在本实验中 signer1 为挖矿节点,我们下面开始进行模拟挖矿,在 signer1 的console 界面,键入 miner.start(),geth 就会开始挖矿了,在 signer1 的 console 会出现正在mining 的信息。
从上面可以看出挖矿的时间间隔为 30 秒,与我们创世块的中参数一致,同时在其他节点(node1 和 node2 和 signer2)则会收到 import block 的信息。如下:
15.交易转账
按照我们的预设,在 node1 和 signer1 上是已经初始化了余额的。我进行查询如下:
但是目前的账户处于锁定状态,所以首先我们要进行解锁。
进行解锁的命令如下:
1 |
|
我们开始对 node2 进行转账,如下图所示:
16.查看矿机的挖矿状态
此时已经将挖到的交易打入到区块中。查看 node2 账户的余额,展示如下:
到目前为止已经完成了 POA 私有链的所有内容的搭建。
17.加入新可信节点
按照预先实验设计,signer2 也为挖矿节点,如果此时启动 signer2 节点进行挖矿,则会出现未授权的异常,如下图所示:
18.节点授权
必须回到已经在授权名单内的节点的 console 界面下,将新的节点加入。在 signer1 的 console输入指令:
此时 signer1 挖矿节点的日志已经发生变化,已经签名,等待其他签名者。
19.重新启动
此时需要以输入密码的形式重新启动 signer2
1 |
|
建立连接,使用 admin.addPeer()重新建立连接
1 |
|
20.启动 singer2 开始挖矿
可以看到 signer1 和 signer2 在交替进行挖矿。
在 40 分 36 时,singner1,挖到了一个合适的区块, 进行签名后并立即进行广播,同时 signer2 获取到了最新的区块段,签名后并提交到网络中。singner1 在收到签名后进行打包,合并到区块中,并广播最新的消息。
至此,环境搭建全部完成 。