From 9cc034af9b8d4a59cb46c4e6fe2b75af837134f3 Mon Sep 17 00:00:00 2001 From: Roman Khimov Date: Tue, 6 Apr 2021 22:49:58 +0300 Subject: [PATCH] examples: add a perfect oracle example --- examples/README.md | 1 + examples/oracle/oracle.go | 36 ++++++++++++++++++++++++++++++++++++ examples/oracle/oracle.yml | 3 +++ 3 files changed, 40 insertions(+) create mode 100644 examples/oracle/oracle.go create mode 100644 examples/oracle/oracle.yml diff --git a/examples/README.md b/examples/README.md index 362aa9318..03a8e2927 100644 --- a/examples/README.md +++ b/examples/README.md @@ -25,6 +25,7 @@ See the table below for the detailed examples description. | [engine](engine) | This contract demonstrates how to use `runtime` interop package which implements an API for `System.Runtime.*` NEO system calls. Please, refer to the `runtime` [package documentation](../pkg/interop/doc.go) for details. | | [events](events) | The contract shows how execution notifications with the different arguments types can be sent with the help of `runtime.Notify` function of the `runtime` interop package. Please, refer to the `runtime.Notify` [function documentation](../pkg/interop/runtime/runtime.go) for details. | | [iterator](iterator) | This example describes a way to work with NEO iterators. Please, refer to the `iterator` [package documentation](../pkg/interop/iterator/iterator.go) for details. | +| [oracle](oracle) | Oracle demo contract exposing two methods that you can use to process URLs. It uses oracle native contract, see [interop package documentation](../pkg/interop/native/oracle/oracle.go) also. | | [runtime](runtime) | This contract demonstrates how to use special `_initialize` and `_deploy` methods. See the [compiler documentation](../docs/compiler.md#vm-api-interop-layer ) for methods details. It also shows the pattern for checking owner witness inside the contract with the help of `runtime.CheckWitness` interop [function](../pkg/interop/runtime/runtime.go). | | [storage](storage) | The contract implements API for basic operations with a contract storage. It shows hos to use `storage` interop package. See the `storage` [package documentation](../pkg/interop/storage/storage.go). | | [timer](timer) | The idea of the contract is to count `tick` method invocations and destroy itself after the third invocation. It shows how to use `contract.Call` interop function to call, update (migrate) and destroy the contract. Please, refer to the `contract.Call` [function documentation](../pkg/interop/contract/contract.go) | diff --git a/examples/oracle/oracle.go b/examples/oracle/oracle.go new file mode 100644 index 000000000..dcaefb614 --- /dev/null +++ b/examples/oracle/oracle.go @@ -0,0 +1,36 @@ +package oraclecontract + +import ( + "github.com/nspcc-dev/neo-go/pkg/interop/native/oracle" + "github.com/nspcc-dev/neo-go/pkg/interop/native/std" + "github.com/nspcc-dev/neo-go/pkg/interop/runtime" +) + +// Request does an oracle request for the URL specified. It adds minimum +// response fee which should suffice for small requests. The data from this +// URL is subsequently processed by OracleCallback function. This request +// has no JSONPath filters or user data. +func Request(url string) { + oracle.Request(url, nil, "oracleCallback", nil, oracle.MinimumResponseGas) +} + +// FilteredRequest is similar to Request but allows you to specify JSONPath filter +// to run against data got from the url specified. +func FilteredRequest(url string, filter []byte) { + oracle.Request(url, filter, "oracleCallback", nil, oracle.MinimumResponseGas) +} + +// OracleCallback is called by Oracle native contract when request is finished. +// It either throws an error (if the result is not successful) or logs the data +// got as a result. +func OracleCallback(url string, data interface{}, code int, res []byte) { + // This function shouldn't be called directly, we only expect oracle native + // contract to be calling it. + if string(runtime.GetCallingScriptHash()) != oracle.Hash { + panic("not called from oracle contract") + } + if code != oracle.Success { + panic("request failed for " + url + " with code " + std.Itoa(code, 10)) + } + runtime.Log("result for " + url + ": " + string(res)) +} diff --git a/examples/oracle/oracle.yml b/examples/oracle/oracle.yml new file mode 100644 index 000000000..6e67ec888 --- /dev/null +++ b/examples/oracle/oracle.yml @@ -0,0 +1,3 @@ +name: "Oracle example" +supportedstandards: [] +events: