abstract_sdk/base/
endpoints.rs

1//! # Endpoints
2//! This module provides endpoints for a base contract.
3//! Each endpoint is a trait that can be implemented by a base contract to support a specific endpoint.
4//!
5//! > *If you're not familiar with the concept of endpoints/entry points, please read the [CosmWasm documentation](https://book.cosmwasm.com/basics/entry-points.html).*
6//!
7//! Endpoints are similar to CosmWasm's entry points but are more opinionated and standardized.
8//! We'll go over all the available endpoints and their functionality and use-cases. But first, let's go over the message format expected by an Abstract module.
9//!
10//! ## Message format
11//! Each Abstract module accepts a fixed message format that can be customized by the developer to add their own functionality.
12//!
13//! The base message format is defined [here](abstract_std::base) as follows:
14//! ```rust
15//! use abstract_std::ibc::IbcResponseMsg;
16//! use cosmwasm_std::Empty;
17//!
18//! /// EndpointMsg to the Base.
19//! #[cosmwasm_schema::cw_serde]
20//! pub enum ExecuteMsg<BaseMsg, ModuleMsg, ReceiveMsg = Empty> {
21//!     /// A base configuration message.
22//!     Base(BaseMsg),
23//!     /// An app request.
24//!     Module(ModuleMsg),
25//!     /// IbcReceive to process IBC callbacks
26//!     IbcCallback(IbcResponseMsg),
27//!     /// Receive endpoint for CW20 / external service integrations
28//!     Receive(ReceiveMsg),
29//! }
30//!
31//! #[cosmwasm_schema::cw_serde]
32//! pub struct InstantiateMsg<BaseMsg, ModuleMsg = Empty> {
33//!     /// base instantiate msg
34//!     pub base: BaseMsg,
35//!     /// custom instantiate msg
36//!     pub app: ModuleMsg,
37//! }
38//!
39//! #[cosmwasm_schema::cw_serde]
40//! pub enum QueryMsg<BaseMsg, ModuleMsg = Empty> {
41//!     /// A query message to the base.
42//!     Base(BaseMsg),
43//!     /// Custom query
44//!     Module(ModuleMsg),
45//! }
46//!
47//! #[cosmwasm_schema::cw_serde]
48//! pub struct MigrateMsg<BaseMsg = Empty, ModuleMsg = Empty> {
49//!     /// base migrate msg
50//!     pub base: BaseMsg,
51//!     /// custom migrate msg
52//!     pub app: ModuleMsg,
53//! }
54//!
55//! ```
56//! Every `Base` variant or field is implemented by the base contract such as the [App](https://crates.io/crates/abstract-app) and [API](https://crates.io/crates/abstract-adapter) contracts.
57//! These contracts then expose a type that requires the missing `App` variant types to be provided. The rust type system
58//! is then smart enough to accept the correct message type for each custom endpoint.
59//!
60//! Lets have a look at the available endpoints.
61//!
62//! ## Execute
63//! The execute endpoint is the most common endpoint. A base contract implements it to handle its `Base` variant messages and forwards `App` or `Receive` variant messages to a custom execute handler.
64//! Here's the implementation for the App contract:
65//!
66//!
67//! ```rust,ignore
68//! use abstract_sdk::std::app::{ExecuteMsg, AppExecuteMsg};
69//! use abstract_app::{AppContract, AppError};
70//! # use abstract_sdk::base::ExecuteEndpoint;
71//! # use cosmwasm_std::{DepsMut, Env, MessageInfo, Response};
72//! # use schemars::JsonSchema;
73//! # use serde::Serialize;
74//!
75//! impl <Error: From<cosmwasm_std::StdError> + From<AppError> + 'static, CustomExecMsg: Serialize + JsonSchema + AppExecuteMsg, CustomInitMsg, CustomQueryMsg, CustomMigrateMsg, SudoMsg: Serialize + JsonSchema >
76//! ExecuteEndpoint for AppContract <Error, CustomInitMsg, CustomExecMsg, CustomQueryMsg, CustomMigrateMsg, SudoMsg > {
77//!     
78//!     // Expected entrypoint ExecuteMsg type, imported from abstract_std.
79//!     // As you can see from the type definition, the `AppContract` accepts a custom `AppExecuteMsg`
80//!     // type that is inserted into the expected execute message.
81//!     type ExecuteMsg = ExecuteMsg<CustomExecMsg>;
82//!     
83//!     fn execute(
84//!         self,
85//!         deps: DepsMut,
86//!         env: Env,
87//!         info: MessageInfo,
88//!         msg: Self::ExecuteMsg,
89//!     ) -> Result<Response, Error> {
90//!         // match message on base message format with help of the type system
91//!         match msg {
92//!             ExecuteMsg::Base(exec_msg) => self
93//!                 .base_execute(deps, env, info, exec_msg)
94//!                 .map_err(From::from),
95//!             // handle the other messages with a custom handler set by the developer
96//!             // by passing `self` to the handlers we expose all the features and Adapters that the base contract provides through the SDK.
97//!             ExecuteMsg::App(request) => self.execute_handler()?(deps, env, info, self, request),
98//!             ExecuteMsg::IbcCallback(msg) => self.ibc_callback(deps, env, info, msg),
99//!            
100//!         }
101//!     }
102//! }
103//! ```
104//! Two variants reside in the ExecuteMsg enum:
105//!
106//! #### IbcCallback
107//! The IbcCallback endpoint is used to handle IBC responses that indicate that a certain IBC action has been completed.
108//!
109//!
110//! ## Instantiate
111//! The instantiate endpoint is used to initialize a base contract. It has a field for a custom `App` message that is passed to the instantiate handler.
112//!
113//! ## Query
114//! The query endpoint is used to query a contract. It is similar to the execute endpoint but it also forwards custom `App` variant queries.
115//!
116//! ## Migrate
117//! Same as the instantiate endpoint but for migrating a contract.
118//!
119//! ## Reply
120//! The reply endpoint is used to handle internal replies. Each reply handler is matched with a reply-id. Both are supplied to the contract builder.
121//!
122//! ## Sudo
123//! The sudo endpoint can only be called by the chain's governance address.
124
125mod execute;
126mod ibc_callback;
127mod instantiate;
128pub(crate) mod migrate;
129mod modules_ibc;
130mod query;
131mod reply;
132mod sudo;
133
134// Provide endpoints under ::base::traits::
135pub use execute::{CustomExecuteHandler, ExecuteEndpoint};
136pub use ibc_callback::IbcCallbackEndpoint;
137pub use instantiate::InstantiateEndpoint;
138pub use migrate::MigrateEndpoint;
139pub use modules_ibc::ModuleIbcEndpoint;
140pub use query::QueryEndpoint;
141pub use reply::ReplyEndpoint;
142pub use sudo::SudoEndpoint;