第一行代码:以太坊(3)-使用更多的工具编写和测试智能合约

《第一行代码:以太坊》开始连载了

在上文中已经使用了Remix环境运行和测试了本书编写的第一个智能合约程序,不过编写和测试智能合约的测试方式很多,例如,在testrpc环境测试;在Intellij IDEA集成开发环境中用Solidity语言编写智能合约;在纯Web环境中测试智能合约;使用AJAX方式测试智能合约等。本文将详细介绍这些用于编写和测试智能合约的方法。

1.安装本地remix环境(Windows、Mac OS X和Linux)

在本节使用Remix环境运行和测试了Calc智能合约,不过使用的是在线Remix环境。由于某些原因(如没有网络,或网络速度很慢),我们希望使用本地的Remix环境运行和测试智能合约,这就要就将Remix环境安装在本地。Remix是跨平台的,所以本节介绍的安装方法同时适用于Windows、Mac OS X和Linux。

不管是在什么操作系统下安装Remix,都必须安装Node.js,读者可以到https://nodejs.org下载Node.js的最新版直接安装即可。

安装完Node.js后,需要使用git命令下载Remix的代码库(browser-solidity),命令行如下:

git clone https://github.com/ethereum/browser-solidity

在Mac OS X和Linux下,一般会集成git命令,但在Windows下,默认是没有git命令的,所以需要到下面的页面下载Windows版的git工具,下载完后直接安装即可。

https://git-scm.com/download/win

使用git命令下载完Remix的代码库后,使用cd命令进入browser-solidity目录,该目录在下载Remix代码库的过程中自动在当前目录中创建。

在browser-solidity目录中执行下面的命令安装browser-solidity。

npm install

安装browser-solidity的过程比较漫长,读者要耐心等待。下图是在Windows下安装browser-solidity环境的效果。

如果成功安装了browser-solidity,可以使用下面的命令启动Remix服务。

npm start

下图是Mac OS X下启动Remix服务后的输出信息,Windows和Linux会输出类似的信息。

Remix服务默认的端口号是8080,如果在浏览器地址栏中输入下面的Url,就可以使用本地的Remix环境编写和测试智能合约。

http://localhost:8080

2. 安装testrpc

testrpc与geth不同,geth是真正的以太坊环境,而testrpc是在本地模拟的一个以太坊环境,主要用于开发调试。当智能合约使用testrpc调试通过后,可以部署在真正的以太坊环境中。
安装testrpc仍然需要Node.js环境,所以读者应该事先安装好Node.js,然后使用下面的命令安装testrpc。
npm install -g ethereumjs-testrpc

安装好testrpc后,可以使用testrpc命令运行testrpc。下图是Mac OS X下启动testrpc服务的效果。

下图是Windows下启动testrpc服务的效果。

我们可以看到,不管是在哪一个平台上启动testrpc服务,都会自动生成10个账号(Accounts)和10个私钥(Private Keys)。这些账号和私钥都是用于测试的,而且每一个账号拥有的以太币几乎是无限大的,因此,不用担心进行某些操作后没有以太币可用。

testrpc本身是一个服务,默认的端口号是8545,这个端口号是用于像web3.js、web3.py一样的程序库连接以太坊节点的,testrpc其实也相当于一个用于测试的以太坊节点。

3.使用testrpc测试智能合约

本节会将智能合约部署到testrpc服务上,然后使用web3.js连接testrpc服务,并调用智能合约中的函数。具体的操作步骤如下:

(1)编写智能合约

启动本地的Remix环境,然后在Remix环境中输入下面的智能合约代码。

本例编写了一个名为Factorial的智能合约程序,在该智能合约中有一个factorial函数,用于计算n的阶乘。

pragma solidity ^0.4.0;
contract Factorial
{
    /*  计算n的阶乘  */
   function factorial(uint n) returns (uint)
   {
        if (n == 0 || n == 1)
            return 1;
        else
            return n * factorial(n - 1);
    }
}

这个智能合约用于计算n的阶乘。

(2)将智能合约部署在testrpc节点上

在Remix环境的右侧进入“Run”页面,并在“Environment”列表中选择“Web3 Provider”,如下图所示。

在Web3 Provider环境下,Remix可以将智能合约直接部署到testrpc服务上。进入Web3 Provider之前,会弹出一个对话框,询问是否连接以太坊节点,单击“OK”按钮,会弹出如下图所示的对话框。在该对话框中有一个文本框,默认值是http://localhost:8545,如果要连接本地的testrpc节点或以太坊节点,直接单击“OK”按钮即可。如果testrpc节点已经启动,那么Remix本地环境会成功连接到testrpc节点上。

单击“Run”页面的“Deploy”按钮,会将Factorial智能合约部署到testrpc上。部署成功后,会在“Run”页面的下方出现“factorial”按钮,如下图所示。在按钮右侧的文本框输入要计算阶乘的n的值,然后点击该按钮即可在以太坊测试环境(testrpc)下执行factorial函数,不过在日志区域点击“Details”按钮后,并没有看到factorial函数的输出结果,这是因为factoria函数是直接在以太坊网络中运行的,所有的数据都存在于以太坊网络中,并不会直接将数据返回给以太坊客户端。

在“factorial”按钮的上方是Factorial智能合约的地址,如果在客户端要访问这个智能合约,需要使用这个地址。

(3)安装Solidity编译器

Solidity编译器是用于编译Solidity源代码文件(.sol文件)的,可以将Solidity源代码文件编译成多种目标文件。使用下面的命令行可以安装Solidity编译器。

npm install -g solc

(4)编译Solidity源代码文件

在当前目录创建一个Factorial.sol文件,然后将例3.2中的代码复制到Factorial.sol文件中。接下来会使用上一步安装的Solidity编译器对Factorial.sol文件进行编译。要注意,尽管安装的是solc,但编译器命令行工具是solcjs。这个工具可以将Solidity源代码文件编译成多种目标文件,对于本例来说,只需要abi文件即可,该文件是智能合约的接口文件。也就是说,使用Web3.js调用智能合约,需要使用abi文件才能调用智能合约中函数。

使用下面的命令可以将Factorial.sol文件编译生成abi文件。其中--abi是命令行参数,表示生成的目标文件类型是abi。

solcjs --abi Factorial.sol

执行完上面的命令后,会在当前目录生成一个Factorial_sol_Factorial.abi文件,该文件就是Factorial.sol对应的abi文件。

(5)安装Web3.js

在使用Web3.js之前必须安装Web3.js,Web3.js是Node.js的一个模块,所以需要使用下面的命令安装。

npm install web3

使用上面的命令会安装web3的最新版,如果读者使用web3最新版不太习惯,可以使用下面的命令安装指定版本。

npm install [email protected]

(6)用Web3.js连接testrpc节点

现在执行node命令进入Node.js的REPL环境(命令行交互环境),然后在Node的REPL环境执行下面的命令。要注意,在执行这些命令之前,要先启动testrpc节点,并且利用Remix环境将例3.2中的智能合约部署到testrpc节点上。

> var Web3 = require("web3");
> var web3 = new Web3(new Web3.providers.HttpProvider("http://localhost:8545"));
undefined
> var eth = web3.eth
undefined
> var abi = JSON.parse(fs.readFileSync("Factorial_sol_Factorial.abi").toString());
undefined
> var contract = eth.contract(abi);
undefined
> var instance = contract.at(‘0x371f45db1a077bbcbeb50d2a21bc85e4e18c1f1f‘)
undefined
> instance.factorial.call(3)
{ [String: ‘6‘] s: 1, e: 0, c: [ 6 ] }
> instance.factorial(10, {from:eth.accounts[0]})
‘0xbb291fec53c4c5aefc87e2d7e8475c4abd4c54d03ef06e857665a10db0c1a3ff‘

上面的内容中“>”表示命令提示符,后面是输入的代码,下面是输出值,undefined是Node输出的,表示当前语句什么也没有输出(定义变量的JavaScript语句不会输出任何东西)。从这几行代码可以了解通过Web3.js连接testrpc节点的核心步骤(与连接以太坊节点的步骤相同)如下。

(1)导入web3模块,代码如下:

var Web3 = require("web3");

(2)创建Web3类的实例,并通过该类的构造方法参数指定testrpc节点的Url(IP和端口号),代码如下:

var web3 = new Web3(new Web3.providers.HttpProvider("http://localhost:8545"));

(3)读取Factorial_sol_Factorial.abi文件的内容,并将文件的内容转换为JSON对象,代码如下:

var abi = JSON.parse(fs.readFileSync("Factorial_sol_Factorial.abi").toString());

(4)使用abi创建智能合约对象,代码如下:

var contract = eth.contract(abi);

(5)将智能合约与testrpc中部署的智能合约绑定,代码如下:

var instance = contract.at(‘0x371f45db1a077bbcbeb50d2a21bc85e4e18c1f1f‘)

其中at方法的参数值就是图3-12所示的factorial方法上方的智能合约地址,也是以太坊中唯一能定位特定智能合约的标识。点击地址右侧的按钮可以将该地址复制到剪贴板上。

(6)本地调用智能合约中的factorial函数,代码如下:

instance.factorial.call(3)

本地调用智能合约,不会对以太坊网络造成任何影响。本地调用智能合约中的函数会直接输出函数的返回值,如果函数返回的是数值类型,会以BigNumber类型返回,这是一个JavaScript扩展,允许JavaScript操作任何的数值,BigNumber类型会在本书后面的章节详细讲解。

执行上面的代码,会输出如下内容,很明显,3的阶乘是6。

[String: ‘6‘] s: 1, e: 0, c: [ 6 ] }

(7)在以太坊网络上调用智能合约,代码如下:

instance.factorial(10, {from:eth.accounts[0]})

在以太坊网络上调用智能合约的函数不会在客户端直接得到函数的返回值,而会得到一个如下的交易地址。

0xbb291fec53c4c5aefc87e2d7e8475c4abd4c54d03ef06e857665a10db0c1a3ff

因为任何在以太坊网络上进行的操作都被视作一次交易,既然有交易,就需要有交易地址,可以通过相应的API根据交易地址查询交易情况。在以太坊网络中有很多类型的地址,如矿工地址、智能合约地址、交易地址等。每一类地址都由若干位十六进制数组成,但不同类型地址的位数可能不同。

在真正的以太坊网络中,任何交易都需要矿工挖矿进行处理,同时每一笔交易会给与完成工作的矿工一定的奖励,也就是矿工的挖矿所得。不过在testrpc节点中由于是模拟以太坊网络和挖矿,所以不需要挖矿,直接会执行以太坊网络上的操作,因此,如果客户端连接的是testrpc节点,发起交易后,会立刻执行。另外,在以太坊网络上调用智能合约,需要指定是谁(一个表示用户的地址)发起的交易,因为在实际的以太坊网络中,要从这个地址扣除相应的以太币给矿工。本例使用eth.accounts[0]指定的地址。其中eth.accounts可以获取testrpc节点启动时生成的10个测试账户的地址,eth.accounts[0]就是第一个测试账户的地址。

从本节的案例来看,客户端访问以太坊网络的步骤就是连接以太坊节点和发起交易两步,当然,以太坊网络要处理交易,就需要矿工挖矿(争夺处理交易的权利,同时获得回报)了。
3.2.4 Intellij IDEA Solidity插件
不管是Remix,还是Windows记事本,或是其他的文本编辑器,都不会用于开发复杂的智能合约,一是界面并不友好,二是也没有必要的智能提示功能,而且如果智能合约的代码量很大,可能会造成Remix死掉。所以前面介绍的工具只是为了测试智能合约的,并不是用来开发实际的智能合约项目的。如果要开发大型的智能合约项目,通常会使用本地的IDE,如Intellij IDEA。这款IDE最初是为开发Java项目推出的,不过由于Intellij IDEA支持第三方插件,所以从理论上,Intellij IDEA可以支持任何的编程语言。

可能很多读者对Intellij IDEA并不熟悉,实际上,这款IDE就是大名鼎鼎的JetBrains公司推出的,如果不了解JetBrains以及它的产品,那么对Android和Google推出的Android开发工具Android Studio一定不陌生,Android Studio就是在Intellij IDEA社区版的基础上开发的。而且JetBrains公司还开发出了大名鼎鼎的Kotlin语言,现在已经成为开发Android App的官方推荐编程语言。

读者可以到下面的页面下载Intellij IDEA的免费版本(社区版)。
https://www.jetbrains.com/idea/download

Solidity语言同样提供了Intellij IDEA插件,建议使用在线安装方式。如果是Mac OSX版本的Intellij IDEA,单击左上角的IntelliJ IDEA菜单的Preferences菜单项,如下图所示。

如果是Windows版的Intellij IDEA,需要单击File菜单的Settings菜单项。单击该菜单项后,会弹出偏好(设置)窗口,如下图所示。

Preferences窗口中间的列表列出了Intellij IDEA已经安装的所有插件。单击窗口下方的Browse repositories按钮,会弹出Browse Repositories窗口,在窗口左上角的文本框中输入Solidity,会在线搜索相关的插件,如下图所示,如果找到,会在右侧显示当前选中插件的详细信息,如果没有安装该插件,会在右侧显示install按钮,单击install按钮即可安装插件。

安装完插件后,在Intellij IDEA中创建一个Java或其他工程(Solidity插件并没有提供Solidity工程),然后在工程右键菜单中单击new菜单项,会显示如下图所示的子菜单。在子菜单上会找到一个Smart contract菜单项。

单击Smart contract菜单项,会显示如下图所示的New Solidity File窗口,从Kind列表框可以选择Solidity文件类型(Smart contract或Solidity library),本例选择Smart contract。

在Name文本框中输入Solidity文件名后,单击OK按钮创建Solidity文件。然后在Intellij IDEA左侧的工程树中双击刚才创建的Solidity文件,会在右侧显示代码编辑区域,并输入如下图所示的Solidity代码。

尽管可以在Intellij IDEA中编写Solidity代码,也支持代码高亮显示和智能提示,但编译Solidity源代码文件仍然需要切换到终端,使用solcjs命令编译,很麻烦,所以在下一节会教大家如何将solcjs命令集成进Intellij IDEA,无需切换到终端就可以编译Solidity源代码文件。

5.将Solidity编译工具与Intellij IDEA集成

Intellij IDEA有一个扩展工具功能,可以将可执行程序与Intellij IDEA集成,也就是说,不用切换到终端,就可以执行这些程序。

现在打开偏好窗口(Windows中是设置窗口),在左侧区域找到Tools > External Tools节点,单击该节点后,会在右侧显示当前集成的扩展工具列表,默认是空。然后单击该区域下方“+”按钮,会弹出一个Create Tool窗口,在该窗口需要填写如下4个字段。

  • Name:solidity
  • Program:solcjs
  • Parameters:--abi --bin $FileName$ -o $OutputPath$
  • Working directory:$FileDir$

填写后的效果如下图所示,最后单击OK按钮创建扩展工具。

创建扩展工具应该了解如下几点。

  • Name只是用于显示的扩展工具名字,可以任意指定,甚至可以与已经存在的扩展工具重名。
  • Program指定的solcjs命令要在终端可以直接执行,否则会出现无法执行该命令的错误。所以在创建扩展工具之前,先要使用npm install -g solc命令安装solcjs。
  • Parameters表示solcjs的命令行参数,其中--abi表示将Solidity源代码文件编译成接口文件(.abi文件),--bin表示将Solidity源代码文件编译成二进制文件(.bin文件),用于发布智能合约。尽管这两类文件并不是在任何时候都需要,但为了省事,干脆将它们一起生成吧。
  • -o表示生成的目标文件(.abi和.bin文件)的路径。
  • $FileName$、$OutputPath$和$FileDir$都是Intellij IDEA提供的环境变量,$FileName$表示当前选择的文件名,$OutputPath$表示文件的输出目录,$FileDir$表示当前选择文件所在的目录。

如果是在Mac OS X下,$OutputPath$指向工程目录的out子目录,与工程相关的生成文件都放在这个目录中,目录结构与src目录相同。图3-20是out目录的结构,注意,读者机器上的目录结构可能有差异,但.abi和.bin文件都在out/production目录或其子目录中。

如果在Windows下,并不能执行solcjs文件,因为这个文件是在Mac OS X和Linux使用的,Windows下是solcjs.cmd,所以要将Program改成solcjs.cmd。而Windows版的Intellij IDEA并没有内置的$OutputPath$变量,所以可以将这个变量改成其他的值,如$FileDir$,这样以来,就会在.sol文件同一个目录生成.abi和.bin文件。所以Windows版的Intellij IDEA需要按下面的内容设置扩展工具。

  • Name:solidity
  • Program:solcjs.cmd
  • Parameters:--abi --bin $FileName$ -o $FileDir$
  • Working directory:$FileDir$

按前面的方式设置完扩展工具后,选中一个.sol文件(假设文件名是MyCalc.sol,里面的智能合约名是Calc),在Intellij IDEA的Tools > External Tools 菜单中出现了一个solidity菜单项,如图3-21所示,单击该菜单项,就会调用solcjs编译MyCalc.sol文件,并在相应的目录生成MyCalc_sol_Calc.abi和MyCalc_sol_Calc.bin文件。

其实在工程的右键菜单中也可以找到External Tools > solidity菜单项,如下图所示,单击该菜单项,效果是一样的。

原文地址:http://blog.51cto.com/androidguy/2304911

时间: 2024-10-08 02:35:52

第一行代码:以太坊(3)-使用更多的工具编写和测试智能合约的相关文章

Windows下以太坊集成开发环境(Remix-IDE)搭建与智能合约的简单应用

前面我们介绍了在以太坊平台下开发区块链私有链的过程,以及在私有链下进行挖矿的操作,而随着区块链技术的发展,区块链技术已不仅限于比特币的应用,未来将重在着眼于向其他领域的扩展推广,以此开启区块链2.0以智能合约为代表的时代.本文选用remix作为开发应用平台,配合geth客户端实现与以太坊网络的交互,下一篇文章则改用truffle和ganache搭建开发框架(这是后话). 本文分为remix-ide搭建和智能合约部署应用两部分. 一.remix-ide搭建 [准备工作] 1.安装Node.js.N

学习资料分享(Java第一行代码视频)<susmote.com>

17年买了一本书,第一行代码(JAVA),李兴华编写的. 一开始我是按照书本一页一页的啃,一个点一个点的去学,虽然当时学的有些枯燥,但里面的知识点大部分还是弄的懂,只是一次偶然,因为有点质疑书上写的(或许是我知识浅薄),所以去找跟这本书关联的文件. 进了李兴华老师的群,这时才发现自己买书时附赠了一本光碟,里面是李兴华的java培训视频,跟书上是紧密关联的,才看了几节课,就深入其中不能自拔,好吧废话少说,直接上干货. 视频分为四个部分共15章: 第一部分Java基础知识 第二部分面向对象 第三部分

《第一行代码:以太坊》已经出版,开始连载了,购买送视频课程

好消息,<第一行代码:以太坊>已经出版!!! ?●骨灰级大牛: 51CTO学院金×××讲师.CSDN.51CTO博客专家.宁哥教育创始人.著名码农李宁亲著 ● 超级学习资源:实打实赠送价值698元JavaScript视频课程 本书视频课 全套实验软件 全书案例源码 一对一解答 不定期惊喜 ● 购买地址: 当当 京东 随书赠送的视频课程1随书赠送的视频课程2 李宁老师的视频课程 购买<第一行代码:以太坊>一书,5分好评,评语不得低于20字,将截图发到[email protected]

第一行代码:以太坊(2)-使用Solidity语言开发和测试智能合约

智能合约是以太坊的核心之一,用户可以利用智能合约实现更灵活的代币以及其他DApp.不过在深入讲解如何开发智能合约之前,需要先介绍一下以太坊中用于开发智能合约的Solidity语言,以及相关的开发和测试环境. 智能合约就是运行在以太坊上的程序.客户端可以通过Web3.js API调用智能合约,而智能合约本身又可以直接访问以太坊网络,也就是说,智能合约前面连接着客户端,后面连接着以太坊网络,起到了承前启后的作用,而且通过智能合约,可以让整个以太坊网络更灵活,可控性更强.其实智能合约的作用相当于微软O

HTML5&CSS3初学者指南(1) – 编写第一行代码

介绍 网络时代已经到来.现在对人们来说,每天上网冲浪已经成为一种最为常见的行为. 在网页浏览器中输入一段文本地址,就像http://www.codeproject.com,等待一下,网页就加载到浏览器窗口中.一个典型的网页是由文本.图像和链接组成的.除去内容上的差异,不同网站的网页也具有不同的外观和感受,以实现在网络上建立自己的身份品牌的目的. 如果你也曾想要了解你屏幕上的这些网页是如何被创建出并以各式各样的方式渲染的,那么这里正是你可以了解到这些知识的地方.让我们一起走进在浏览器中创建了这么多

第一行代码

今天看打了一篇推荐<第一行代码 Android>(郭霖),是郭大神的, Android:一 简介 框架 已发布的版本 应用特色 开发环境 程序结构 Logcat工具 二 Activity 什么是活动 活动用法 intent与其用法 生命周期:onCreate() onStart() onPause() onStop() onDestory() onRestart() 活动启动模式:standard singleTop singleTask singleInstance 活动集合三 UI控件 常

历时一年,我的著作《第一行代码——Android》火爆预售!

前言 其实我当初决定开始写博客的想法挺简单的,觉得自己搞技术这么多年了,总应该要留下点什么.既然没能写出什么出色的应用,那至少也要留下点文字分享给大家,以指引在我后面的开发者们,毕竟我也从前辈们的博客那里受惠了很多. 受邀 下定决心之后我就开始了我的博客之旅,令我没想到的是,我写的文章竟然非常受大家的欢迎,短时间内就聚集了大量的人气.更令我没想到的事,在我开始写博客不久之后,人民邮电出版社图灵公司的副总编辑陈冰先生就联系上了我,希望我可以写一本关于Android开发技术的书籍! 陈冰,第一次听到

20172327 2017-2018-2 《第一行代码Android》第一章学习总结

学号 2017-2018-2 <第一行代码Android>第一章学习总结 教材学习内容总结 - Android系统架构: 1.Linux内核层 Android系统是基于Linux内核的,这一层为Android设备的各种硬件提供了底层的驱动,如显示驱动,音频驱动,照相机驱动,蓝牙驱动,Wi-Fi驱动,电源管理等. 2.系统运行底层 - 通过一些C/C++库来为Android系统提供了主要的特性支持 库名 功能 SQLite库 提供数据库的支持 OpenGL/ES库 提供3D绘图支持 Webkit

跟刷 《 Android Studio 单刷第一行代码》 记录坑

跟刷系列   Android Studio 单刷第一行代码 原帖地址http://www.cnblogs.com/DebugLife/p/4355687.html 记录自己的失误,也算是个督促自己了. 1. 坑--去除标题栏 在 Activity 的 onCreate()方法中添加 requestWindowFeature(Window.FEATURE_NO_TITLE);