Callbacks Middleware: Evmos Case Study
Last month we released v0.1.0 of the callbacks middleware. This feature allows smart contracts and modules to receive callbacks from IBC applications like ICS-20 transfer and ICS-27 interchain accounts (ICA) in order to execute subsequent logic.
The callbacks middleware unlocked use cases of the form ‘transfer + action’. What previously took a user 3 or more steps to achieve can now be condensed into a single user transaction. See this blog post that explains how the callbacks middleware works and why it’s important.
Today we’re excited to announce that Evmos will be one of the first users of the callbacks middleware, pioneering the best-in-class UX for their users by leveraging this novel feature. This is the first in an ongoing series of case studies showing how chains, applications, and teams use IBC in production.
What is Evmos?
Evmos is a blockchain built using the Cosmos SDK and CometBFT, offering EVM equivalence for Solidity developers. Evmos provides the best of both Ethereum and Cosmos worlds by offering all the standard EVM libraries while leveraging the instant finality of CometBFT, customization of the Cosmos SDK, and out-of-the-box interoperability using IBC - the Inter-Blockchain Communication Protocol.
Evmos is building for a world where ‘Web3 users’ are just regular users. Their team is dedicated to developing dapps that match or exceed the performance of Web2 applications, offering an exceptional user experience. To achieve this goal, Evmos has embraced a ‘cross-chain’ approach, where instead of dapps being deployed on multiple chains, they live only on Evmos. Using IBC, users can access these dapps from anywhere without needing to know which chain they’re on or where they want their assets to go.
To build a superior UX of this kind, features that abstract away user complexity are critical. And this is exactly what the callbacks middleware aims to provide.
Using the Callbacks Middleware for Stateful Precompiled Contracts
Below is an example Solidity interface that developers can use to receive callbacks on the EVM level. Developers that want to utilize the callbacks middleware will have to implement this interface in their contract in order to receive and respond to messages from the middleware.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
// SPDX-License-Identifier: LGPL-3.0-only
pragma solidity ^0.8.0;
/// @author Evmos Team
/// @title Packet Actor Interface
/// @dev The interface through which solidity contracts define their own IBC
/// packet callbacks handling logic
interface IPacketActor {
/// @dev onRecvPacket will be called on the IBCActor after the IBC Application
/// handles the RecvPacket callback if the packet has an IBC Actor as a receiver.
/// @param packet The IBC packet received.
/// @param relayer The relayer address that sent the packet.
/// @return acknowledgement The success or failure acknowledgement bytes.
function onRecvPacket(
Packet calldata packet,
address relayer
) external returns (bytes calldata acknowledgement);
/// @dev onAcknowledgementPacket will be called on the IBC Actor
/// after the IBC Application handles its own OnAcknowledgementPacket callback
/// @param packet The IBC packet acknowledged.
/// @param acknowledgement The IBC transaction acknowledgement (success or error) bytes.
/// @param relayer The relayer that handled the acknowledgment.
/// @return success The success or failure boolean.
function onAcknowledgementPacket(
Packet calldata packet,
bytes calldata acknowledgement,
address relayer
) external returns (bool success);
/// @dev onTimeoutPacket will be called on the IBC Actor
/// after the IBC Application handles its own OnTimeoutPacket callback.
/// @param packet The IBC packet that timeouted.
/// @param relayer The relayer that handled the timeout.
/// @return success The success or failure boolean.
function onTimeoutPacket(
Packet calldata packet,
address relayer
) external returns (bool success);
}
Evmos intends to use the callbacks middleware to compose with their ‘Outposts’. Outposts are stateful precompiled contracts (aka. EVM Extensions) on Evmos that can interact with other chains over IBC to leverage functionality specific to those chains, providing a better experience to end users and smart contracts. For example, the Osmosis Outpost allows an Evmos user (EOA) or contract to automatically swap token X for token Y in one transaction without having to manually execute multiple cross-chain transactions to and from Osmosis.
Prior to introducing the callbacks middleware, smart contracts and modules could not receive callbacks from IBC apps such as transfer or Interchain Accounts. The absence of these callbacks left contracts and modules without the means to determine the success/failure result of a packet, blocking their ability to execute follow-up actions based on the outcome of said packet.
We had the opportunity to meet the Evmos team and gain a detailed walkthrough of how they plan to use the callbacks middleware. Here are the primary use cases that they have in mind.
Use Case #1: Liquid stake and use liquid tokens to provide LP
Use the Stride Outpost on Evmos for liquid staking and use the liquid-staked tokens to provide liquidity on a DEX on Evmos, all in one transaction.
User journey (shown in Figures 1 and 2):
- Alice calls yield contract Y on Evmos with the intent to provide liquidity on an EVMOS/stEVMOS pool to a DEX on Evmos using only EVMOS tokens.
- Contract Y calls the liquidStake function of the Stride Outpost (0x0000000000000000000000000000000000000900) to liquid stake EVMOS and receive stEVMOS, triggering a chain of automated steps via the Stride Autopilot feature.
- Stride Oupost sends EVMOS over IBC to Stride
- Liquid stake EVMOS on Stride to mint stEVMOS
- Send stEVMOS over IBC to contract Y on Evmos
- On acknowledgement of step 2c., the callbacks middleware on Evmos recognizes the callback address and triggers the callback function implemented on the receiving smart contract Y.
- Contract Y’s callback function calls a DEX contract on Evmos (e.g. Forge) and uses stEVMOS and EVMOS balance from Alice to provide liquidity.
Use Case #2: Cross-Chain Portfolio Rebalance
Use a cross-chain DeFi aggregator to find the best swap rates and automatically balance a user’s portfolio (similar to Calc Finance).
User journey (shown in Figures 3 and 4):
- Alice invokes a portfolio contract P with the intent to balance her portfolio.
- Contract P invokes the Osmosis outpost which sends an IBC transfer of EVMOS tokens to Osmosis, including the data required for balancing her portfolio.
- On acknowledgement of the IBC transfer, the callbacks middleware on Evmos recognizes the callback address and sends an ICA packet to swap tokens on Osmosis and return funds to Alice on Evmos.
Use Case #3: Onboard from Ethereum and use interchain services through IBC
Use Evmos to bridge assets from Ethereum and use interchain services through IBC. For example, perform an Osmosis swap through Metamask.
User journey (shown in Figures 5 and 6):
- Alice invokes an Ethereum Outpost contract with the intent to onboard onto Evmos with ETH.
- The outpost bridges ETH to Evmos using an Ethereum bridge contract B on Evmos (Axelar, Polymer, etc.).
- B calls the Osmosis Outpost contract to swap ETH on Osmosis and receive EVMOS tokens on Evmos. Using Osmosis’s cross-chain swaps a chain of steps is triggered:
- Send ETH over IBC to Osmosis
- Swap ETH to EVMOS
- Send EVMOS over IBC to Evmos
- On acknowledgement, the callbacks middleware on Evmos recognizes the callback address and triggers the callback function implemented on the receiving contract B.
- B’s callback function calls the staking extension to stake EVMOS for Alice.
By being one of the early adopters of this feature, Evmos is at the forefront of delivering a superior end-user experience. Evmos leverages the callbacks middleware to enable interactions with Outposts and unlock one-click features like liquid stake+action, portfolio balancing, and cross-chain asset bridging. Over time, we expect more chains to adopt this feature, leading to a cross-chain UX where users never have to hop between multiple interfaces.
Get Started with the Callbacks Middleware
The introduction of the callbacks middleware represents a major advancement for Interchain composability. This feature empowers smart contracts and modules to receive callbacks from IBC applications, streamlining processes and enabling use cases where multiple different transactions can be bundled into a single one.
Cosmos chains that use Evmos’ EVM as the execution environment will be able to use the callbacks middleware soon. The team at Confio will add support for this feature in x/wasm later this year.