Operator
Oracles must deploy an on-chain contract to handle requests made through the LINK token (Read Basic Request Model to learn more).
When the Basic Request model was introduced, node operators had to deploy Oracle contracts. However, these come with some limitations, and soon, we introduced operator contracts.
In addition to replacing oracle contracts, operator contracts come with additional features that add more security and flexibility for node operators.
Features
Multi-word Response
In the EVM architecture, a word is made up of 32 bytes. One limitation of the Oracle.sol contract is that it limits responses to requests to 32 bytes. Operator.sol doesn’t have the same limitation as it supports a response made of multiple EVM words.
Factory deployment
To deploy an Oracle contract, each node operator has to manually compile and deploy Oracle.sol. The vast number of Solidity versions and steps involved in verifying the contract made it difficult for a client to verify that the deployed contract had not been tampered with. To fix this, node operators can use a factory to deploy an instance of the operator contract. Moreover, the factory exposes a getter for clients to check if it deployed a specific operator contract address.
Distributing funds to multiple addresses
A common pain point of node operators is keeping their addresses funded. Operator’s distributeFunds
method allows node operators to fund multiple addresses in a single transaction.
Flexibility and Security
By using multiple External-owned accounts(EOA) on Chainlink nodes and forwarder contracts, node operators can set up different transaction-sending strategies.
As discussed in the forwarder contracts page:
- Chainlink nodes’ EOAs are hot wallets that fulfill requests.
- These EOAs can be associated with one or multiple forwarder contracts. The forwarder’s owner must whitelist them to call the forward function. One operator contract owns one or multiple forwarder contracts.
- Node operators manage their forwarder contracts through operator contracts. They use a secure wallet such as hardware or a multisig wallet as the operator’s owner account.
API Reference
The operator contract inherits AuthorizedReceiver and ConfirmedOwnerWithProposal. Read AuthorizedReceiver and ConfirmedOwnerWithProposal API references.
Methods
oracleRequest
function oracleRequest(address sender, uint256 payment, bytes32 specId, address callbackAddress, bytes4 callbackFunctionId, uint256 nonce, uint256 dataVersion, bytes data) external
Creates the Chainlink request. This is backwards compatible API with Oracle.sol contracts, but the behavior changes because callbackAddress
is assumed to be the same as the request sender.
Parameters
Name | Type | Description |
---|---|---|
sender | address | The sender of the request |
payment | uint256 | The amount of payment given (specified in wei) |
specId | bytes32 | The Job Specification ID |
callbackAddress | address | The consumer of the request |
callbackFunctionId | bytes4 | The callback function ID for the response |
nonce | uint256 | The nonce sent by the requester |
dataVersion | uint256 | The specified data version |
data | bytes | The extra request parameters |
operatorRequest
function operatorRequest(address sender, uint256 payment, bytes32 specId, bytes4 callbackFunctionId, uint256 nonce, uint256 dataVersion, bytes data) external
Creates the Chainlink request. Stores the hash of the params as the on-chain commitment for the request. Emits OracleRequest event for the Chainlink node to detect.
Parameters
Name | Type | Description |
---|---|---|
sender | address | The sender of the request |
payment | uint256 | The amount of payment given (specified in wei) |
specId | bytes32 | The Job Specification ID |
callbackFunctionId | bytes4 | The callback function ID for the response |
nonce | uint256 | The nonce sent by the requester |
dataVersion | uint256 | The specified data version |
data | bytes | The extra request parameters |
fulfillOracleRequest
function fulfillOracleRequest(bytes32 requestId, uint256 payment, address callbackAddress, bytes4 callbackFunctionId, uint256 expiration, bytes32 data) external returns (bool)
Called by the Chainlink node to fulfill requests. Given params must hash back to the commitment stored from oracleRequest
. Will call the callback address’ callback function without bubbling up error checking in a require
so that the node can get paid. Emits OracleResponse event.
Parameters
Name | Type | Description |
---|---|---|
requestId | bytes32 | The fulfillment request ID that must match the requester’s |
payment | uint256 | The payment amount that will be released for the oracle (specified in wei) |
callbackAddress | address | The callback address to call for fulfillment |
callbackFunctionId | bytes4 | The callback function ID to use for fulfillment |
expiration | uint256 | The expiration that the node should respond by before the requester can cancel |
data | bytes32 | The data to return to the consuming contract |
Return Values
Name | Type | Description |
---|---|---|
bool | Status if the external call was successful |
fulfillOracleRequest2
function fulfillOracleRequest2(bytes32 requestId, uint256 payment, address callbackAddress, bytes4 callbackFunctionId, uint256 expiration, bytes data) external returns (bool)
Called by the Chainlink node to fulfill requests with multi-word support. Given params must hash back to the commitment stored from oracleRequest
. Will call the callback address’ callback function without bubbling up error checking in a require
so that the node can get paid. Emits OracleResponse event.
Parameters
Name | Type | Description |
---|---|---|
requestId | bytes32 | The fulfillment request ID that must match the requester’s |
payment | uint256 | The payment amount that will be released for the oracle (specified in wei) |
callbackAddress | address | The callback address to call for fulfillment |
callbackFunctionId | bytes4 | The callback function ID to use for fulfillment |
expiration | uint256 | The expiration that the node should respond by before the requester can cancel |
data | bytes | The data to return to the consuming contract |
Return Values
Name | Type | Description |
---|---|---|
bool | Status if the external call was successful |
transferOwnableContracts
function transferOwnableContracts(address[] ownable, address newOwner) external
Transfer the ownership of ownable contracts. This is primarily intended for authorized forwarders but could possibly be extended to work with future contracts.
Parameters
Name | Type | Description |
---|---|---|
ownable | address[] | list of addresses to transfer |
newOwner | address | address to transfer ownership to |
acceptOwnableContracts
function acceptOwnableContracts(address[] ownable) public
Accept the ownership of an ownable contract. This is primarily intended for authorized forwarders but could possibly be extended to work with future contracts. Emits OwnableContractAccepted event.
Must be the pending owner on the contract
Parameters
Name | Type | Description |
---|---|---|
ownable | address[] | list of addresses of Ownable contracts to accept |
setAuthorizedSendersOn
function setAuthorizedSendersOn(address[] targets, address[] senders) public
Sets the fulfillment permission for senders
on targets
. Emits TargetsUpdatedAuthorizedSenders event.
Parameters
Name | Type | Description |
---|---|---|
targets | address[] | The addresses to set permissions on |
senders | address[] | The addresses that are allowed to send updates |
acceptAuthorizedReceivers
function acceptAuthorizedReceivers(address[] targets, address[] senders) external
Accepts ownership of ownable contracts and then immediately sets the authorized sender list on each of the newly owned contracts. This is primarily intended for authorized forwarders but could possibly be extended to work with future contracts.
Parameters
Name | Type | Description |
---|---|---|
targets | address[] | The addresses to set permissions on |
senders | address[] | The addresses that are allowed to send updates |
withdraw
function withdraw(address recipient, uint256 amount) external
Allows the node operator to withdraw earned LINK to a given address recipient
.
The owner of the contract can be another wallet and does not have to be a Chainlink node
Parameters
Name | Type | Description |
---|---|---|
recipient | address | The address to send the LINK token to |
amount | uint256 | The amount to send (specified in wei) |
withdrawable
function withdrawable() external view returns (uint256)
Displays the amount of LINK that is available for the node operator to withdraw.
We use 1
in place of 0 in storage
Return Values
Name | Type | Description |
---|---|---|
uint256 | The amount of withdrawable LINK on the contract |
ownerForward
function ownerForward(address to, bytes data) external
Forward a call to another contract.
Only callable by the owner
Parameters
Name | Type | Description |
---|---|---|
to | address | address |
data | bytes | to forward |
ownerTransferAndCall
function ownerTransferAndCall(address to, uint256 value, bytes data) external returns (bool success)
Interact with other LinkTokenReceiver contracts by calling transferAndCall.
Parameters
Name | Type | Description |
---|---|---|
to | address | The address to transfer to. |
value | uint256 | The amount to be transferred. |
data | bytes | The extra data to be passed to the receiving contract. |
Return Values
Name | Type | Description |
---|---|---|
success | bool | bool |
distributeFunds
function distributeFunds(address payable[] receivers, uint256[] amounts) external payable
Distribute funds to multiple addresses using ETH sent to this payable function.
Array length must be equal, ETH sent must equal the sum of amounts. A malicious receiver could cause the distribution to revert, in which case it is expected that the address is removed from the list.
Parameters
Name | Type | Description |
---|---|---|
receivers | address payable[] | list of addresses |
amounts | uint256[] | list of amounts |
cancelOracleRequest
function cancelOracleRequest(bytes32 requestId, uint256 payment, bytes4 callbackFunc, uint256 expiration) external
Allows recipient to cancel requests sent to this oracle contract. Will transfer the LINK sent for the request back to the recipient address. Given params must hash to a commitment stored on the contract in order for the request to be valid. Emits CancelOracleRequest event.
Parameters
Name | Type | Description |
---|---|---|
requestId | bytes32 | The request ID |
payment | uint256 | The amount of payment given (specified in wei) |
callbackFunc | bytes4 | The requester’s specified callback function selector |
expiration | uint256 | The time of the expiration for the request |
cancelOracleRequestByRequester
function cancelOracleRequestByRequester(uint256 nonce, uint256 payment, bytes4 callbackFunc, uint256 expiration) external
Allows requester to cancel requests sent to this oracle contract. Will transfer the LINK sent for the request back to the recipient address. Given params must hash to a commitment stored on the contract in order for the request to be valid. Emits CancelOracleRequest event.
Parameters
Name | Type | Description |
---|---|---|
nonce | uint256 | The nonce used to generate the request ID |
payment | uint256 | The amount of payment given (specified in wei) |
callbackFunc | bytes4 | The requester’s specified callback function selector |
expiration | uint256 | The time of the expiration for the request |
getChainlinkToken
function getChainlinkToken() public view returns (address)
Returns the address of the LINK token
This is the public implementation for chainlinkTokenAddress, which is an internal method of the ChainlinkClient contract.
Events
OracleRequest
event OracleRequest(bytes32 specId, address requester, bytes32 requestId, uint256 payment, address callbackAddr, bytes4 callbackFunctionId, uint256 cancelExpiration, uint256 dataVersion, bytes data)
CancelOracleRequest
event CancelOracleRequest(bytes32 requestId)
OracleResponse
event OracleResponse(bytes32 requestId)
OwnableContractAccepted
event OwnableContractAccepted(address acceptedContract)
TargetsUpdatedAuthorizedSenders
event TargetsUpdatedAuthorizedSenders(address[] targets, address[] senders, address changedBy)