sv::messages
attribute
Use sv::messages
to expand your contract functionality with the Sylvia interface.
The sv::messages
attribute expects that the trait is implemented on the contract type.
Macros
List of macros supporting the sv::messages
attribute:
Usage
pub mod interface {
use cosmwasm_schema::cw_serde;
use sylvia::cw_std::{Response, StdError, StdResult};
use sylvia::interface;
use sylvia::types::{ExecCtx, QueryCtx};
#[cw_serde]
pub struct InterfaceQueryResp {}
#[interface]
pub trait Interface {
type Error: From<StdError>;
#[sv::msg(exec)]
fn interface_exec(&self, ctx: ExecCtx) -> StdResult<Response>;
#[sv::msg(query)]
fn interface_query(&self, ctx: QueryCtx) -> StdResult<InterfaceQueryResp>;
}
}
pub mod contract {
use cosmwasm_std::StdError;
use sylvia::contract;
use sylvia::cw_std::{Response, StdResult};
use sylvia::types::{ExecCtx, InstantiateCtx, QueryCtx};
use crate::interface::{Interface, InterfaceQueryResp};
pub struct CounterContract;
#[cfg_attr(feature = "library", sylvia::entry_points)]
#[contract]
#[sv::messages(crate::interface)]
impl CounterContract {
pub const fn new() -> Self {
Self
}
#[sv::msg(instantiate)]
fn instantiate(&self, ctx: InstantiateCtx) -> StdResult<Response> {
Ok(Response::new())
}
}
impl Interface for CounterContract {
type Error = StdError;
fn interface_exec(&self, ctx: ExecCtx) -> StdResult<Response> {
// Your logic here
Ok(Response::new())
}
fn interface_query(&self, ctx: QueryCtx) -> StdResult<InterfaceQueryResp> {
// Your logic here
Ok(Response::new())
}
}
}
Single sv::messages
attribute corresponds to a single interface implemented on a contract. If
multiple interfaces are implemented, add this attribute for each of them.
Module/Interface name mismatch
In most cases, the only parameter the sv::messages
expects is a path to the interface, in this
case crate::interface
. Sylvia macros can deduce the interface's name if it is simply an
UpperCamelCase version of the module name.
If the interface name differs from the module name, use the syntax below:
#[sv::messages(crate::interface as OtherInterface)]
Custom types
It's possible to implement an interface using
Empty
(opens in a new tab) instead of custom
types used in the contract.
In such a case, we must inform Sylvia to convert the types in the dispatch
methods.
#[sv::messages(crate::interface: custom(msg, query))]
The order of msg
and query
doesn't matter, and the attribute accepts either msg
, query
or
both.