sp_messenger/
endpoint.rs

1#[cfg(not(feature = "std"))]
2extern crate alloc;
3
4#[cfg(not(feature = "std"))]
5use alloc::vec::Vec;
6use frame_support::Parameter;
7use frame_support::weights::Weight;
8use parity_scale_codec::{Decode, Encode};
9use scale_info::TypeInfo;
10use sp_core::DecodeWithMemTracking;
11use sp_domains::ChainId;
12use sp_runtime::traits::Member;
13use sp_runtime::{DispatchError, DispatchResult};
14
15/// Represents a particular endpoint in a given Execution environment.
16pub type EndpointId = u64;
17
18/// Endpoint as defined in the formal spec.
19/// Endpoint is an application that can send and receive messages from other chains.
20#[derive(Debug, Encode, Decode, Clone, Eq, PartialEq, TypeInfo, DecodeWithMemTracking)]
21pub enum Endpoint {
22    /// Id of the endpoint on a specific chain.
23    Id(EndpointId),
24}
25
26/// Endpoint request or response payload.
27pub type EndpointPayload = Vec<u8>;
28
29/// Fee collected on src_chain for execution of XDM on both the src and dst chains.
30#[derive(Default, Debug, Encode, Decode, Clone, Eq, PartialEq, TypeInfo)]
31pub struct CollectedFee<Balance> {
32    /// Collected execution fee for src_chain.
33    pub src_chain_fee: Balance,
34    /// Collected execution fee for dst_chain.
35    pub dst_chain_fee: Balance,
36}
37
38/// Request sent by src_endpoint to dst_endpoint.
39#[derive(Debug, Encode, Decode, Clone, Eq, PartialEq, TypeInfo)]
40pub struct EndpointRequest {
41    pub src_endpoint: Endpoint,
42    pub dst_endpoint: Endpoint,
43    pub payload: EndpointPayload,
44}
45
46/// Request sent by src_endpoint to dst_endpoint with collected Fee
47#[derive(Debug, Encode, Decode, Clone, Eq, PartialEq, TypeInfo)]
48pub struct EndpointRequestWithCollectedFee<Balance> {
49    pub req: EndpointRequest,
50    pub collected_fee: CollectedFee<Balance>,
51}
52
53impl<Balance> From<EndpointRequestWithCollectedFee<Balance>> for EndpointRequest {
54    fn from(value: EndpointRequestWithCollectedFee<Balance>) -> Self {
55        value.req
56    }
57}
58
59impl<Balance: Default> From<EndpointRequest> for EndpointRequestWithCollectedFee<Balance> {
60    fn from(value: EndpointRequest) -> Self {
61        EndpointRequestWithCollectedFee {
62            req: value,
63            collected_fee: CollectedFee::default(),
64        }
65    }
66}
67
68/// Response for the message request.
69pub type EndpointResponse = Result<EndpointPayload, DispatchError>;
70
71/// Sender provides abstraction on sending messages to other chains.
72pub trait Sender<AccountId> {
73    /// Unique Id of the message between dst_chain and src_chain.
74    type MessageId: Parameter + Member + Copy + Default;
75    /// Sends a message to dst_chain_id.
76    fn send_message(
77        sender: &AccountId,
78        dst_chain_id: ChainId,
79        req: EndpointRequest,
80    ) -> Result<Self::MessageId, DispatchError>;
81
82    /// Only used in benchmark to prepare for a upcoming `send_message` call to
83    /// ensure it will succeed.
84    #[cfg(feature = "runtime-benchmarks")]
85    fn unchecked_open_channel(dst_chain_id: ChainId) -> Result<(), DispatchError>;
86}
87
88/// Handler to
89///  - handle message request from other chains.
90///  - handle requested message responses from other chains.
91pub trait EndpointHandler<MessageId> {
92    /// Triggered by pallet-messenger when a new inbox message is received and bound for this handler.
93    fn message(
94        &self,
95        src_chain_id: ChainId,
96        message_id: MessageId,
97        req: EndpointRequest,
98        // if pre_checks failed, implementation should reject the transfer
99        pre_check_result: DispatchResult,
100    ) -> EndpointResponse;
101
102    /// Return the maximal possible consume weight of `message`
103    fn message_weight(&self) -> Weight;
104
105    /// Triggered by pallet-messenger when a response for a request is received from dst_chain_id.
106    fn message_response(
107        &self,
108        dst_chain_id: ChainId,
109        message_id: MessageId,
110        req: EndpointRequest,
111        resp: EndpointResponse,
112    ) -> DispatchResult;
113
114    /// Return the maximal possible consume weight of `message_response`
115    fn message_response_weight(&self) -> Weight;
116}
117
118#[cfg(feature = "runtime-benchmarks")]
119pub struct BenchmarkEndpointHandler;
120
121#[cfg(feature = "runtime-benchmarks")]
122impl<MessageId> EndpointHandler<MessageId> for BenchmarkEndpointHandler {
123    fn message(
124        &self,
125        _src_chain_id: ChainId,
126        _message_id: MessageId,
127        _req: EndpointRequest,
128        _pre_check_result: DispatchResult,
129    ) -> EndpointResponse {
130        Ok(Vec::new())
131    }
132
133    fn message_weight(&self) -> Weight {
134        Weight::zero()
135    }
136
137    fn message_response(
138        &self,
139        _dst_chain_id: ChainId,
140        _message_id: MessageId,
141        _req: EndpointRequest,
142        _resp: EndpointResponse,
143    ) -> DispatchResult {
144        Ok(())
145    }
146
147    fn message_response_weight(&self) -> Weight {
148        Weight::zero()
149    }
150}