Skip to main content

snowbridge_inbound_queue_primitives/v2/
traits.rs

1// SPDX-License-Identifier: Apache-2.0
2// SPDX-FileCopyrightText: 2025 Snowfork <hello@snowfork.com>
3// SPDX-FileCopyrightText: 2021-2025 Parity Technologies (UK) Ltd.
4use super::Message;
5use sp_runtime::DispatchError;
6use xcm::latest::{SendError, Xcm};
7use Debug;
8
9/// Converts an inbound message from Ethereum to an XCM message that can be
10/// executed on a parachain.
11pub trait ConvertMessage {
12	fn convert(message: Message) -> Result<Xcm<()>, ConvertMessageError>;
13}
14
15/// Reason why a message conversion failed.
16#[derive(Copy, Clone, Debug, PartialEq)]
17pub enum ConvertMessageError {
18	/// Invalid foreign ERC-20 token ID
19	InvalidAsset,
20	/// Cannot reachor a foreign ERC-20 asset location.
21	CannotReanchor,
22	/// Invalid network specified (not from Ethereum)
23	InvalidNetwork,
24}
25
26/// Reason why a message processor failed.
27#[derive(Clone, Debug, PartialEq)]
28pub enum MessageProcessorError {
29	/// Message processing failed.
30	ProcessMessage(DispatchError),
31	/// Message conversion failed.
32	ConvertMessage(ConvertMessageError),
33	/// Message sending failed.
34	SendMessage(SendError),
35}
36
37/// Trait to define the logic for checking and processing inbound messages.
38pub trait MessageProcessor<AccountId> {
39	/// Lightweight function to check if this processor can handle the message
40	fn can_process_message(relayer: &AccountId, message: &Message) -> bool;
41	/// Process the message and return the message ID
42	fn process_message(
43		relayer: AccountId,
44		message: Message,
45	) -> Result<[u8; 32], MessageProcessorError>;
46}
47
48#[impl_trait_for_tuples::impl_for_tuples(10)]
49impl<AccountId> MessageProcessor<AccountId> for Tuple {
50	fn can_process_message(relayer: &AccountId, message: &Message) -> bool {
51		for_tuples!( #(
52 			match Tuple::can_process_message(&relayer, &message) {
53				true => {
54					return true;
55				},
56				_ => {}
57			}
58		)* );
59
60		false
61	}
62
63	fn process_message(
64		relayer: AccountId,
65		message: Message,
66	) -> Result<[u8; 32], MessageProcessorError> {
67		for_tuples!( #(
68 			match Tuple::can_process_message(&relayer, &message) {
69				true => {
70					return Tuple::process_message(relayer, message)
71				},
72				_ => {}
73			}
74		)* );
75
76		Err(MessageProcessorError::ProcessMessage(DispatchError::Other(
77			"No handler found for message!",
78		)))
79	}
80}