搭建以太坊私链 & 实现简单的智能合约

环境配置

使用平台为Windows 10,安装go-ethereum客户端

输入geth --help检查是否安装成功:

搭建私有链

在genesis.json里定义创世区块配置信息

初始化区块链geth –datadir data0 init genesis.json

启动私有链节点geth –datadir data0 –networkid 1000 console --nodiscover

成功进入javascript控制台

私有链测试

添加账户

查看账户eth.accounts

创建账户personal.newAcount(),根据提示Passphrase输入密码

创建两个账户后,再次查看账户

查看这两个账户的余额

挖矿

启动挖矿,线程数为4个

生成挖矿所需的DAG文件之后开始输出挖矿信息

逐字符输入miner.stop()并回车停止挖矿,然后查看coinbase,也就是获得挖矿奖励的账户

就是上面创建的0号账户

查看矿工账户余额,单位是wei

转账

之前创建的1号账户余额应该为0

解锁0号账户

输入密码成功解锁账户,从0号账户转移10个以太币到1号账户

查看1号账户中的余额

发现余额依然是0,查看txpool

说明这次交易只是提交到了区块链,但是还没有被处理(pending),需要再次挖矿。这里设置挖到一个区块后就停止。

再次查看1号账户余额

1号账户余额为10,说明交易成功处理。

实现众筹合约

实现

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
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
// 版本为0.4.24
pragma solidity 0.4.24;


// 众筹合约
contract CrowFunding {
//赞助方结构体
struct Investor {
address addr; // 赞助地址
uint count; // 赞助数量
}

//发起方结构体
struct Initiator {
address addr; //发起方地址
uint goal; //众筹金额
uint received; //已经众筹到的金额
bool isClosed; //众筹是否结束
mapping(address =>Investor) investors; //赞助方信息
}

uint private initiatorNum = 0; //发起方的ID
mapping(uint => Initiator) private initiators; //发起方信息

//生成发起方对象
function addInitiator() public payable {
//要求金额大于0
require(msg.value > 0);
initiatorNum++;
initiators[initiatorNum] = Initiator(msg.sender, msg.value, 0, false);
}

//赞助功能
function sponsor(uint initiatorId) public payable {
//要求ID有效且赞助的金额必须 > 0
require(initiatorId <= initiatorNum && msg.value > 0);
Initiator storage initiator = initiators[initiatorId];
if (!initiator.isClosed) {
initiator.received += msg.value;
initiator.investors[msg.sender] = Investor(msg.sender, msg.value);
}
}

//查询目标金额
function getGoal(uint initiatorId) public constant returns (uint) {
//要求ID有效
require(initiatorId <= initiatorNum);
return initiators[initiatorId].goal;
}

//查询已众筹到的金额
function getReceived(uint initiatorId) public constant returns (uint) {
//要求ID有效
require(initiatorId <= initiatorNum);
return initiators[initiatorId].received;
}

//检查众筹金额是否足够
function checkComplete(uint initiatorId) public constant returns (bool) {
//要求ID有效
require(initiatorId <= initiatorNum);
Initiator storage initiator = initiators[initiatorId];
return initiator.received >= initiator.goal;
}

//撤资
function withdrawal(uint initiatorId) public payable {
//要求ID有效
require(initiatorId <= initiatorNum);
Initiator storage initiator = initiators[initiatorId];
if (!initiator.isClosed) {
uint amount = initiator.investors[msg.sender].count;
msg.sender.transfer(amount);
initiator.received -= amount;
initiator.investors[msg.sender].count = 0;
}
}

//关闭众筹
function close(uint initiatorId) public payable {
//要求ID有效
require(initiatorId <= initiatorNum);
Initiator storage initiator = initiators[initiatorId];
if (!initiator.isClosed) {
if (checkComplete(initiatorId)) {
initiator.addr.transfer(initiator.received);
}
initiator.isClosed = true;
}
}
}

测试

使用在线IDE

发起一个众筹项目

查看当前募资状态

赞助60

查看状态

再赞助50

再次查询状态

关闭众筹

参考

[1] 深入浅出区块链技术