Skip to content

Add and stabilize a basic interface for signing transactions #2468

@jsdw

Description

@jsdw

We currently have a smoldot-v1 interface for communicating with a Smoldot in an extension, and a substrate-connect-unstable interface for talking with extensions like Substrate Connect (this hasn't been given much love I think).

What we want is to be able to stabilise some interface that libraries like PJS can use to have transactions signed. If we have this, we can migrate things like PJS to using this new interface so that they aren't stuck relying on the PJS based one which has various issues including no standard way to handle new signed extensions.

How about an interface like this?:

/** The interface we'll expose */
type Interface = {
    /** Subscribe to acocunts. The callback fires whenever the list of acocunts changes */
    subscribeAccounts: (callback: (accounts: Account[]) => void) => void
    /** Sign a transaction, handing back the signed bytes ready to submit */
    signTransaction: (transaction: Transaction) => Promise<SignedTransaction>
}

/** Details about an available account */
type Account = {
    /** Often this will be a MultiAddress, or an AccountID20 on eth chains */
    address: Bytes
    /** Name to present with the account. */
    name: string
}

/** 
 * The information required to construct a transaction. We can ask to 
 * construct either a V4 or a V5 transaction.
 */
type Transaction = {
    output: 'v4-signed',
    address: Bytes,
    transactionExtensions: Bytes,
    callData: Bytes
} | {
    output: 'v5-signed',
    address: Bytes,
    transactionExtensionsVersion: number,
    transactionExtensions: Bytes,
    callData: Bytes
} | {
    output: 'v5-general',
    transactionExtensionsVersion: number,
    transactionExtensions: Bytes,
    callData: Bytes
}

/** Bytes representing the signed transaction, ready to submit */
type SignedTransaction = ArrayBuffer

/** Some binary data, in the form of a hex encoded string (0x prefixed) or raw bytes */
type Bytes = string | Uint8Array | ArrayBuffer;

The aim here is to be fairly minimal, but allow getting accounts (so that we know what the extension is able to sign) and signing transactions (which here allows you to ask for a V4 or V5 transaction and then provide the relevant details required to construct it.

  • Is there anything that I'm missing?
  • Can we simplify it even more?
  • The account address here is whatever type the chain has configured, so that it can be put into the tx with the help of metadata. Is this reasonable? Should it be ss58 formatted or raw bytes as above (but that would then be an issue for eth chains)? Can extensions migrate to this easily enough?
  • Should we also add a keypair: type KeypairType = 'ed25519' | 'sr25519' | 'ecdsa' | 'ethereum' to the account info, or is it enough to rely on the address type + metadata to decode and understand. I think we don't need the extra info.

\cc @josepot

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions