NEAR Protocol Web3 provider. Use it to connect your Ethereum frontend or Truffle to NEAR Protocol.
$ npm install near-web3-provider
Tests require running a local nearcore
.
Install Rustup:
$ curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh
Add wasm target to your toolchain:
$ rustup target add wasm32-unknown-unknown
Install and run NEARCore using Docker:
$ git clone https://github.com/nearprotocol/nearcore
$ cd nearcore
$ make docker-nearcore
$ ./scripts/start_localnet.py
To run NEARcore without Docker
$ git clone https://github.com/nearprotocol/nearcore
$ cd nearcore
$ ./scripts/start_localnet.py --nodocker
Run tests
$ npm run test
Tests currently take ~50 seconds to run.
Node > 11.0
You can use this provider wherever a Web3 provider is needed.
const { NearProvider, nearlib } = require('near-web3-provider');
const nearNetworkId = '<local, default, test, etc>'; // default is 'default'
const accountId = '<account id to use for tx>';
const keyStore = new nearlib.keyStores.<one of keyStores>;
const web = new Web3();
web.setProvider(new NearProvider("<url to NEAR RPC>", keyStore, accountId, nearNetworkId));
web.eth.net.isListening();
Add to your truffle-config.json
:
// Import NearProvider and nearlib
const { NearProvider, nearlib } = require('near-web3-provider');
// Specify which NEAR network to use
const nearNetworkId = '<local, default, test, etc>';
// If developing against a local node, use http://localhost:3030
const url = 'https://rpc.nearprotocol.com';
// Specify where to store keys
const keyDir = 'neardev';
// Use standard near-shell structure for storing keys. See note below for other options.
const keyStore = new nearlib.keyStores.UnencryptedFileSystemKeyStore(keyDir);
// Account ID
const accountId = 'test.account';
module.exports = {
networks: {
near: {
network_id: "99",
skipDryRun: true,
provider: function() {
return new NearProvider(url, keyStore, accountId, nearNetworkId)
},
}
}
}
See key store documentation for other options.
NEAR Protocol is a sharded, proof-of-stake blockchain. Keeping that in mind, some Ethereum concepts are naturally not shared with NEAR; for example, there is no concept of uncle blocks, pending blocks, or block difficulty.
As a sharded blockchain, the structure of NEAR blocks is also different. In Ethereum, blocks have transactions. In NEAR, blocks have chunks, and chunks have transactions.
near-web3-provider
has been adapted to follow the Ethereum JSON RPC API and its web3
equivalents as closely as possible. Where there are no equivalents, empty values have been passed through. Other return values have been adapted to account for the difference in block structure (for example, the root of the transaction trie comes from a chunk rather than a block).
Mining, hashrates, ssh,
and db
methods are not supported.
-
Methods that have an extra default block parameter will function as
latest
, regardless of the actual argument. This is a Near RPC limitation. -
eth_call
does not supportfrom
orvalue
arguments. This is a Near RPC limitation. -
eth_estimateGas
will always return0x0
. Near RPC does not seem to support gas estimation for calls. -
Many fields in Ethereum data structures do not have a direct correspondance to Near data structures. Some attributes of transaction and block objects will be unreliable.
-
Some fields are just unimplemented. For example, tx receipts currently always have a
0x1
status, regardless of the success of the transaction. -
Some fields are just unimplemented. Always consult implementation in
near_to_eth_objects.js
. E.g. tx index is constant, and not reliable. -
Some calls, like
eth_getTransactionByBlockHashAndIndex
have no sensible correspondance to Near block structure
Unless specified, NearProvider returns the values specified in the web3 documentation for each method.
If a method has no direct translation, an Unsupported method
error is returned.
Near uses base58
while Ethereum uses Keccak
. This necessitates the need to convert between the two. With the exception of transaction hashes, Near hashes are converted to Ethereum-compatible hashes when using web3
.
-
blockHash
- a block hash is the hash equivalent of a Near block hash (denoted inbase58
) -
transactionHash
- a transaction hash is the combination of a Near transaction hash (inbase58
) concatenanted with the accountId of the transaction's sender, and separated by:
<base58TxHash>:<senderAccountId>
-
gas
- Gas is denominated in yoctoNEAR -
value
- Transaction values/amounts are denominated in yoctoNEAR -
to
,from
,address
- Addresses are the EVM hash of a Near AccountId
web3.eth.getCoinbase
web3.eth.isMining
web3.eth.getHashrate
web3.eth.getBlockUncleCount
web3.eth.getUncle
web3.eth.getPendingTransactions
web3.eth.sign
web3.eth.estimateGas
web3.eth.getPastLogs
web3.eth.getWork
web3.eth.submitWork
web3.eth.requestAccounts
web3.eth.getChainId
web3.eth.getNodeInfo
web3.eth.getProof
web3.eth.getProtocolVersion([callback])
Returns the Near protocol version of the node.
Promise
returns String
: the protocol version.
- Returns the Near protocol version instead of the Ethereum protocol version
web3.eth.isSyncing
Checks if the node is currently syncing and returns either a syncing object, or false.
Promise
returns Object|Boolean
- a syncing object, or false
.
startingBlock
- Unsupported, returns0x0
currentBlock
- Returns the latest block heighthighestBlock
- Returns the latest block heightknownStates
- Unsupported, returns0x0
pulledStates
- Unsupported, returns0x0
- This will almost always return
false
- If a syncing object does return, the values are generally not useful
web3.eth.getGasPrice()
Returns the current gas price in yoctoNEAR.
Promise
returns String
- Number string of the current gas price in yoctoNEAR.
- The gas price is returned in yoctoNEAR instead of wei
- At the moment, the gas price is determined from the most recent block. web3 typically determines the gas price by the last few blocks median gas price.
web3.eth.getAccounts()
Returns a list of accounts the node controls.
Promise
returns Array
- An array of addresses controlled by node.
- Addresses are the EVM hash of a Near AccountId
web3.eth.getBlockNumber()
Returns the current block number
Promise
returns Number
- The number of the most recent block.
web3.eth.getBalance(address)
Returns the balance of an address.
String
address
- The address to get the balance of. This is the EVM address equivalent of a Near AccountId
Promise
returns String
- The current balance for the given address in yoctoNEAR.
- Due to Near RPC limitations, the balance of the address will always be from the latest block.
- Address is the EVM hash of a Near AccountId
web3.eth.getStorageAt(address, position)
Get the storage at a specific position of an address.
String
address
- The address to get the storage from. This is the EVM address equivalent of a Near AccountIdNumber|String|BN|BigNumber
position
- the index position of the storage
Promise
returns String
- The value in storage at the given position.
- Due to Near RPC limitations, the balance of the address will always be from the latest block.
- Address is the EVM hash of a Near AccountId
web3.eth.getCode(address)
Get the code at a specific address
String
address
- The address to get the code from.
Promise
returns String
- The data at given address address
.
- Due to Near RPC limitations, the balance of the address will always be from the latest block.
- Address is the EVM hash of a Near AccountId
web3.eth.getBlock(blockHashOrBlockNumber [, returnTransactionObjects])
Returns a block matching the block number or block hash
String|Number|BN|BigNumber
- The block number or block hash. Or the string'genesis'
,'latest'
,'earliest'
, or'pending'
Boolean
- (optional, defaultfalse
) If specifiedtrue
, the returned block will contain all transactions as objects. By default it isfalse
so, there is no need to explictly specify false. And, iffalse
it will only contain the transaction hashes.
Promise
returns Object
- The block object
number
- The block numberhash
- Hash equivalent of the base58 Near block hashparentHash
- Hash equivalent of the base58 Near block's parent block hashnonce
- Always returnsnull
. This is typically the hash of the generated proof-of-work. There is no equivalent concept in Near.transactionsRoot
- Always returns0x0000...
. Since transactions are on chunks and chunks are on block, there is no equivalent of a transaction trie of the blocksize
- Returns the weight of the blockgasLimit
- The maximum gas allowed in this block. Returned in yoctoNEARgasUsed
- The total used gas by all chunks in this block. A chunk may have a transaction, but that transaction may be processed in a different chunk.timestamp
- The unix timestamp for when the block was collatedtransactions
- Array of transaction objects, or the 32 byte transaction hashes equivalent of the base58 Near transaction hashes.sha3Uncles
- Unsupported, undefined/null value returnedlogsBloom
- Unsupported, undefined/null value returnedstateRoot
- Unsupported, undefined/null value returnedminer
- Unsupported, undefined/null value returneddifficulty
- Unsupported, undefined/null value returnedtotalDifficulty
- Unsupported, undefined/null value returnedextraData
- Unsupported, undefined/null value returneduncles
- Unsupported, undefined/null value returned
- Passing through
'genesis'
or'earliest'
will return block 0 - Passing through
'latest'
or'pending'
will return the latest block. There is no concept of pending blocks. - See Important Format Changes for information on
hash
,gas
,transactions
web3.eth.getBlockTransactionCount(blockHashOrBlockNumber)
Returns the number of transactions in a given block.
{String|Number|BN|BigNumber}
- The block number or block hash. Or the string'genesis'
,'latest'
,'earliest'
, or'pending'
Promise
returns Number
- The number of transactions in the given block.
- Blocks have chunks and chunks have transactions; all the transactions are collected from a block's chunks and counted. Conceptually this is the same thing, but note that transactions do not actually reside in blocks.
web3.eth.getTransaction(transactionHash)
Returns a transaction matching the given transaction hash.
String
transactionHash
- the transaction hash
Promise
returns Object
- A transaction object
hash
- Hash of the transaction<nearTxHash>:<accountId>
(transaction's sender's accountId)nonce
- The number of transactions made by the sender prior to this oneblockHash
- hash equivalent of the block where this transaction was in.blockNumber
- Block number where this transaction was intransactionIndex
- integer of the transactions index position in the block.from
- EVM Address of the senderto
- EVM address of the receivervalue
- Value transfered in yoctoNEARgasPrice
- Gas price set by the block in yoctoNEARgas
- Gas consumed by the sender in yoctoNEARinput
- Unsupported, null value provided
-
Due to the Near protocol, getting a transaction's status requires knowing both the transaction hash and the Near AccountId of the transaction's signer. To allow for this, transaction hashes in NearProvider are the base58 transaction hashes concatenated with the
signer_id
of the transaction, and separated with a:
.Example:
// A Near transaction hash (base58) const nearTxHash = 'ByGDjvYxVZDxv69c86tFCFDRnJqK4zvj9uz4QVR4bH4P'; // A Near AccountId. In particular, the AccountId of the transaction's signer const signerId = 'test.near' // Concatenate and separate with ':' const txHash = `${nearTxHash}:${signerId}; console.log(txHash); // ByGDjvYxVZDxv69c86tFCFDRnJqK4zvj9uz4QVR4bH4P:test.near
-
See Important Format Changes for additional information.
web3.eth.getTransactionFromBlock(hashStringOrNumber, indexNumber)
Returns a transaction based on a block hash or number and the transaction's index position.
{String|Number|BN|BigNumber}
hashStringOrNumber
The block number or block hash. Or the string'genesis'
,'latest'
,'earliest'
, or'pending'
{Number}
indexNumber
- The transaction's index position
Promise
returns Object
- A transaction object. See web3.eth.getTransaction.
web3.eth.getTransactionReceipt(hash)
Returns the receipt of a transaction by transaction hash.
String
transactionHash
- the transaction hash. See web3.eth.getTransaction.
Promise
returns Object
- A transaction receipt object
status
- Returnstrue
if the transaction was successful,false
if the EVM reverted the transactionblockHash
Hash of the block where this transaction was in.blockNumber
- Block number where this transaction was in.transactionHash
- Hash of the transaction.transactionIndex
- Integer of the transactions index position in the block.from
- Address of the sender.to
- Address of the receiver. null when its a contract creation transaction.contractAddress
- The contract address created, if the transaction was a contract creation, otherwise null.cumulativeGasUsed
- The total amount of gas used when this transaction was executed in the block.gasUsed
- The amount of gas used by this specific transaction alone.logs
- Array of log objects, which this transaction generated.
web3.eth.getTransactionCount(address)
Get the numbers of transactions sent from this address.
String
address
- The address to get the numbers of transactions from. Address is the EVM address of a Near AccountId
Promise
returns Number
- The number of transactions sent from the given address
- Specifically, returns the nonce of transactions sent from the address. Near will only return the total transactions; selecting a block is not supported.
web3.eth.sendTransaction(transactionObject
Sends a transaction to the network.
-
Object
- the transaction object to send:to
-String
: EVM destination addressvalue
-Number|String|BN|BigNumber
: amount of yoctoNEAR to attachgas
-Number
: amount of gas to use for the transaction in yoctoNEARdata
-String
: the encoded call data
Returns the transactionHash
of the transaction: <base58TxHash>:<accountId>
- The sender is the default accountId. At this time, another account cannot be specified.
- All other optional properties on the transaction object are unsupported
Unsupported at the moment, always returns 0x0
.
web3.eth.signTransaction(transactionObject)
Executes a new message call immediately without creating a transaction on the block chain.
Object
- A transaction object, see web3.eth.sendTransaction, with the difference that only theto
field is required.
Promise
returns String
: The returned data of the call, e.g. a smart contract functions return value.
- Due to Near RPC limitations, this will always be called on the latest block.
- Update hardcoded
transactionIndex
- Make sure all errors are handled
- Expose
utils.nearAccountToEvmAddress
, otherwise users will not be able to pass through the EVM Address equivalent - Expose conversion utils like
base58ToHex
,hexToBase58
- Add documentation about accessing provider methods (point to Near docs, explain relevant methods)