Note, that many of the things we implement in this article are for education purposes and they might need to be refined before production use.Moreover, all these V5 wallet contract interfaces are implemented in @ton/ton client library as WalletV5 contract wrapper class.
- Send external signed message
- Send internal signed message
- Send internal message from extension
Message structure
Message structure for V5 wallet contract is quite cumbersome and hard to read, it’s made for optimal (de-)serialization and not optimized for understanding. It is described in TL-B language and includes snake-cell pattern. We will try to get a grip of it by breaking down core data structures and how they are used. You can skip to Examples section, where we would use existing high-level libraries that abstract low level logic from the user.TL-B
This is TL-B for V5 wallet actions, it includes some complex TL-B patterns. You can also find it on GitHib, in the wallet repo.InnerRequest
field that dictates whats need to be done by wallet contract. In case of signed messages, the request needs to be verified, so InnerRequest
is wrapped in SignedRequest
structure, which contains necessary information for this.
Let’s break down these data structures.
Signed Request
Signed message is a message that was signed using owners private key from his dedicated keypair, method from asymmetric cryptography. Later this message will be verified on-chain using public key stored in wallet smart contract - read more about how ownership verification works. Before V5 standard, there was only one way to deliver signed message to wallet contract - via external-in message. However, external messages has certain limitations, e.g. you can only send external-out messages from the smart contracts themselves. This means that it wasn’t possible to deliver signed message from inside the blockchain, from another smart contract. V5 standard adds this functionality, partially enabling gassless transaction. BesidesInnerRequest
field that contains actual actions that will be performed, Signed message
structure contains usual wallet message fields that were in-place in previous versions, read more about them here.
Inner Request
Inner request is defined as follows:- Send Message Actions: Standard message sending with specified mode
- Extended Actions: Advanced wallet management operations
- Add Extension: Register new extension addresses
- Delete Extension: Remove extension addresses
- Set Signature Auth: Enable/disable signature-based authentication
out_actions
are snake-cell list of ordinary out messages, followed then by binary flag has_other_actions
and other_actions
extended action list.
Inner Request Structure
The Inner Request serialization follows this structure:Serialization Layout
The Inner Request is serialized in the following order:Examples
Here we will take a look at code examples in Typescript using low level serialization library @ton/core.How to create Inner Request
As per message structure section above,Inner Request
consists of 2 kinds of actions, basic send message actions and extended actions that affect contract behavior.
Let’s write code that handles packing for extended actions:
Inner Request
TL-B:
How to create and send Signed Request
There are several additional arguments that we need to create signed message besides the list of actions from previous section:walletId
seqno
privateKey
validUntil