这篇博客演示的基本操作系统环境是CentOS 7,参考书籍:以太坊开发实战——以太坊关键技术与案例分析 第十章(吴寿鹤、冯翔、刘涛、周广益   著)。鉴于内容较多,分成两篇,下一篇博文请见:以太坊学习路线——(四、下)truffle项目合约交互、合约测试、配置文件、依赖管理

文章结构:

一、Truffle简介

二、安装Truffle

三、创建并初始化项目

四、创建合约

五、编译合约

六、迁移合约

一、Truffle简介

  • Solidity学习网站
  • 通过密码僵尸游戏学习Solidity
  • Truffle学习网站

Truffle是一套针对以太坊Solidity语言的开发框架,本身基于javascript。Truffle为以太坊提供了开发环境、测试框架和资产管道(pipeline),旨在使以太坊开发更加容易。Truffle特性:

  • 内置的智能合约编译,链接,部署和二进制文件的管理。
  • 快速开发下的自动合约测试。
  • 脚本化的,可扩展的部署与发布框架。
  • 部署到不管多少的公网或私网的网络环境管理功能
  • 使用EthPM&NPM提供的包管理,使用ERC190标准。
  • 与合约直接通信的直接交互控制台(写完合约就可以命令行里验证了)。
  • 可配的构建流程,支持紧密集成。
  • 在Truffle环境里支持执行外部的脚本。

二、安装Truffle

$ npm install -g truffle

检查Turffle是否正确安装:

[root@localhost myproject]# truffle
Truffle v5.0.10 - a development framework for EthereumUsage: truffle <command> [options]Commands:build     Execute build pipeline (if configuration present)compile   Compile contract source filesconfig    Set user-level configuration optionsconsole   Run a console with contract abstractions and commands availablecreate    Helper to create new contracts, migrations and testsdebug     Interactively debug any transaction on the blockchain(experimental)deploy    (alias for migrate)develop   Open a console with a local development blockchainexec      Execute a JS module within this Truffle environmenthelp      List all commands or provide information about a specific commandinit      Initialize new and empty Ethereum projectinstall   Install a package from the Ethereum Package Registrymigrate   Run migrations to deploy contractsnetworks  Show addresses for deployed contracts on each networkobtain    Fetch and cache a specified compileropcode    Print the compiled opcodes for a given contractpublish   Publish a package to the Ethereum Package Registryrun       Run a third-party commandtest      Run JavaScript and Solidity testsunbox     Download a Truffle Box, a pre-built Truffle projectversion   Show version number and exitwatch     Watch filesystem for changes and rebuild the projectautomaticallySee more at http://truffleframework.com/docs
//我的truffle版本
[root@localhost myproject]# truffle version
Truffle v5.0.10 (core: 5.0.10)
Solidity v0.5.0 (solc-js)
Node v11.13.0
Web3.js v1.0.0-beta.37

三、创建并初始化项目

$ mkdir myproject
$ cd myproject
$ truffle init//完成后目录结构如下:
[root@localhost myproject1]# tree ./
./
├── contracts
│   └── Migrations.sol
├── migrations
│   └── 1_initial_migration.js
├── test
└── truffle-config.js
  • contracts/:存放我们编写的合约。
  • migrations/:存放迁移部署脚本
  • test/:存放合约测试脚本。
  • truffle-config.js/:存放truffle配置文件。

较早版本truffle init会在目录中创建一个名叫MetaCoin的代币应用。将这个应用相关文件删除,直到和上面的目录结构相同。

四、创建合约

在contracts目录下创建自己的合约Storage.sol:

$ cd contracts/
$ vi Storage.sol//合约内容如下:根据编译器版本不同,可能会出现不同的错误与警告,请自己核实处理
pragma solidity >=0.4.21 <0.6.0;contract Storage {uint256 public storedData;function set(uint256 data) public {storedData = data;}function get() public view returns (uint256) {return storedData;}
}

五、编译合约

[root@localhost myproject]# truffle compileCompiling your contracts...
===========================
> Compiling ./contracts/Storage.sol
> Artifacts written to /opt/myproject/build/contracts
> Compiled successfully using:- solc: 0.5.0+commit.1d4f565a.Emscripten.clang

从输出结果可以看到,合约编译后的文件会写入./build/contracts目录中,这些合约编译好之后的文件对于Truffle框架能否正常工作至关重要。请不要手动修改这些文件,因为即使修改了,再次执行编译命令时又会被覆盖。

Truffle默认只编译自上次编译后修改过的合约,目的是减少不必要的编译。如果你想编译全部合约,可以使用--all选项。

$ truffle compile --all

六、迁移合约

迁移脚本是由一些javascript文件组成,在truffle中部署合约需要用到迁移脚本。这是因为你的部署需求会随着时间改变。随着项目的发展,你可以创建新的迁移脚本把这些变化的合约部署到区块链上。之前你运行的迁移历史记录,会被一个特殊的Migrations.sol合约记录在区块链。

迁移合约命名规则:文件以数字开头,以一个描述性的后缀结尾。数字前缀是必须的,用于记录移植是否成功。后缀仅仅是为了提高可读性,以方便理解。

下面进入migrations目录中为Storage合约创建一个迁移脚本:

$ cd migrations
$ touch 2_storage_migrations.js//迁移脚本2_storage_migrations.js内容:
const Migrations = artifacts.require("Storage");module.exports = function(deployer) {deployer.deploy(Migrations);
};

1.artifacts.require()

在迁移脚本中的最开始,通过artifacts.require()方法告诉truffle我们将要与哪个合约交互。这个方法类似于Nodejs中的require,但在这里,它返回的是一个合约抽象。我们可以在迁移脚本的其余部分中使用这个合约抽象。artifacts.require()参数中使用的名字不是必须与合约源文件的文件名相同,相反,它应该与在合约源代码中定义的合约类定义的合约类的名称相同。

2.module.exports

在迁移合约脚本最后,我们通过module.exports导出一个函数,被迁移脚本导出的函数都应高接受一个depoyer对象作为其第一个参数。

3.迁移合约

至此就可以把Storage.sol部署到区块链上了,这次把智能合约部署到Testrpc环境中。

//如果你还没有安装Testrpc那么先执行下面的命令,其需要Node较高版本的环境依赖
$ npm install -g ethereumjs-testrpc//安装完成后启动Testrpc:
$ testrpc

testrpc启动后,回到myproject项目的目录中,通过执行下面的命令就可以完成合约迁移:

$ truffle migrate

但是由于的truffle版本是,所以出现了如下问题:

Compiling your contracts...
===========================
> Everything is up to date, there is nothing to compile.Could not connect to your Ethereum client with the following parameters:- host       > 127.0.0.1- port       > 7545- network_id > 5777
Please check that your Ethereum client:- is running- is accepting RPC connections (i.e., "--rpc" option is used in geth)- is accessible over the network- is properly configured in your Truffle configuration file (truffle-config.js)Truffle v5.0.10 (core: 5.0.10)
Node v11.13.0

猜测可能是提示检测的最后一条选项,所以打开truffle-config.js,设置其中部分内容如下:

 networks: {// Useful for testing. The `development` name is special - truffle uses it by default// if it's defined here and no other network is specified at the command line.// You should run a client (like ganache-cli, geth or parity) in a separate terminal// tab if you use this network and you must also set the `host`, `port` and `network_id`// options below to some value.//development: {host: "127.0.0.1",     // Localhost (default: none)port: 8545,            // Standard Ethereum port (default: none)network_id: "*",       // Any network (default: none)},

修改后重新迁移,部分显示结果如下:

2_storage_migration.js
======================Deploying 'Storage'-------------------> transaction hash:    0x92cb91d96ddce4c5f5f73ba7b31a6d26b7f92e6a9b559f5e624281e35be8a50c> Blocks: 0            Seconds: 0> contract address:    0x92Afc835189BAf7a82AFfa45282eFbAa449da4c6> account:             0xF8A0A572fF93C87A711D7B6FD71b7b81650daCE1> balance:             99.99084662> gas used:            130727> gas price:           20 gwei> value sent:          0 ETH> total cost:          0.00261454 ETH> Saving migration to chain.> Saving artifacts-------------------------------------> Total cost:          0.00261454 ETH

从显示信息可以看出在部署Storage合约时,是以交易的形式将合约发布到测试网络中,可以看到发布合约的交易地址hash,合约地址、合约用户account帐号……,而且在testrpc终端也可以看到相同的操作记录:

  Transaction: 0x92cb91d96ddce4c5f5f73ba7b31a6d26b7f92e6a9b559f5e624281e35be8a50cContract created: 0x92afc835189baf7a82affa45282efbaa449da4c6Gas usage: 130727Block Number: 3Block Time: Tue Apr 02 2019 09:26:46 GMT+0800 (Hong Kong Standard Time)

truffle migrate命令会执行所有位于migrates目录内的迁移脚本。如果你之前已经成功执行过迁移脚本,那么truffle migrage仅会执行新创建的迁移。如果没有新的迁移脚本,这个命令不会执行任何操作,可使用选项--reset来重新执行全部迁移脚本。

$ truffle migrate --reset

4.初始化性的迁移合约

为了使用迁移功能,Truffle要求你要有一个迁移合约。这个合约必须包含一个特定的接口,对于大多数项目来说,这个合约只会在第一次做迁移的时被部署,以后都不会做任何更改了。这个合约就是在一开始truffle init之后在contracts目录下默认创建的那个Migrations.sol文件。

为了利用迁移的特性,首先必须部署这个Migrations.sol合约,所以truffle init时也默认在migrations目录下创建了该合约的迁移脚本:1_initial_migrations.js      要部署其他合约你可以递增数字编号前缀来创建新的迁移脚本。

5.部署器(deployer)

你的迁移脚本会使用deployer对象来组织部署任务。deployer对象会同步执行部署任务,故你可以按顺序编写部署任务。

//先部署A,后部署B
deployer.deploy(A);
deployer.deploy(B);

另外,deployer上的每一个函数都会返回一个promise,通过promise可以把有执行顺序依赖关系的部署任务组成队列。

//先部署A,然后部署B,把A部署后的地址传给B
deployer.deploy(A).then( function () {return deployer.deploy(B,A.address);
});

6.deployer API

(1).deployer.deploy(CONTRACT,ARGS…,OPTIONS)

这个API用来部署合约,contract参数传入需要部署的合约名字,args参数传入合约的构造函数需要的参数,options是一个可选参数,它的值是{overwrite:true/false}。如果overwrite被设置为false,那么当这个合约之前已经部署过了,这个deployer就不会再部署这个合约,这在一个合约的依赖由另一个外部地址提供的情况下是有用的。为了快速进行部署多个合约,你可以向deployer。deploy(…)函数中传入一个或多个数组。eg:

//部署单个合约,不带任何构造参数
deployer.deploy(A);//部署单个合约带有构造参数
deployer.deploy(A,arg1,arg2,……);//部署多个合约,有的带有构造参数,有的不带构造参数
//比写三次deployer.deploy()语句更快,因为deployer可以把所有的合约部署一次性打包提交
deployer.deploy([[A,arg1,arg2,…],[B],[C,arg1]
]);//外部依赖的例子:
//overwrite:false表示如果SomeDependency合约之前已经被部署过,那么不再重复部署,之结使用之前已经部署好的地址
//如果合约要运行在自己的测试链上,或者将要运行的链上没有SomeDependency合约,
//那么把overwrite:false改为ovwewrite:true,表示不再检查之前SomeDependency有没有部署过,一律覆盖部署
deployer.deploy(SomeDependency,{overwrite:false});

(2).deployer.link(LIBRARY,DESTINATIONS)

把一个已部署好的库链接到一个或多个合约里。destinations可以传入一个合约,也可以传入一组合约。如果destinations中的某个合约不依赖这个库,那么deployer的link函数就会忽略这个合约。

//部署库LibA,然后把LibA链接到合约B,然后部署合约B
deployer.deploy(LibA);
deployer.link(LibA,B);
deployer.deploy(B);//库LibA链接到多个合约
deployer.link(LibA,[B,C,D]);

(3).deployer.then(function() {…})

在迁移过程中使用它调用特定合约的函数来部署新的合约,为已部署的合约做一些初始化工作等。eg:

var a,b;
deployer.then(function () {//部署合约A的一个新版本到网络上return A.new();
}).then(function (instance) {a = instance;//获取已部署的合约B的实例return B.deployed();
}).then(function (instance) {b = instance;//使用合约B的setA()方法设置A的地址的新实例return b.setA(a.address);
});

(4).网络相关

在执行迁移时,Truffle会把truffle-config.js里配置的networks传递给迁移脚本,你可以在迁移脚本中的module.exports导出函数中的第二个参数位置接受这个networks参数值。

//truffle-config.js文件
module.exports = {networks: {development: {host: "127.0.0.1",     // Localhost (default: none)port: 8545,            // Standard Ethereum port (default: none)network_id: "*",       // Any network (default: none)}}
};//在迁移脚本中接受networks:
module.exports = function(deployer.network) {if (network == "live") {//TODO} else {//TODO}
}

(5).可用的账户

在执行迁移时,Truffle会把当前以太坊客户端或web3.provider中可用的账户列表传递给迁移脚本,这个账户列表与web3.eth.getAccount()返回的账户列表完全一样。你可以在迁移脚本中的module.exports导出函数中第三个参数位置接受这个accounts参数值。

module.exports = function(deployer,networks,accounts) {//在你的迁移脚本中使用账户
}

以太坊学习路线——(四、上)Truffle安装、truffle项目创建、编译、部署相关推荐

  1. 以太坊学习路线——(二、上)搭建testrpc测试链

    这篇博客演示的基本操作系统环境是CentOS 7,参考书籍:以太坊开发实战--以太坊关键技术与案例分析 第五章(吴寿鹤.冯翔.刘涛.周广益   著).首先请自行搜索安装并更新nodejs到较高版本. ...

  2. 以太坊学习路线——(五)DApp开发:简易版去中心化微博

    这篇博客演示的基本操作系统环境是CentOS 7,参考书籍:以太坊开发实战--以太坊关键技术与案例分析 第十一章(吴寿鹤.冯翔.刘涛.周广益   著). 项目地址,包含该项目所需大部分文件,前端因为依 ...

  3. 以太坊学习路线——(三)Solidity常用IDE搭建、合约编译、部署、调用

    这篇博客演示的基本操作系统环境是CentOS 7,参考书籍:以太坊开发实战--以太坊关键技术与案例分析 第七.九章(吴寿鹤.冯翔.刘涛.周广益   著). 一.常用IDE 1.remix:是一个浏览器 ...

  4. 以太坊学习路线——(一)私有链搭建与基本操作

    这篇博客演示的基本操作系统环境是CentOS 7,参考书籍:以太坊开发实战--以太坊关键技术与案例分析 第五章(吴寿鹤.冯翔.刘涛.周广益   著). 文章结构: 一.geth客户端安装 二.搭建一个 ...

  5. 以太坊学习路线——(二、下)以太坊编程接口:web3.js

    这篇博客演示的基本操作系统环境是CentOS 7,参考书籍:以太坊开发实战--以太坊关键技术与案例分析 第六章(吴寿鹤.冯翔.刘涛.周广益   著).要运行本博文相关程序,需要搭建以太坊私有链.安装t ...

  6. 以太坊学习笔记(持续更新,欢迎指正)

    以太坊学习笔记 一.SyntaxError: Functions are not allowed to have the same name as the contract. If you inten ...

  7. 区块链学习-以太坊学习简介

    想知道更多关于区块链技术知识,请百度[链客区块链技术问答社区] 链客,有问必答!! 区块链1.0时代: 也就是比特币应用中的区块链技术,里面记录着自比特币诞生以来的所有比特币转账交易,相当于比特币网络 ...

  8. Android开发学习总结(四)——Eclipse在线安装ADT插件

    Android开发学习总结(四)--Eclipse在线安装ADT插件 要想使用Eclipse开发Android应用,首先要安装一个ADT插件,在此记录一下在Eclipse中采用在线安装的方式ADT插件 ...

  9. Django框架学习(一)Django框架安装和项目创建详解

    Django框架学习(一)Django框架安装和项目创建详解 文章目录 Django框架学习(一)Django框架安装和项目创建详解 一.简介 1.1介绍 1.2 URL 1.3.框架原理 二.安装 ...

最新文章

  1. 1 分钟带你认识从 � 到 锟斤拷
  2. cctype,string,vector
  3. HDMI高清光端机产品特点及应用场合介绍
  4. Linux USB 驱动开发实例 (三)—— 基于USB总线的无线网卡浅析
  5. 前端学习(1872)vue之电商管理系统电商系统之完善登录之后的操作
  6. 为什么使用数据库从库
  7. 统计数字(信息学奥赛一本通-T1239)
  8. 3D深度估计,让视频特效更梦幻!
  9. python 元组与数组的区别_python – NumPy – 从元组到数组的高效转换?
  10. 【网络信息安全】Web 安全
  11. Voleon Group:一家『纯』用机器学习策略的对冲基金
  12. Arduino IDE搭建ESP8266开发环境!文件下载过慢解决方法!
  13. MIUI ROM for Milestone 刷机教程
  14. PC端后台项目的总结
  15. 8-1 职场价值塑造-摆脱低价值瓶颈,展示高价值收获新机会
  16. 素人程序员:如何在技术浪潮更迭中保持较高成长速度?
  17. 【安卓Android】VibratorService分析
  18. WebDriver - 伪浏览器PhantomJs(ghost driver) HtmlUnit
  19. win10系统1903版本设置默认英文输入法
  20. 2021 年第十三届四川省 ACM-ICPC 大学生程序设计竞赛(A/B/D/H/E/K/M/L)

热门文章

  1. 结绳4.0编程悬浮窗制作
  2. 跨时钟域同步-结绳法
  3. 通过cib.xml重新启动pacemaker
  4. matlab R2011a汉化包,《科学计算语言》(Mathworks Matlab)R2011a Win/UNIX[光盘镜像]
  5. java编程思想读书笔记
  6. sql查询取第一条数据
  7. http——基础知识
  8. 幼儿使用计算机需要注意事项,儿童玩电脑的优缺点及注意事项
  9. 关于Paxos的历史
  10. nltk安装,语料库nltk下载