内容简介:以太坊oracle:一个人们可能会在Meetups听到或其他技术活动中被抛出的非常模糊的术语。如果你不了解,你可能没有意识到区块链oracle只是一个离线数据源的专门案例,它通过响应合约中的链上事件与以太坊EVM进行交互。这可能听起来似乎挺复杂,但实际上并非如此——只需坚持几分钟。oracle的主要关注点是在合约要求时将外部数据返回合约。这些数据可以是合约开展业务所需的任何数据:存储在数据库中的客户数量,由40年历史的大型机计算的精算风险评估。在本文中,我们将关注通过易于使用的人们需要开始与外界联系,以太坊
以太坊oracle:一个人们可能会在Meetups听到或其他技术活动中被抛出的非常模糊的术语。如果你不了解,你可能没有意识到区块链oracle只是一个离线数据源的专门案例,它通过响应合约中的链上事件与以太坊EVM进行交互。这可能听起来似乎挺复杂,但实际上并非如此——只需坚持几分钟。
oracle的主要关注点是在合约要求时将外部数据返回合约。这些数据可以是合约开展业务所需的任何数据:存储在数据库中的客户数量,由40年历史的大型机计算的精算风险评估。在本文中,我们将关注通过易于使用的 Dark Sky weather forecast API 获得的请求洛杉矶温度时的数据。
Chatty合约
人们需要开始与外界联系,以太坊虚拟机也不例外。否则,它只会是另一个孤立的书呆子,坐在周围,害羞只与自己说话。EVM是一种社交动物,它让你知道它想要聊天的方式是发射一个事件(希望有人在听)。在oracle的情况下,该事件会告诉你合约想要谈论的内容,你要提供的信息以及有时你如何加入对话。如果正在运行的合约是礼貌的话,如果你想知道,它甚至可以通过让你知道你做了什么来完成对话。然而,就像脱衣舞娘和律师一样,对EVM的讨厌会花钱,所以我们将不必要的调情保持在最低限度。
无论如何,让我们开始构建我们的Weather oracle。我们使用的是Web3.js 1.0,它的工作方式与0.2.x版本略有不同。我们还使用Ganache作为testnet,它可以很好地处理Websockets连接和事件。除了Node和Javascript之外,你不需要Truffle或Embark或其他工具——oracle将为你编译和部署合约。
确保安装了最新的Solidity编译器以及solc npm软件包。并且不要忘记安装针对Dark Sky的出站HTTP调用的请求包。
如果你想在家里玩,oracle和测试客户端的完整代码位于 https://github.com/robinagist/EthereumWeatherOracle 。为了清楚起见,有一些冗余。(注意:我在Javascript和Node上有一点菜鸟,但不是软件,所以请原谅我可能已经 Python 化了你心爱的Javascript,Python和 Go 是我的主要语言。)
你还需要在 https://darksky.net 上获得一个Dark Sky API帐户。
细节
过程很简单:
- 一个帐户(EOA或合约)调用主合约上的方法,询问一些离线数据,然后回归其业务。
- 合约方法与在执行期间发出的事件相关联。
- 将通知oracle(已在合约地址处在线监听此特定事件),并开始处理数据请求。
- 处理完毕后,oracle在合约地址上运行另一种方法,完成调用帐户/合约的数据请求。有时,会从此方法发出一个事件,以便通知调用者。
合约
我们的合约很简单。除了通常的潜在交互者(与构造函数的合约)之外,我们有两种方法和两种事件。第一个被调用的方法是 request
。请求没有参数,并且它的唯一目的是在被调用时发出一个 TempRequest
事件,希望它被oracle选中。如果我们的oracle选择事件,它会调用Dark Sky获取最新数据,然后使用当前温度调用 fill
方法。 fill
方法需要无符号整数作为参数,将合约变量 temp
设置为传递的值并以当前温度作为参数触发 FilledRequest
事件。(注意:这里不需要返回值 - 我们只是为了控制台输出而在这里传递它们。)
pragma solidity ^0.4.21; contract WeatherOracle { address public owner; uint public temp; uint public timestamp; event TempRequest(address sender); event FilledRequest(uint rtemp); function constructor() public { temp = 0; owner = msg.sender; } function request() public returns (string) { emit TempRequest(msg.sender); return "sent"; } function fill(uint rtemp) public returns (uint){ temp = rtemp; emit FilledRequest(rtemp); return temp; } }
代码
只是一个标准的设置。我们宣布 abi
以便以后分配。该帐户是Ganache帐户。
要注意的一件事(特别是如果你使用过Web3.js的早期版本)是我们现在正在使用 Websockets
。这为我们提供了真正的点对点功能,并且无需轮询即可捕获事件通知。
// SETUP // let Web3 = require('web3') let fs = require('fs') let request = require('request') // using Websockets URL. Ganache works w/ Web3 1.0 and Websockets const testNetWS = "ws://127.0.0.1:7545" // create a WebsocketProvider const web3 = new Web3(new Web3.providers.WebsocketProvider(testNetWS)) // account address const account = "0xf17f52151EbEF6C7334FAD080c5704D77216b732" // we're using the Dark Sky API - get your API key at darksky.net const apiKey = "GetYourOwnKey" // using the Dark Sky API - getting the forecast, centered on LA let url= "https://api.darksky.net/forecast/"+apiKey+"/37.8267,-122.4233" // store the ABI for the contract so we can use it later let abi = null
下一段代码编译和部署合约,该合约应该与oracle位于同一目录中。成功部署和挖掘合约(返回合约地址)后,将在该地址上启动事件监听器。
// LOAD, COMPILE, DEPLOY // // load, compile and deploy the included contract (contract.sol) let c = loadCompileDeploy("contract.sol", ":WeatherOracle").then(function(address) { console.log("contract address: " + address) startListener(address) }, function(err) { console.log("didn't work. here's why: " + err) })
我们的监听器设置为从区块链时间开始以来监听任何块上的 TempRequest
事件。如果调用事件,它会记录事件数据,并使用合约地址调用 handler
来处理程序 。
// EVENT LISTENER // function startListener(address) { console.log("starting event monitoring on contract: " + address) let myContract = new web3.eth.Contract(abi, address); myContract.events.TempRequest({fromBlock: 0, toBlock: 'latest' }, function(error, event){ console.log(">>> " + event) }) .on('data', (log) => { console.log("event data: " + JSON.stringify(log, undefined, 2)) handler(address) }) .on('changed', (log) => { console.log(`Changed: ${log}`) }) .on('error', (log) => { console.log(`error: ${log}`) }) }
请求处理程序是从Dark Sky获取温度数据的函数,稍微清理一下数据,并在提供的地址处调用合约上的 fill
方法。
// REQUEST HANDLER // // handles a request event and sends the response to the contract function handler(address) { request(url, function(error, response, body) { if(error) console.log("error: " + error) console.log("status code: " + response.statusCode) let wx = JSON.parse(body) let temperature = Math.round(wx.currently.temperature) console.log("temp: " + temperature) // run the 'fill' method on the contract let MyContract = new web3.eth.Contract(abi, address); MyContract.methods.fill(temperature).call() .then(function(result) { console.log("call result: " + result) if (temperature == result) console.log("+++success+++") }, function(error) { console.log("error " + error) }) }) }
启动Oracle
- Clone the repo https://github.com/robinagist/EthereumWeatherOracle
- 配置你的 Dark Sky API密钥 和Ganache的帐户。
- 运行
npm install
- 运行
oracle:node wxoracle.js
- 启动后,从控制台输出中复制合约地址。你需要它作为测试客户端。
测试客户端
测试客户端是 wxclient.js
,与Github repo中的 wxoracle.js
位于同一目录中。启动oracle后,从控制台输出中复制联系地址,然后将其粘贴,以便将其分配给此代码底部的地址。
此外,从Ganache获取帐户并粘贴帐户。
// account address const account = "0xC5fdf4076b8F3A5357c5E395ab970B5B54098Fef" ''' ''' // cut and paste the deployed contract address const address = "contract address here"
运行测试客户端
启动一个新终端,然后在提示符下键入 node wxclient
。
目前,测试客户端编译 contract.sol
文件以获取ABI,这对于此示例来说是不必要的,但很快。我就不进入测试客户端的工作。这很简单。
如果你正在观看oracle输出,你应该看到如下内容:
在测试客户端上,从另一个终端运行:
你可以从oracle的输出中看到它从Dark Sky获得了200状态代码,并且圆形温度为53(对于LA来说太冷了)。温度存储在合约存储中,并触发另一个事件以通知监听器新的温度可用。
结论
Web3 1.0和Websockets使oracle构建成为一个快照。你不再需要构建轮询事件的系统。
其他oracle教程要么过时,要么太复杂。我试图保持这个简单的,并保持像Truffle和Embark这样的工具,所以你可以看到一切真的如何工作。oracle进行自己的部署,oracle和test客户端都编译并生成自己的ABI(虽然我会优化它,所以没有那么多的编译和剪切和粘贴)。
======================================================================
分享一些以太坊、EOS、比特币等区块链相关的交互式在线编程实战教程:
- java以太坊开发教程,主要是针对 java 和android程序员进行区块链以太坊开发的web3j详解。
- php以太坊,主要是介绍使用 php 进行智能合约开发交互,进行账号创建、交易、转账、代币开发以及过滤器和交易等内容。
- python以太坊,主要是针对python工程师使用web3.py进行区块链以太坊开发的详解。
- 以太坊入门教程,主要介绍智能合约与dapp应用开发,适合入门。
- 以太坊开发进阶教程,主要是介绍使用node.js、 mongodb 、区块链、ipfs实现去中心化电商DApp实战,适合进阶。
- C#以太坊,主要讲解如何使用C#开发基于.Net的以太坊应用,包括账户管理、状态与交易、智能合约开发与交互、过滤器和交易等。
- EOS教程,本课程帮助你快速入门EOS区块链去中心化应用的开发,内容涵盖EOS工具链、账户与钱包、发行代币、智能合约开发与部署、使用代码与智能合约交互等核心知识点,最后综合运用各知识点完成一个便签DApp的开发。
- java比特币开发教程,本课程面向初学者,内容即涵盖比特币的核心概念,例如区块链存储、去中心化共识机制、密钥与脚本、交易与UTXO等,同时也详细讲解如何在Java代码中集成比特币支持功能,例如创建地址、管理钱包、构造裸交易等,是Java工程师不可多得的比特币开发学习课程。
- php比特币开发教程,本课程面向初学者,内容即涵盖比特币的核心概念,例如区块链存储、去中心化共识机制、密钥与脚本、交易与UTXO等,同时也详细讲解如何在Php代码中集成比特币支持功能,例如创建地址、管理钱包、构造裸交易等,是Php工程师不可多得的比特币开发学习课程。
- tendermint区块链开发详解 ,本课程适合希望使用tendermint进行区块链开发的工程师,课程内容即包括tendermint应用开发模型中的核心概念,例如ABCI接口、默克尔树、多版本状态库等,也包括代币发行等丰富的实操代码,是go语言工程师快速入门区块链开发的最佳选择。
汇智网原创翻译,转载请标明出处。这里是 使用Web3.js 1.0构建以太坊Oracle
以上就是本文的全部内容,希望本文的内容对大家的学习或者工作能带来一定的帮助,也希望大家多多支持 码农网
猜你喜欢:- 在 Android Studio 里使用构建分析器提升构建性能
- 使用 Docker 构建
- 使用 webpack 构建应用
- 使用Dockerfile构建镜像
- 使用模式构建:总结
- 使用 AutoAI 自动构建模型
本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。
HTML 压缩/解压工具
在线压缩/解压 HTML 代码
Markdown 在线编辑器
Markdown 在线编辑器