智能合约笔记

智能合约学习笔记

1. 安装testrpc、truffle

1
$ npm install -g ganache-cli truffle

2. 启动testrpc

1
$ testrpc

3. 创建智能合约项目

3.1 初始化项目

新开一个终端窗口,通过以下命令建立项目:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
ted@MacBook-Pro  ~  mkdir SmartContact
ted@MacBook-Pro  ~  cd SmartContact
ted@MacBook-Pro  ~/SmartContact  mkdir HelloWorld
ted@MacBook-Pro  ~/SmartContact  cd HelloWorld
ted@MacBook-Pro  ~/SmartContact/HelloWorld  truffle init
Downloading...
Unpacking...
Setting up...
Unbox successful. Sweet!

Commands:

Compile: truffle compile
Migrate: truffle migrate
Test contracts: truffle test

ted@MacBook-Pro  ~/SmartContact/HelloWorld  ls
contracts migrations test truffle-config.js truffle.js

需要对目录结构做一个解释说明:
/contracts : 存放智能合约原始代码的地方,可以看到里面已经有一个sol文件。
/migrations : 这是 Truffle用来部署智能合约的功能。
/test : 测试智能合约的代码。
truffle.js : Truffle的设置文件。

3.2 创建HelloWorld合约

contracts文件夹中创建HelloWorld.sol文件,内容如下:

1
2
3
4
5
6
7
pragma solidity ^0.4.4;

contract HelloWorld {
function sayHello() internal pure returns (string) {
retrun ("Hello World");
}
}

3.3 编译

在项目的目录下执行truffle compile命令,将sol文件编译成Ethereum bytecode

1
2
3
4
ted@MacBook-Pro  ~/SmartContract/HelloWorld  truffle compile
Compiling ./contracts/HelloWorld.sol...
Compiling ./contracts/Migrations.sol...
Writing artifacts to ./build/contracts

3.4 部署

migrations文件夹中已经存在一个配置文件,1_initial_migration.js,仿照这个文件新建一个2_deploy_contracts.js,内容如下:

1
2
3
4
5
var HelloWorld = artifacts.require("HelloWorld");

module.exports = function(deployer) {
deployer.deploy(HelloWorld);
};

在命令行中执行truffle migrate开始部署,可能会遇到以下问题:

  • 问题1:no-network-specified-cannot-determine-current network

    解决办法是在`HelloWorld/truffle.js·文件中添加以下内容:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    module.exports = {
    // See <http://truffleframework.com/docs/advanced/configuration>
    // to customize your Truffle configuration!
    networks: {
    development: {
    host: "127.0.0.1",
    port: 8545,
    network_id: "*" // Match any network id
    }
    }
    };

如果没有问题,顺利执行之后,智能合约即可部署成功

1
2
3
4
5
6
7
8
9
10
11
12
13
14
 ted@MacBook-Pro  ~/SmartContract/HelloWorld  truffle migrate
Using network 'development'.

Running migration: 1_initial_migration.js
Deploying Migrations...
... 0x3bcee88795e7c924e37cafbc8d45ac4c1366027046b0a862c1eedaef7f52b766
Migrations: 0xf2922d5da87b0b1db38fa3b97f7f14c8f7addf8a
Saving artifacts...
Running migration: 2_deploy_contracts.js
Deploying HelloWorld...
... 0xda4bed7b7f31caaec9648419fd3cbe92e080c42929e6afdcfd4b113ccd64cbd9
HelloWorld: 0x58e311f91cae06f7e7d1e86fb8252d5f58c3f5c0
Saving artifacts...
ted@MacBook-Pro  ~/SmartContract/HelloWorld 

于此同时testrpc的窗口也有一些内容输出:

3.5 调用合约

通过命令truffle console进入truffle控制台,即可使用Javascript调用刚才部署的合约。

1
2
3
4
5
6
7
8
ted@MacBook-Pro  ~/SmartContract/HelloWorld  truffle console

truffle(development)> HelloWorld.deployed().then(instance => contract = instance)
TruffleContract {
//此处省略很多输出内容
//调用sayHello 方法
truffle(development)> contract.sayHello.call()
'Hello World & Ted'

需要解释一段代码

1
HelloWorld.deployed().then(instance => contract = instance)

·truffle console中预载了truffle-contract`函数库,以方便操作部署到区块链上的合约。

这边使用HelloWorld.deployed().then语句来取得HelloWorld合约的Instance(实例),并存到contract变量中,以方便后续的调用。

上面用的是Javascript ES6+的语法,这句也可以写成:

1
2
3
HelloWorld.deployed().then(instance => {
contract = instance
});

还可以用ES5的写法:

1
2
3
HelloWorld.deployed().then(function(instance) {
hello = instance;
});

这里直接呼叫contract.sayHello()也会得到一样的结果。truffle-contract提供使用call()来读取只读(read only)的数据,这样就不需提供gas。因此如果遇到的操作需要向区块链写入数据,我们就不能用call语句了。

最后在truffle console中输入.exit即可退出控制台回到终端页面。


参考文章:
如何编写智能合约(Smart Contract)?(I)

0%