API Reference CMD

Incubed can be used as a command-line utility or as a tool in Bash scripts. This tool will execute a JSON-RPC request and write the result to standard output.

If you want to read more about it this might a short blogpost : https://blog.slock.it/blockchain-in-a-shell-45b6626dc2c0 .

Usage

in3 [options] method [arguments]
-c, -chain

The chain to use currently:

mainnet:Mainnet
kovan:Kovan testnet
tobalaba:EWF testchain
goerli:Goerli testchain using Clique
btc:Bitcoin (still experimental)
local:Use the local client on http://localhost:8545
RPCURL:If any other RPC-URL is passed as chain name, this is used but without verification
-p, -proof

Specifies the verification level:

none:No proof
standard:Standard verification (default)
full:Full verification
-np Short for -p none.
-a max number of attempts before giving up (default 5).
-s, -signs Number of signatures to use when verifying.
-rc number of request per try (default 1)
-ns no stats if set requests will not be part of the official metrics and considered a service request
-md specifies the minimum Deposit of a node in order to be selected as a signer
-eth converts the result (as wei) to ether.
-f finality - number of blocks on top of the current one.
-path the HD wallet derivation path . We can pass in simplified way as hex string i.e [44,60,00,00,00] => 0x2c3c000000
-b, -block The block number to use when making calls. Could be either latest (default), earliest, or a hex number.
-l, -latest replaces latest with latest BlockNumber - the number of blocks given.
-pk The path to the private key as keystore file.
-pwd Password to unlock the key. (Warning: since the passphrase must be kept private, make sure that this key may not appear in the bash_history)
-to The target address of the call.
-st, -sigtype the type of the signature data : eth_sign (use the prefix and hash it), raw (hash the raw data), hash (use the already hashed data). Default: raw
-port specifies the port to run incubed as a server. Opening port 8545 may replace a local parity or geth client.
-d, -data

The data for a transaction.

This can be a file path, a 0x-hexvalue, or - to read it from standard input. If a method signature is given with the data, they will be combined and used as constructor arguments when deploying.

-gas The gas limit to use when sending transactions (default: 100000).
-gas_price the gas price to use when sending transactions. (default: use eth_gasPrice)
-value The value to send when conducting a transaction. Can be a hex value or a float/integer with the suffix eth or wei like 1.8eth (default: 0).
-w, -wait If given, eth_sendTransaction or eth_sendRawTransaction will not only return the transaction hash after sending but also wait until the transaction is mined and returned to the transaction receipt.
-json If given, the result will be returned as JSON, which is especially important for eth_call, which results in complex structres.
-hex If given, the result will be returned as hex.
-debug If given, Incubed will output debug information when executing.
-q quiet. no warnings or log to stderr.
-ri Reads the response from standard input instead of sending the request, allowing for offline use cases.
-ro Writes the raw response from the node to standard output.
-kin3 if kin3 is specified, the response including in3-section is returned.
-bw initialize with weights from boot nodes.
-tr runs test request when showing in3_weights
-thr runs test request including health-check when showing in3_weights
-fi reads a prerecorded request from the filepath and executes it with the recorded data. (great for debugging)
-fo records a request and writes the reproducable data in a file (including all cache-data, timestamps …)
-nl a coma seperated list of urls (or address:url) to be used as fixed nodelist
-bn a coma seperated list of urls (or address:url) to be used as boot nodes
-os only sign, don’t send the raw Transaction
-x Allow usage of experimental features. This option is required if you want to use experimental features.

Install

From Binaries

You can download the from the latest release-page:

https://github.com/slockit/in3-c/releases

These release files contain the sources, precompiled libraries and executables, headerfiles and documentation.

From Package Managers

We currently support

Ubuntu Launchpad (Linux)

Installs libs and binaries on IoT devices or Linux-Systems

# Add the slock.it ppa to your system
sudo add-apt-repository ppa:devops-slock-it/in3

# install the commandline tool in3
apt-get install in3

# install shared and static libs and header files
apt-get install in3-dev

Brew (MacOS)

This is the easiest way to install it on your mac using brew

# Add a brew tap
brew tap slockit/in3

# install all binaries and libraries
brew install in3

From Sources

Before building, make sure you have these components installed:

  • CMake (should be installed as part of the build-essential: apt-get install build-essential)
  • libcurl (for Ubuntu, use either sudo apt-get install libcurl4-gnutls-dev or apt-get install libcurl4-openssl-dev)
  • If libcurl cannot be found, Conan is used to fetch and build curl
# clone the sources
git clone https://github.com/slockit/in3-c.git

# create build-folder
cd in3-c
mkdir build && cd build

# configure and build
cmake -DCMAKE_BUILD_TYPE=Release .. && make in3

# install
sudo make install

When building from source, CMake accepts the flags which help to optimize. For more details just look at the CMake-Options .

From Docker

Incubed can be run as docker container. For this pull the container:

# run a simple statement
docker run slockit/in3:latest eth_blockNumber

# to start it as a server
docker run -p 8545:8545 slockit/in3:latest -port 8545

# mount the cache in order to cache nodelists, validatorlists and contract code.
docker run -v $(pwd)/cache:/root/.in3 -p 8545:8545 slockit/in3:latest -port 8545

Environment Variables

The following environment variables may be used to define defaults:

IN3_PK
The raw private key used for signing. This should be used with caution, since all subprocesses have access to it!
IN3_CHAIN
The chain to use (default: mainnet) (same as -c). If a URL is passed, this server will be used instead.

Methods

As methods, the following can be used:

<JSON-RPC>-method
All officially supported JSON-RPC methods may be used.
send <signature> …args

Based on the -to, -value, and -pk, a transaction is built, signed, and sent. If there is another argument after send, this would be taken as a function signature of the smart contract followed by optional arguments of the function.

# Send some ETH (requires setting the IN3_PK-variable before).
in3 send -to 0x1234556 -value 0.5eth
# Send a text to a function.
in3 -to 0x5a0b54d5dc17e0aadc383d2db43b0a0d3e029c4c  -gas 1000000 send "registerServer(string,uint256)" "https://in3.slock.it/kovan1" 0xFF
sign <data>
signs the data and returns the signature (65byte as hex). Use the -sigtype to specify the creation of the hash.
call <signature> …args
eth_call to call a function. After the call argument, the function signature and its arguments must follow.
in3_nodeList
Returns the NodeList of the Incubed NodeRegistry as JSON.
in3_sign <blocknumber>

Requests a node to sign. To specify the signer, you need to pass the URL like this:

# Send a text to a function.
in3 in3_sign -c https://in3.slock.it/mainnet/nd-1 6000000
in3_stats
Returns the stats of a node. Unless you specify the node with -c <rpcurl>, it will pick a random node.
abi_encode <signature> …args
Encodes the arguments as described in the method signature using ABI encoding.
abi_decode <signature> data
Decodes the data based on the signature.
pk2address <privatekey>
Extracts the public address from a private key.
pk2public <privatekey>
Extracts the public key from a private key.
ecrecover <msg> <signature>
Extracts the address and public key from a signature.
createkey
Generates a random raw private key.
key <keyfile>

Reads the private key from JSON keystore file from the first argument and returns the private key. This may ask the user to enter the passphrase (unless provided with -pwd). To unlock the key to reuse it within the shell, you can set the environment variable like this:

export IN3_PK=`in3 keystore mykeyfile.json`

if no method is passed, this tool will read json-rpc-requests from stdin and response on stdout until stdin is closed.

echo '{"method":"eth_blockNumber","params":[]}' | in3 -q -c goerli

This can also be used process to communicate with by startiing a in3-process and send rpc-comands through stdin and read the responses from stout. if multiple requests are passed in the input stream, they will executed in the same order. The result will be terminated by a newline-character.

Running as Server

While you can use in3 to execute a request, return a result and quit, you can also start it as a server using the specified port ( -port 8545 ) to serve RPC-requests. Thiss way you can replace your local parity or geth with a incubed client. All Dapps can then connect to http://localhost:8545.

# starts a server at the standard port for kovan.
in3 -c kovan -port 8545

Cache

Even though Incubed does not need a configuration or setup and runs completely statelessly, caching already verified data can boost the performance. That’s why in3 uses a cache to store.

NodeLists
List of all nodes as verified from the registry.
Reputations
Holding the score for each node to improve weights for honest nodes.
Code
For eth_call, Incubed needs the code of the contract, but this can be taken from a cache if possible.
Validators
For PoA changes, the validators and their changes over time will be stored.

By default, Incubed will use ~/.in3 as a folder to cache data.

If you run the docker container, you need to mount /root/.in3 in to persist the cache.

Signing

While Incubed itself uses an abstract definition for signing, at the moment, the command-line utility only supports raw private keys. There are two ways you can specify the private keys that Incubed should use to sign transactions:

  1. Use the environment variable IN3_PK. This makes it easier to run multiple transaction.

    Warning

    Since the key is stored in an envirmoent variable all subpoccess have access to this. That’s why this method is potentially unsafe.

    #!/bin/sh
    
    # reads the key from the keyfile and asks the user for the passphrase.
    IN3_PK = `in3 key my_keyfile.json`
    
    # you can can now use this private keys since it is stored in a enviroment-variable
    in3 -to 0x27a37a1210df14f7e058393d026e2fb53b7cf8c1 -value 3.5eth -wait send
    in3 -to 0x5a0b54d5dc17e0aadc383d2db43b0a0d3e029c4c  -gas 1000000 send "registerServer(string,uint256)" "https://in3.slock.it/kovan1" 0xFF
    
  2. Use the -pk option

    This option takes the path to the keystore-file and will ask the user to unlock as needed. It will not store the unlocked key anywhere.

    in3 -pk my_keyfile.json -to 0x27a37a1210df14f7e058393d026e2fb53b7cf8c1 -value 200eth -wait send
    

Autocompletion

If you want autocompletion, simply add these lines to your .bashrc or .bash_profile:

_IN3_WORDS=`in3 autocompletelist`
complete -W "$_IN3_WORDS" in3

if you are using zshell, you can install the more advanced version of it

curl https://raw.githubusercontent.com/blockchainsllc/in3/master/scripts/_in3.sh > /usr/local/share/zsh/site-functions/_in3.sh

Function Signatures

When using send or call, the next optional parameter is the function signature. This signature describes not only the name of the function to call but also the types of arguments and return values.

In general, the signature is built by simply removing all names and only holding onto the types:

<FUNCTION_NAME>(<ARGUMENT_TYPES>):(<RETURN_TYPES>)

It is important to mention that the type names must always be the full Solidity names. Most Solidity functions use aliases. They would need to be replaced with the full type name.

e.g., uint -> uint256

Examples

Getting the Current Block

# On a command line:
in3 eth_blockNumber
> 8035324

# For a different chain:
in3 -c kovan eth_blockNumber
> 11834906

# Getting it as hex:
in3 -c kovan -hex eth_blockNumber
> 0xb49625

# As part of shell script:
BLOCK_NUMBER=`in3 eth_blockNumber`

Using jq to Filter JSON

# Get the timestamp of the latest block:
in3 eth_getBlockByNumber latest false | jq -r .timestamp
> 0x5d162a47

# Get the first transaction of the last block:
in3 eth_getBlockByNumber latest true | jq  '.transactions[0]'
> {
   "blockHash": "0xe4edd75bf43cd8e334ca756c4df1605d8056974e2575f5ea835038c6d724ab14",
   "blockNumber": "0x7ac96d",
   "chainId": "0x1",
   "condition": null,
   "creates": null,
   "from": "0x91fdebe2e1b68da999cb7d634fe693359659d967",
   "gas": "0x5208",
   "gasPrice": "0xba43b7400",
   "hash": "0x4b0fe62b30780d089a3318f0e5e71f2b905d62111a4effe48992fcfda36b197f",
   "input": "0x",
   "nonce": "0x8b7",
   "publicKey": "0x17f6413717c12dab2f0d4f4a033b77b4252204bfe4ae229a608ed724292d7172a19758e84110a2a926842457c351f8035ce7f6ac1c22ba1b6689fdd7c8eb2a5d",
   "r": "0x1d04ee9e31727824a19a4fcd0c29c0ba5dd74a2f25c701bd5fdabbf5542c014c",
   "raw": "0xf86e8208b7850ba43b7400825208947fb38d6a092bbdd476e80f00800b03c3f1b2d332883aefa89df48ed4008026a01d04ee9e31727824a19a4fcd0c29c0ba5dd74a2f25c701bd5fdabbf5542c014ca043f8df6c171e51bf05036c8fe8d978e182316785d0aace8ecc56d2add157a635",
   "s": "0x43f8df6c171e51bf05036c8fe8d978e182316785d0aace8ecc56d2add157a635",
   "standardV": "0x1",
   "to": "0x7fb38d6a092bbdd476e80f00800b03c3f1b2d332",
   "transactionIndex": "0x0",
   "v": "0x26",
   "value": "0x3aefa89df48ed400"
  }

Calling a Function of a Smart Contract

 # Without arguments:
 in3 -to 0x2736D225f85740f42D17987100dc8d58e9e16252 call "totalServers():uint256"
 > 5

 # With arguments returning an array of values:
 in3 -to 0x2736D225f85740f42D17987100dc8d58e9e16252 call "servers(uint256):(string,address,uint256,uint256,uint256,address)" 1
 > https://in3.slock.it/mainnet/nd-1
 > 0x784bfa9eb182c3a02dbeb5285e3dba92d717e07a
 > 65535
 > 65535
 > 0
 > 0x0000000000000000000000000000000000000000

# With arguments returning an array of values as JSON:
 in3 -to 0x2736D225f85740f42D17987100dc8d58e9e16252 -json call "servers(uint256):(string,address,uint256,uint256,uint256,address)" 1
 > ["https://in3.slock.it/mainnet/nd-4","0xbc0ea09c1651a3d5d40bacb4356fb59159a99564","0xffff","0xffff","0x00","0x0000000000000000000000000000000000000000"]

Sending a Transaction

# Sends a transaction to a register server function and signs it with the private key given :
in3 -pk mykeyfile.json -to 0x27a37a1210df14f7e058393d026e2fb53b7cf8c1  -gas 1000000  send "registerServer(string,uint256)" "https://in3.slock.it/kovan1" 0xFF

Deploying a Contract

# Compiling the Solidity code, filtering the binary, and sending it as a transaction returning the txhash:
solc --bin ServerRegistry.sol | in3 -gas 5000000 -pk my_private_key.json -d - send

# If you want the address, you would need to wait until the text is mined before obtaining the receipt:
solc --bin ServerRegistry.sol | in3 -gas 5000000 -pk my_private_key.json -d - -wait send | jq -r .contractAddress