Skip to content

Add DefaultParams to allow more transaction extensions to be used when calling _default() methods#1979

Merged
jsdw merged 5 commits intomasterfrom
jsdw-default-params
Apr 4, 2025
Merged

Add DefaultParams to allow more transaction extensions to be used when calling _default() methods#1979
jsdw merged 5 commits intomasterfrom
jsdw-default-params

Conversation

@jsdw
Copy link
Copy Markdown
Collaborator

@jsdw jsdw commented Apr 1, 2025

We currently rely on extrinsic parameters implementing Default on these two methods of TxClient:

    pub async fn sign_and_submit_then_watch_default<Call, Signer>(
        &mut self,
        call: &Call,
        signer: &Signer,
    ) -> Result<TxProgress<T, C>, Error>
    where
        Call: Payload,
        Signer: SignerT<T>,
        <T::ExtrinsicParams as ExtrinsicParams<T>>::Params: Default, // <-- here
    {
        self.sign_and_submit_then_watch(call, signer, DefaultParams::default_params())
            .await
    }

    pub async fn sign_and_submit_default<Call, Signer>(
        &mut self,
        call: &Call,
        signer: &Signer,
    ) -> Result<T::Hash, Error>
    where
        Call: Payload,
        Signer: SignerT<T>,
        <T::ExtrinsicParams as ExtrinsicParams<T>>::Params: Default, // <-- here
    {
        self.sign_and_submit(call, signer, DefaultParams::default_params())
            .await
    }

Extrinsic params are, by default, a tuple containing an entry for each transaction extension configured via AnyOf. Our default transaction extensions are this:

transaction_extensions::AnyOf<
    T,
    (
        transaction_extensions::VerifySignature<T>,
        transaction_extensions::CheckSpecVersion,
        transaction_extensions::CheckTxVersion,
        transaction_extensions::CheckNonce,
        transaction_extensions::CheckGenesis<T>,
        transaction_extensions::CheckMortality<T>,
        transaction_extensions::ChargeAssetTxPayment<T>,
        transaction_extensions::ChargeTransactionPayment,
        transaction_extensions::CheckMetadataHash,
    ),
>;

And AnyOf is implemented such that the parameters to configure each extension are expected in a tuple with a size matching the extensions above.

We currently have support for 9 default transaction extensions above, but if this number were to exceed 12 (which is the max tuple size that Rust implements Default for), then we could no longer use AnyOf in conjunction with our _default methods, since the parameters would no longer implement Default.

So, we add a DefaultParams trait instead, which supports up to 26 entries in the tuple (as long as each of those impls Default), matching the number of tuple entries AnyOf supports.

The downside is that a user going off the beaten path will need to implement DefaultParams instead of Default for their own params if they want to use the _default methods, but this is likely to be a rare case.

Closes #1975.

@jsdw jsdw requested a review from a team as a code owner April 1, 2025 15:18
Copy link
Copy Markdown
Contributor

@gui1117 gui1117 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good to me

@jsdw jsdw merged commit b3317c5 into master Apr 4, 2025
13 checks passed
@jsdw jsdw deleted the jsdw-default-params branch April 4, 2025 09:08
@jsdw jsdw mentioned this pull request May 9, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

signed_extensions::AnyOf don't implement default for more than 12 extensions.

4 participants