XCM builder pattern improvement - Accept impl Into<T> instead of just T (#3708)

The XCM builder pattern lets you build xcms like so:

```rust
let xcm = Xcm::builder()
    .withdraw_asset((Parent, 100u128).into())
    .buy_execution((Parent, 1u128).into())
    .deposit_asset(All.into(), AccountId32 { id: [0u8; 32], network: None }.into())
    .build();
```

All the `.into()` become quite annoying to have to write.
I accepted `impl Into<T>` instead of `T` in the generated methods from
the macro.
Now the previous example can be simplified as follows:

```rust
let xcm = Xcm::builder()
    .withdraw_asset((Parent, 100u128))
    .buy_execution((Parent, 1u128))
    .deposit_asset(All, [0u8; 32])
    .build();
```

---------

Co-authored-by: Bastian Köcher <git@kchr.de>
Co-authored-by: command-bot <>
Co-authored-by: Adrian Catangiu <adrian@parity.io>
This commit is contained in:
Francisco Aguirre
2024-04-04 14:40:21 +02:00
committed by GitHub
parent bcb4d137c9
commit c130ea9939
5 changed files with 59 additions and 16 deletions
+12 -6
View File
@@ -107,7 +107,8 @@ fn generate_builder_raw_impl(name: &Ident, data_enum: &DataEnum) -> TokenStream2
.collect();
let arg_types: Vec<_> = fields.unnamed.iter().map(|field| &field.ty).collect();
quote! {
pub fn #method_name(mut self, #(#arg_names: #arg_types),*) -> Self {
pub fn #method_name(mut self, #(#arg_names: impl Into<#arg_types>),*) -> Self {
#(let #arg_names = #arg_names.into();)*
self.instructions.push(#name::<Call>::#variant_name(#(#arg_names),*));
self
}
@@ -117,7 +118,8 @@ fn generate_builder_raw_impl(name: &Ident, data_enum: &DataEnum) -> TokenStream2
let arg_names: Vec<_> = fields.named.iter().map(|field| &field.ident).collect();
let arg_types: Vec<_> = fields.named.iter().map(|field| &field.ty).collect();
quote! {
pub fn #method_name(mut self, #(#arg_names: #arg_types),*) -> Self {
pub fn #method_name(mut self, #(#arg_names: impl Into<#arg_types>),*) -> Self {
#(let #arg_names = #arg_names.into();)*
self.instructions.push(#name::<Call>::#variant_name { #(#arg_names),* });
self
}
@@ -188,8 +190,9 @@ fn generate_builder_impl(name: &Ident, data_enum: &DataEnum) -> Result<TokenStre
let arg_types: Vec<_> = fields.unnamed.iter().map(|field| &field.ty).collect();
quote! {
#(#docs)*
pub fn #method_name(self, #(#arg_names: #arg_types),*) -> XcmBuilder<Call, LoadedHolding> {
pub fn #method_name(self, #(#arg_names: impl Into<#arg_types>),*) -> XcmBuilder<Call, LoadedHolding> {
let mut new_instructions = self.instructions;
#(let #arg_names = #arg_names.into();)*
new_instructions.push(#name::<Call>::#variant_name(#(#arg_names),*));
XcmBuilder {
instructions: new_instructions,
@@ -203,8 +206,9 @@ fn generate_builder_impl(name: &Ident, data_enum: &DataEnum) -> Result<TokenStre
let arg_types: Vec<_> = fields.named.iter().map(|field| &field.ty).collect();
quote! {
#(#docs)*
pub fn #method_name(self, #(#arg_names: #arg_types),*) -> XcmBuilder<Call, LoadedHolding> {
pub fn #method_name(self, #(#arg_names: impl Into<#arg_types>),*) -> XcmBuilder<Call, LoadedHolding> {
let mut new_instructions = self.instructions;
#(let #arg_names = #arg_names.into();)*
new_instructions.push(#name::<Call>::#variant_name { #(#arg_names),* });
XcmBuilder {
instructions: new_instructions,
@@ -249,8 +253,9 @@ fn generate_builder_impl(name: &Ident, data_enum: &DataEnum) -> Result<TokenStre
fields.named.iter().map(|field| &field.ty).collect();
quote! {
#(#docs)*
pub fn #method_name(self, #(#arg_names: #arg_types),*) -> XcmBuilder<Call, AnythingGoes> {
pub fn #method_name(self, #(#arg_names: impl Into<#arg_types>),*) -> XcmBuilder<Call, AnythingGoes> {
let mut new_instructions = self.instructions;
#(let #arg_names = #arg_names.into();)*
new_instructions.push(#name::<Call>::#variant_name { #(#arg_names),* });
XcmBuilder {
instructions: new_instructions,
@@ -308,8 +313,9 @@ fn generate_builder_unpaid_impl(name: &Ident, data_enum: &DataEnum) -> Result<To
Ok(quote! {
impl<Call> XcmBuilder<Call, ExplicitUnpaidRequired> {
#(#docs)*
pub fn #unpaid_execution_method_name(self, #(#arg_names: #arg_types),*) -> XcmBuilder<Call, AnythingGoes> {
pub fn #unpaid_execution_method_name(self, #(#arg_names: impl Into<#arg_types>),*) -> XcmBuilder<Call, AnythingGoes> {
let mut new_instructions = self.instructions;
#(let #arg_names = #arg_names.into();)*
new_instructions.push(#name::<Call>::#unpaid_execution_ident { #(#arg_names),* });
XcmBuilder {
instructions: new_instructions,