Skip to content

Conversation

grod220
Copy link
Member

@grod220 grod220 commented Aug 12, 2025

This PR extends the SyncMetadataToToken2022 instruction to support syncing metadata from an spl-token's metaplex PDA to the wrapped token's metadata extension.

Note that this copies over non-overlapping fields as addditional_metadata serialized to json. Up for discussion if this is ok or overkill.


[workspace.dependencies]
anyhow = "1.0.98"
borsh = "0.10.4"
Copy link
Member Author

Choose a reason for hiding this comment

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

The version of borsh synced to the version used in mpl-token-metadata due to compatibility reasons

Comment on lines +9 to +11
fn extract_additional_metadata(
metaplex_metadata: &MetaplexMetadata,
) -> Result<Vec<(String, String)>, ProgramError> {
Copy link
Member Author

Choose a reason for hiding this comment

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

The idea behind this is to convert the remaining metaplex metadata fields to token-2022-metadata-ext-compatible. And for that it has to be added to the additional_metadata: Vec<(String, String)> field. Using serde to serialize the value. This may be overkill 🤷 . Worth discussing.

Choose a reason for hiding this comment

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

Yeah this works for me! Nice!

@grod220 grod220 force-pushed the sync-metadata-token-2022-pt-2 branch from 4b687cd to 825aa70 Compare August 12, 2025 16:17
Comment on lines +131 to +132
/// 4. `[]` (Optional) `Metaplex` Metadata PDA. Required if the unwrapped
/// mint is an `spl-token` mint.

Choose a reason for hiding this comment

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

Shoot, this actually reminds me that TokenMetadata can actually exist in a separate account for Token2022 mints as well. The MetadataPointer can point to another account.

As followup work, maybe here in this optional account slot, we can just say "Token Metadata account, if separate" or something like that, and also mention the Metaplex PDA?

Copy link
Member Author

Choose a reason for hiding this comment

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

Oh! Totally forgot about that case. That feels like independent conditional branch of work. Cool if it goes in the next PR?

Comment on lines +9 to +11
fn extract_additional_metadata(
metaplex_metadata: &MetaplexMetadata,
) -> Result<Vec<(String, String)>, ProgramError> {

Choose a reason for hiding this comment

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

Yeah this works for me! Nice!

Comment on lines +557 to +562
// Source is Token-2022: read from extension
let unwrapped_mint_data = unwrapped_mint_info.try_borrow_data()?;
let unwrapped_mint_state = PodStateWithExtensions::<PodMint>::unpack(&unwrapped_mint_data)?;
unwrapped_mint_state
.get_variable_len_extension::<TokenMetadata>()
.map_err(|_| TokenWrapError::UnwrappedMintHasNoMetadata)?

Choose a reason for hiding this comment

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

Here is where you'd have a check to see if the address in the MetadataPointer is the mint, or if it's another account, which should have been provided last.

@grod220 grod220 requested a review from buffalojoec August 15, 2025 18:05
@grod220 grod220 merged commit 743a50c into main Aug 15, 2025
10 checks passed
@grod220 grod220 deleted the sync-metadata-token-2022-pt-2 branch August 15, 2025 22:00
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.

2 participants