繁体   English   中英

有没有比通过节点单独调用多个 API 更简单的方法从 Chainlink 获取去中心化数据?

[英]Is there a simpler way to get decentralized data from Chainlink than doing separate multiple API calls through nodes?

我想在我正在 Remix 中测试的 Solidity 项目中以美元获取 ETH 的价格馈送数据。 我使用Chainlink请求数据作为指导,以便我的数据可以去中心化。

现在,我向具有不同 URL 的不同节点发出 3 个链链接请求,然后计算三个响应的中值以获得去中心化的价格。 看起来这是一种相当乏味的方法,有没有更简单的方法来做到这一点?

 function requestEthereumPrice(address _address, bytes32 job_id, string url) 
    public
    onlyOwner
  {
    Chainlink.Request memory req = buildChainlinkRequest(stringToBytes32(JOB_ID), address(this), this.fulfill.selector);
    req.add("get", url);
    req.add("path", "USD");
    req.addInt("times", 100);
    sendChainlinkRequestTo(_address, req, ORACLE_PAYMENT);
  }

  function multipleData() public{
      requestEthereumPrice(ORACLE_ADDRESS, JOB_ID);
      requestEthereumPrice(ORACLE2_ADDRESS, JOB2_ID);
      requestEthereumPrice(ORACLE3_ADDRESS, JOB3_ID);
  }

 function fulfill(bytes32 _requestId, uint256 _price)
    public
    // Use recordChainlinkFulfillment to ensure only the requesting oracle can fulfill
    recordChainlinkFulfillment(_requestId)
  {
    currentPriceList[index] = _price;
    index = (index + 1) & 3
    currentPrice = median();
  }

欢迎来到 SO!

您的方法是执行此操作的最“蛮力”方法,它有效。 但是,目前有两种方法可以改善这一点。

1. 使用参考数据合约

参考数据合约是一种合约,它具有多个受信任的去中心化 Chainlink 节点,将来自不同数据提供者的价格更新发送到区块链上的一个参考点,供任何人查询。 您的特定货币对ETH/USD是当前支持的货币对之一。 获取该数据的代码如下所示:

pragma solidity ^0.6.0;

import "github.com/smartcontractkit/chainlink/evm-contracts/src/v0.6/dev/AggregatorInterface.sol";

contract ReferenceConsumer {
  AggregatorInterface internal ref;

// Use 0xF79D6aFBb6dA890132F9D7c355e3015f15F3406F as the address of the ETH/USD pair
  constructor(address _aggregator) public {
    ref = AggregatorInterface(_aggregator);
  }

  function getLatestAnswer() public view returns (int256) {
    return ref.latestAnswer();
  }

  function getLatestTimestamp() public view returns (uint256) {
    return ref.latestTimestamp();
  }

您可以在feeds 文档中找到当前支持的 feeds 列表,或者在他们的feeds explorer中看起来更好看的页面。

2. 使用预协调器合约

如果你想要一个盒装的解决方案,第 1 个很好,但是,也许你不同意 Chainlink 的节点选择,并且想要你自己的实现(这增加了去中心化。)。 您的解决方案是选择您自己的节点网络的一种方式。

precoordinator 合约允许您像上面那样进行正常的buildChainlinkRequest ,但会为您将其分散到多个节点。 要创建它,首先部署一个合约:

pragma solidity ^0.5.0;

import "github.com/smartcontractkit/chainlink/evm-contracts/src/v0.5/PreCoordinator.sol";

然后,您可以从合约中调用createServiceAgreement ,该合约接受参数uint256 _minResponses, address[] _oracles, address[]_jobIds, uint256[] _payments 您可以使用 remix 来部署它们。 预协调员

从预协调员合同部署服务协议后,它将为您提供服务协议 ID。 您可以通过检查日志或查看诸如 etherscan 之类的内容并转到topic 1以查看 ID 来找到此 ID。 这是一个例子

有了precoordinator的地址和服务协议后,就可以使用precoordinator合约的地址为oracle地址,服务协议为jobId。 这意味着您可以调用大量节点:

function requestEthereumPrice(address precoordinator_address, bytes32 service_agreement, string url) 
    public
    onlyOwner
  {
    Chainlink.Request memory req = buildChainlinkRequest(service_agreement, address(this), this.fulfill.selector);
    req.add("get", url);
    req.add("path", "USD");
    req.addInt("times", 100);
    sendChainlinkRequestTo(precoordinator_address, req, ORACLE_PAYMENT);
  }

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM