Version 1.0.0
GitHub
Get Support

Oracle Service

Overview

The Oracle Service provides a secure bridge between the Neo N3 blockchain and external data sources. It enables smart contracts to access real-world data such as market prices, weather information, sports results, and other off-chain data that would otherwise be inaccessible from within the blockchain.

Key Features

TEE Protection

All oracle operations run within a Trusted Execution Environment (TEE), ensuring data integrity and confidentiality.

Flexible Data Sources

Connect to almost any API or data source, including REST APIs, databases, and streaming services.

Custom Data Transformations

Transform and process the data before it reaches your smart contract to ensure it's in the right format.

Multiple Consensus Mechanisms

Configure your oracle to use different consensus mechanisms for data validation, including majority voting and threshold signatures.

Architecture

The Oracle Service consists of the following components:

  1. Data Source Manager: Manages connections to external data sources
  2. Request Processor: Handles oracle data requests
  3. Data Validator: Validates and formats data from external sources
  4. Blockchain Integration: Delivers data to Neo N3 contracts
  5. Storage Layer: Records request history and data for auditing
  6. TEE Runner: Executes data retrieval in a secure environment

Request Flow

The service follows this basic flow for delivering data:

  1. Request Submission:
    • Smart contract or user requests data via the API
    • Request includes data source, parameters, and callback information
  2. Data Collection:
    • Oracle service retrieves data from the specified external source
    • Data is validated and formatted according to request parameters
  3. On-chain Delivery:
    • Validated data is delivered to the requesting contract
    • Transaction is signed and sent to the blockchain
  4. Verification:
    • Smart contract can verify the data integrity
    • Data provenance is recorded for auditing

Supported Data Sources

The service supports multiple types of data sources:

  • REST APIs: HTTP/HTTPS endpoints with JSON or XML responses
  • WebSockets: Real-time data streams
  • File Systems: CSV, JSON, or XML files
  • IPFS: Decentralized file system
  • Databases: SQL or NoSQL databases
  • Custom Sources: Extendable interface for custom data sources

Authentication Methods

The service supports various authentication methods for external APIs:

  • API Key authentication
  • OAuth 2.0
  • JWT tokens
  • Basic authentication
  • Custom authentication headers

Security Best Practice

All API credentials and authentication tokens are securely stored in the TEE and never exposed to the public. Use the Secrets Service to manage your API credentials.

Smart Contract Integration

To integrate the Oracle Service with your Neo N3 smart contracts, you need to implement a specific interface that can handle callbacks from the Oracle Service.

Example Oracle Consumer Contract

1// Oracle consumer contract interface
2type OracleConsumer interface {
3    // Request data from the oracle service
4    RequestData(requestID uint64, url string, path string, callback string) bool
5    
6    // Callback for receiving the data
7    ReceiveData(requestID uint64, data []byte, proof []byte) bool
8    
9    // Get the last received data
10    GetLastData() (data []byte, timestamp uint64)
11}

Once you have implemented this interface, your contract can request data from the Oracle Service and receive the results via a callback.

API Endpoints

Admin API

  • GET /api/v1/oracles - List all oracle data feeds
  • GET /api/v1/oracles/:id - Get details of a specific oracle
  • POST /api/v1/oracles - Create a new oracle data feed
  • PUT /api/v1/oracles/:id - Update an oracle data feed
  • DELETE /api/v1/oracles/:id - Delete an oracle data feed
  • GET /api/v1/oracles/:id/requests - List requests for an oracle
  • GET /api/v1/oracles/requests/:id - Get details of a specific request

Public API

  • POST /api/v1/public/oracles/request - Submit a new oracle data request
  • GET /api/v1/public/oracles/request/:id - Get the status and result of a request
  • GET /api/v1/public/oracles/data/:id - Get historically stored oracle data

Creating an Oracle Request

Here's an example of creating a new oracle request:

1{
2  "url": "https://api.coingecko.com/api/v3/simple/price?ids=neo&vs_currencies=usd",
3  "method": "GET",
4  "headers": {
5    "Content-Type": "application/json"
6  },
7  "path": "$.neo.usd",
8  "transform": "parseInt(data * 100)",
9  "callback_address": "0x1234567890abcdef1234567890abcdef12345678",
10  "callback_method": "ReceivePrice",
11  "gas_fee": 0.5
12}

Request Parameters

Oracle requests support the following parameters:

  • url: The API endpoint URL to fetch data from
  • method: HTTP method (GET, POST, etc.)
  • headers: Custom HTTP headers for the request
  • body: Request body for POST/PUT requests
  • auth_type: Authentication type (API_KEY, OAUTH, BASIC, etc.)
  • auth_params: Authentication parameters (keys, tokens, etc.)
  • path: JSONPath or XPath expression to extract specific data
  • transform: Transformation function to apply to the data
  • callback_address: Neo N3 contract address to receive the data
  • callback_method: Method to call with the data
  • gas_fee: GAS fee to pay for the callback transaction

JSONPath Examples

The Oracle Service uses JSONPath expressions to extract specific data from complex JSON responses. Here are some examples:

1// Simple price data
2$.neo.usd
3
4// First item in an array
5$.results[0].price
6
7// Multiple data points
8$.data.markets[?(@.symbol=="NEO")].price
9
10// Complex filtering
11$.data.pairs[?(@.base=="NEO" && @.quote=="USD")].price

Security Features

  • All oracle operations execute within the TEE environment
  • Data signatures ensure integrity from source to blockchain
  • Rate limiting prevents API abuse and DoS attacks
  • Input validation prevents injection attacks
  • Secure credential storage for API authentication
  • Detailed audit logs for all requests and responses

Performance Considerations

The Oracle Service includes several optimizations for performance:

  • Connection pooling for efficient API requests
  • Caching of frequently requested data
  • Batched blockchain transactions for multiple data points
  • Automatic retry mechanisms for failed requests
  • Prioritization of time-sensitive requests

Use Cases

Financial Data

Token prices, exchange rates, interest rates, and other financial metrics.

Sports & Gaming

Sports results, statistics, and real-time game data for betting and gaming platforms.

Weather Data

Current conditions, forecasts, and historical data for weather-dependent applications.

IoT Integration

Data from IoT sensors and devices to trigger smart contract actions.

Social Media

Monitor for specific events, mentions, or trends on social platforms.

Supply Chain

Track and verify shipments, inventory levels, and logistics information.

Monitoring and Metrics

The service provides comprehensive monitoring capabilities:

  • Request volume and success rate by data source
  • Response time for external APIs
  • Data validation success rates
  • Gas usage for on-chain operations
  • Error rates by source and type
  • Request distribution by client

These metrics are exposed via Prometheus endpoints and can be visualized using Grafana dashboards.

Example: Creating a Price Oracle

Let's create a simple price oracle that fetches Neo token price from CoinGecko and reports it to a smart contract:

1. Create an Oracle Definition

1{
2  "name": "NeoPriceOracle",
3  "description": "Neo/USD price oracle using CoinGecko API",
4  "source": {
5    "type": "rest",
6    "url": "https://api.coingecko.com/api/v3/simple/price?ids=neo&vs_currencies=usd",
7    "method": "GET",
8    "headers": {
9      "Accept": "application/json"
10    }
11  },
12  "extraction": {
13    "path": "$.neo.usd",
14    "transform": "parseFloat(data) * 100000000" // Convert to integer with 8 decimal places
15  },
16  "schedule": {
17    "type": "interval",
18    "interval": 3600 // Update hourly
19  },
20  "delivery": {
21    "contract_hash": "0x1234567890abcdef1234567890abcdef12345678",
22    "method": "UpdatePrice",
23    "gas": 1.0
24  }
25}

2. Create a Consumer Smart Contract

1using Neo.SmartContract.Framework;
2using Neo.SmartContract.Framework.Services;
3using System;
4using System.ComponentModel;
5
6namespace NeoPriceConsumer
7{
8    [DisplayName("PriceConsumer")]
9    [ManifestExtra("Author", "Neo Service Layer")]
10    [ManifestExtra("Description", "Sample Oracle Price Consumer")]
11    public class PriceConsumer : SmartContract
12    {
13        // Price storage key
14        private static readonly StorageKey PriceKey = new StorageKey("price");
15        
16        // Notification event when price is updated
17        [DisplayName("PriceUpdated")]
18        public static event Action<BigInteger> OnPriceUpdated;
19        
20        // Method called by the Oracle Service
21        public static void UpdatePrice(BigInteger price)
22        {
23            // Only allow the Oracle Service to call this method
24            if (!Runtime.CheckWitness(Oracle.OracleAddress))
25                throw new Exception("Unauthorized caller");
26                
27            // Store the price
28            Storage.Put(PriceKey, price);
29            
30            // Emit event
31            OnPriceUpdated(price);
32        }
33        
34        // Get the current price
35        public static BigInteger GetPrice()
36        {
37            return (BigInteger)Storage.Get(PriceKey);
38        }
39    }
40}

3. Query the Oracle Data

Once the oracle is set up and reporting data to your contract, you can query the data:

1// Using Neo SDK to call the consumer contract
2const { rpc, sc } = require('@cityofzion/neon-js');
3
4const rpcClient = new rpc.RPCClient('https://n3seed1.ngd.network:10332');
5const scriptHash = '0x1234567890abcdef1234567890abcdef12345678'; // Your contract hash
6
7async function getNeoPrice() {
8  const result = await rpcClient.invokeFunction(scriptHash, 'GetPrice');
9  
10  if (result.state === 'HALT') {
11    const price = parseInt(result.stack[0].value) / 100000000; // Convert back to decimal
12    console.log(`Current Neo price: $${price.toFixed(2)}`);
13    return price;
14  } else {
15    console.error('Failed to get price:', result);
16    return null;
17  }
18}
19
20getNeoPrice();

Advanced Features

Multi-Source Oracles

For critical data points, you can create multi-source oracles that aggregate data from multiple providers:

1{
2  "name": "Neo Multi-Source Price Oracle",
3  "sources": [
4    {
5      "name": "CoinGecko",
6      "url": "https://api.coingecko.com/api/v3/simple/price?ids=neo&vs_currencies=usd",
7      "path": "$.neo.usd",
8      "weight": 1.0
9    },
10    {
11      "name": "Binance",
12      "url": "https://api.binance.com/api/v3/ticker/price?symbol=NEOUSDT",
13      "path": "$.price",
14      "weight": 1.0
15    },
16    {
17      "name": "Huobi",
18      "url": "https://api.huobi.pro/market/detail/merged?symbol=neousdt",
19      "path": "$.tick.close",
20      "weight": 1.0
21    }
22  ],
23  "aggregation": "median", // Options: mean, median, mode, weighted_average
24  "filtering": {
25    "outlier_threshold": 3.0, // Standard deviations for outlier detection
26    "min_sources": 2 // Minimum sources needed for a valid result
27  }
28}

Custom Data Transformations

You can use JavaScript transformations to process data before it's sent to the blockchain:

1// Example transformation function
2function transform(data) {
3  // Convert string to float
4  const price = parseFloat(data);
5  
6  // Apply scaling factor for integer representation (8 decimal places)
7  const scaledPrice = Math.round(price * 100000000);
8  
9  // Validate the result
10  if (isNaN(scaledPrice) || scaledPrice <= 0) {
11    throw new Error('Invalid price data');
12  }
13  
14  return scaledPrice;
15}

Security Considerations

Data Source Security

  • Always use HTTPS endpoints
  • Store credentials securely using the Secrets Service
  • Implement regular rotation of API keys
  • Monitor for unusual access patterns

On-chain Security

  • Implement data validity checks in your contract
  • Use rate limiting for updates
  • Verify the Oracle Service signature
  • Set appropriate gas limits

API Reference

For a complete API reference, see the Oracle API Documentation.

Next Steps

Was this page helpful?

Edit this page on GitHub