From 1705d1637618eda0dabb06384aa14e8a0c960650 Mon Sep 17 00:00:00 2001 From: "Jean Marchand (Exotic Markets)" Date: Wed, 7 Jun 2023 16:29:23 +0200 Subject: [PATCH] docs: Add doc for InitSpace macro (#2521) --- docs/src/pages/docs/space.md | 34 ++++++++++++++++++++++++++++++++- lang/derive/accounts/src/lib.rs | 2 +- 2 files changed, 34 insertions(+), 2 deletions(-) diff --git a/docs/src/pages/docs/space.md b/docs/src/pages/docs/space.md index 45bb46a756..40bd6ba971 100644 --- a/docs/src/pages/docs/space.md +++ b/docs/src/pages/docs/space.md @@ -12,6 +12,8 @@ so there the `C` layout applies. In addition to the space for the account data, you have to add `8` to the `space` constraint for Anchor's internal discriminator (see the example). +## Type chart + | Types | Space in bytes | Details/Example | | ---------- | ----------------------------- | ----------------------------------------------------------------------------------------------- | | bool | 1 | would only require 1 bit but still uses 1 byte | @@ -29,7 +31,7 @@ In addition to the space for the account data, you have to add `8` to the `space | f32 | 4 | serialization will fail for NaN | | f64 | 8 | serialization will fail for NaN | -# Example +## Example ```rust #[account] @@ -59,3 +61,33 @@ pub struct InitializeMyData<'info> { pub system_program: Program<'info, System> } ``` + +## The InitSpace macro + +Sometimes it can be difficult to calculate the initial space of an account. This macro will add an `INIT_SPACE` constant to the structure. It is not necessary for the structure to contain the `#[account]` macro to generate the constant. Here's an example: + +```rust +#[account] +#[derive(InitSpace)] +pub struct ExampleAccount { + pub data: u64, + #[max_len(50)] + pub string_one: String, + #[max_len(10, 5)] + pub nested: Vec>, +} + +#[derive(Accounts)] +pub struct Initialize<'info> { + #[account(mut)] + pub payer: Signer<'info>, + pub system_program: Program<'info, System>, + #[account(init, payer = payer, space = 8 + ExampleAccount::INIT_SPACE)] + pub data: Account<'info, ExampleAccount>, +} +``` + +A few important things to know: + +- Don't forget the discriminator when defining `space` +- The `max_len` length represents the length of the structure, not the total length. (ie: the `max_len` of a Vec will be `max_len` \* 4) diff --git a/lang/derive/accounts/src/lib.rs b/lang/derive/accounts/src/lib.rs index 9a04c866ee..4f9348ed58 100644 --- a/lang/derive/accounts/src/lib.rs +++ b/lang/derive/accounts/src/lib.rs @@ -117,7 +117,7 @@ use syn::parse_macro_input; /// The given space number is the size of the account in bytes, so accounts that hold /// a variable number of items such as a Vec should allocate sufficient space for all items that may /// be added to the data structure because account size is fixed. -/// Check out the space reference +/// Check out the space reference /// and the borsh library /// (which anchor uses under the hood for serialization) specification to learn how much /// space different data structures require.