Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Integrating Kiln On-Chain gives integrators total control over the staking experience. This includes designing the user experience, integration with native workflows, end-user fees, and the selection of node operators.
This comprehensive guide equips you with all the essentials to initiate the integration process.
This page provides a high-level understanding and overview of the architecture of the smart contracts as it relates to pooled staking.
Before getting started, here are a few terms we commonly use in the architecture overview.
integrator: a platform (e.g., wallet, web platform) offering staking services to their users by integrating with the On-Chain platform.
operator: a node operator or validator infrastructure provider (e.g., Kiln or Coinbase Cloud) that owns and operates Ethereum validators for staking services on the On-Chain platform.
operator pool: also known as a 'vPool', it is a set of smart contracts serving as the 'pooled staking engine,' with each one owned and operated by a node operator. One vPool can serve multiple integrators.
integration contract: A smart contract owned and operated by the integrator, serving as the primary integration point to the platform (end-user fees, commissions, node operator preferences and splits, and more!)
A smart contract owned and operated by the integrator, serving as the primary integration point for their users to the platform. These contracts manage end-user fees, commissions, node operator preference and split, and can be paused to prevent deposits at the discretion of the integrator.
Integrator contracts can connect to multiple Operator Pools to enable validator set diversification. They can be configured to allocate the desired balance across each operator, allowing for configurations such as 50/50, 60/40, 80/20, etc., tailored to specific requirements.
Under the hood, when a user deploys their ETH, the integration contract forwards the ETH to the operator pool. Users are abstracted from the underlying technical complexity of the platform, receiving a ERC-20 token in their wallet when they stake ETH. This token, soulbound or transferable based on the integrator's preference, represents their stake ownership and serves as the withdrawal credentials.
Integrators have full control over the can customise the token and define the token name and symbol. For example, myETH (My Company ETH).
NOTE: the Operator Pool has no concept of tokens. The integrator contracts are where tokens are issued and managed.
Think of Operator Pools as pooled staking engines, each owned by a node operator but entirely managed by smart contract logic. These sets of smart contracts handle all fundamental operations and lifecycle tasks of the pool, including deposits, validator activation and deactivation, reward distribution, exits, and management of staking fees.
Every Operator Pool can allow one or more integration contracts to connect and deposit ETH, allowing simple validator set diversification.
Rewards are generated by all of the validators supporting the pool, and are recycled back into the pool.
The value of the pool is recalculated daily via the receipt of oracle reports and the value of the operator pool will increase in value over time as rewards flow into the system.
This means that users will typically see the value of their staked position increase on daily basis.
An oracle report consists of data like total ETH staked, total ETH currently in the protocol Exit Queue, total validators staked, total validators exited and strategy inputs to tell the pool to either accelerate user exits time or increase new validator deposits.
Using this data, Operator pool will perform multiple state transitions to:
deposit new validators
answer the exit demand in the exit queue
compute operator commission
update the Operator pool shares exchange rate with ETH to take into account new rewards
exit validators if needed to match the user exit demand in the pool exit queue
Users can request to exit any amount of ETH up to the total value of their staked position. That is, they can request a full or partial exit.
Exiting, or withdrawing ETH, from the pool is a three staged process:
Request exit (requires user tx)
Wait for the request to be fulfilled
Withdraw the ETH (requires user tx)
Issue a request to withdraw an amount of ETH from the pool. After the transaction is confirmed and executed, an 'exit queue ticket' is issued, which is a soulbound NFT token representing the withdrawal request.
Exit requests are processed on a daily basis via the receipt of Oracle reports.
Fulfilling exit requests involves two scenarios::
ETH from deposits not yet staked and generated rewards.
The next oracle report on the pool (daily on mainnet) will process the exit.
ETH from validator exits
Where exit demand significantly surpasses available ETH, validator exits become necessary.
In this case, the validator must complete the full exit and withdrawal process, and then await the subsequent oracle report. This process generally takes between 2-10 days but may extend further, depending on the dynamics of the Ethereum exit queue.
Under normal conditions, with the pool earning rewards and incoming liquidity from deposits, it will take approximately 1-4 days for the user's exited ETH to become available for withdrawal.
Once fulfilled, the exited ETH is available to be withdrawn by the user.
When the ETH is available, the user will need to perform a 'claim transaction' during which the NFT will be burned in exchange for the ETH.
Before diving straight into integrating, think about the user experience and all the key workflows you should consider as part of your integration. Here is a non-exhaustive list to help plan your user experience.
Feature in 'Earn' dashboard or integrate into existing workflows.
Emphasize ETH staking as a new product for heightened awareness.
Clearly display the reward rate for informed user decision-making. It is not static.
Set a practical minimum (e.g. 0.1 or 0.05 ETH) to avoid the staking tx costing more than the stake itself.
Alert users if the cost of the transaction is high relative to the amount being staked
Clarify if users must read and accept your Terms and Conditions.
Consider displaying estimated rewards based on the current reward rate, as some integrators do.
Provide users with an estimate of when their stake begins earning rewards.
Include a link to the 'staking request' transaction on Etherscan for transparency.
Display the user's staked ETH amount and current value
Consider showing historical reward data e.g. yesterday, last week, last month
Simplify 'stake more' or 'unstake' options for user convenience.
Enable users to request full or partial unstake.
Highlight that unstaking may take several days; the ETH is not immediately available.
For each exit request, show users an estimate
If unstaking too early, caution about potential network fee implications.
Include a link to the 'unstaking request' transaction on Etherscan for transparency.
Display 'unstake request' status and estimated time.
Alert the user to the fact that they have ETH to be claimed.
Include a link to the 'claim ETH' transaction on Etherscan for transparency.
Think about how you handle the integration contract being paused?
Stakers will not be able to stake (transactions will revert), so it's better to think about how to gracefully handle these situations before they happen.
This page describes the roles needed to operate the integration contracts
Learn more about your integration contract along with the choice of receipt tokens available to you.
The integration contract will be deployed by Kiln, but then owned and operated by the integrator. This provides integrators with complete control over the user experience and the staking product being distributed to their end users.
Integrators can do the following:
Users receive a receipt token representing their staked position. Integrators must decide on the token type upfront (soulbound or liquid), as it cannot be set or changed later. Kiln deploys the correct integration contract based on this initial decision.
Integrators can customise the below token attributes. Both attributes will be displayed on Etherscan and ERC20/ERC1155 compatible interfaces:
token symbol: e.g. cbETH, cdcETH, psETH
token name: e.g. Pooled Staked ETH, Coinbase Wallet ETH
Integrators need to choose the token type they wish to include in the staking product being offered to their end users.
Below is a comparison and summary of token types, highlighting differences in integration approaches, capabilities, and end-user experiences.
NOTE: Commonly, start with Native20 (non-transferrable tokens). Consider an optional upgrade to Liquid20 later; connect with us for details on the upgrade path and associated considerations.
contract expose the exact same view methods as Liquid20C
without the transfer
and approve
methods. It looks like a token, but cannot behave like one.
Liquid20A
an ERC20
rebase token.
the quantity of tokens held in the users wallet will increase each time rewards are distributed. Rebase tokens maintain a fixed exchange rate but the quantity of tokens issued increases to reflect earned rewards.
Liquid20C
standard ERC20
token
The quantity of tokens held in the users wallet do not change, however their value increases each time rewards are distributed.
If you are interacting with the smart contracts using javascript (e.g. web3.js or ethers.js) you need the contract ABI and its address.
The ABI is used to encode the interface of a smart contract in a format understandable to your user interface.
Role name | Setup | Actions |
---|---|---|
Role name | Setup | Actions |
---|---|---|
Feature | Native20 | Liquid20A | Liquid20C | Native1155 | Liquid1155 |
---|---|---|---|---|---|
Parameter | Description | |
---|---|---|
Parameter | Description | |
---|---|---|
SYS_ADMIN
multi-sig or MPC wallet
pausing deposits
changing SYS_ADMIN
modifying end user fee (aka commission)
modifying commission split and recipients
modifying operator pools
modifying weighting across operator pools,
when connected to two or more pools
PROXY_ADMIN
multi-sig or MPC wallet
pausing and resume contract
changing PROXY_ADMIN
upgrading implementation contract
Stake any amount
✅
✅
✅
✅
✅
Commission taken on-chain
✅
✅
✅
✅
✅
Multi commission recipients
✅
✅
✅
✅
✅
Users chooses pool
❌
❌
❌
✅
✅
Integrator chooses pool (sets % distribution across pools)
✅
✅
✅
❌
❌
Transfers
❌
✅
✅
❌
✅
NOTES
aToken
cToken
ERC1555 compliant
admin
address
Admin wallet address
pools
address[]
List of pool addresses
poolFees
uint256[]
List of fee for each pool in basis points
poolPercentages
uint256[]
Share of new stake to go to each pool, in basis points, must add up to 10 000
commissionRecipients
address[]
List of address of commission beneficiaries
commissionDistribution
uint256[]
Share of each beneficiary, in basis points, must add up to 10 000
name
string
ERC-20 style display name
symbol
string
ERC-20 style display symbol
admin
address
Admin wallet address
pools
address[]
List of pool addresses
poolFees
uint256[]
List of fee for each pool in basis points
commissionRecipients
address[]
List of address of commission beneficiaries
commissionDistribution
uint256[]
Share of each beneficiary, in basis points, must add up to 10 000
baseUri
string
Uri from which to pull the metadata
name
string
ERC-20 style display name
symbol
string
ERC-20 style display symbol
TheGraph indexes data from the smart contracts to facilitate easier access. You can use it to understand what happens live during this guide.
To gain access to TheGraph, contact Kiln and you will receive credentials to Kiln's TheGraph instance. Feel free to also host the subgraph on your end, allowing you to run the queries locally. During this guide, we will often use TheGraph queries to verify that specific actions had the expected outcome.
The easiest way to interact with TheGraph is by visiting the web query builder.
To test it, you can try a simple query to retrieve all the deposits made by an address on an integration contract (Native20,Liquid20A or Liquid20C):
And if everything goes well, you should have a response looking like this if the wallet made some deposits.
You're now ready to follow the guide and run the queries when needed !
Used to stake any amount of ETH into the pool.
This can only be executed by calling a smart contract method:
Used to find the amount of shares for a given wallet from the integration contract
Using the smart contract view methods
Allows you to obtain the value (in ETH) of the users current staked position
For example, consider the scenario where a user staked 12 ETH several months ago. Every time they visit your app, you want to showcase the current value of the staked position accounting for the accrued value from staking rewards over time.
You can simply query the smart contract with the users wallet.
Using the smart contract view methods
Using TheGraph queries
TheGraph queries
This page provides an overview of the various contract interactions when staking.
The examples below when calling smart contract functions (e.g. stake()) are done using cast,
a cli tool, only as an illustration of how the transactions or view calls should be performed.
All of the contract calls below are for: Liquid20C, Liquid20A & Native20 contracts
Integrating Kiln into native workflow will require a mix of smart contract calls and TheGraph queries:
Smart contract
The Graph
Use the credentials provided by Kiln if using the public instance, or your own credentials if you are hosting your own instance.
Used to retrieve the historical reward rate of the pool so that it can be displayed to your users in your native workflow.
The pool reward rate can only ever be based on a rolling historical average (we can never predict the future rate). The data returned includes the average of the last week, last month, last 3 months, last 6 months and 'all time'.
It is up to you to choose the which historical rolling average to use, but most integrators currently use the last week.
TIP: you need to convert the results to a percentage (%). For example:
'All Time' Gross Reward Rate returns: 26478817328005117
Convert to %
26478817328005117 / 10^18 =
.02647 (2.647%)
Using The Graph
Query
Example results
Used to retrieve the rewards of the given user based on their staked position
TIP: the result is in wei, you need to convert it to ETH. For example:
allTimeRewards = 46478817328005117
Convert to ETH
46478817328005117 / 10^18 = 0.046478817
ETH
allTimeRewards
= ((sharesBalance * totalUnderlyingSupply) / totalSupply) - adjustedTotalDeposited
Using The Graph
Query
Example results
Action | How to... | Description |
---|---|---|
Get the historical reward rate of the pool (last week, month, 3 months, 6 months, All Time).
Stake any amount of ETH into the pool.
Get a list of all deposits / stakes made from a wallet
Current value of stake(s)
Get the current underlying value of a wallet's staked position. Includes original stake + accrued rewards.
Get the historical reward rate of the wallet's staked position.
Unstake
Initiate an exit (or unstake) of a wallet's full or partial staked position.
Unstake status
Get the current status of a wallet's exit request.
Withdraw unstaked ETH
Claim unstaked ETH once the exit request has been fulfilled.
The unstaking process is a three-stage process:
user requests an exit or unstake (user tx)
exit request is processed and ETH is sourced to pay for the exit
user claims exited ETH (user tx)
When user request an exit, they burn their shares (receipt tokens in their wallet) in exchange for one or exit queue tickets.
These tickets have a status based on wether or not they can be claimed (user is able to claim their ETH), which depends on the liquidity provided to the exit queues by the vPools.
You can find more details about tickets and casks here.
Used to request an exit (unstake) of any amount of ETH, up to the maximum user balance.
When initiating an exit, you must specify the quantity of integration tokens to exit. Subsequently, the integration contract will generate one or several tickets in the associated vPool exit queues.
This can only be executed by calling a smart contract method:
Used to retrieve all exit queue tickets for a user, providing the status of each ticket. This information enables you to inform the user about the availability of their exited ETH for claiming. Additionally, you have the option to permit users to claim a portion of their exit request if it is partially fulfilled, with the ability to claim the remainder once it becomes available.
Using The Graph
Query
Example results
Used to claim the ETH of a user who has requested to exit the pool.