0

I'm trying to call a specific endpoint on a Solana smart contract using @solana-web3 and I can't quite figure out how todo that. Iv'e seen it done like this:

const buffer = Buffer.from("hello");
  const instruction = new web3.TransactionInstruction({
    keys: [{ pubkey: fromWallet.publicKey, isSigner: false, isWritable: true }],
    programId: new web3.PublicKey(metaDataProgramID),
    data: buffer,
  });
  const confirmation = await web3.sendAndConfirmTransaction(
    connection,
    new web3.Transaction().add(instruction),
    [fromWallet],
    {
      commitment: "singleGossip",
      preflightCommitment: "singleGossip",
    }
  );`

But I'm not sure how todo it will a smart contract like this with multiple end points. Because how would one tell the smart contract what endpoint to use and what data to pass to that endpoint?:

pub fn process_instruction<'a>(
    program_id: &'a Pubkey,
    accounts: &'a [AccountInfo<'a>],
    input: &[u8],
) -> ProgramResult {
    let instruction = MetadataInstruction::try_from_slice(input)?;
    match instruction {
        MetadataInstruction::CreateMetadataAccount(args) => {
            msg!("Instruction: Create Metadata Accounts");
            process_create_metadata_accounts(
                program_id,
                accounts,
                args.data,
                false,
                args.is_mutable,
            )
        }
        MetadataInstruction::UpdateMetadataAccount(args) => {
            msg!("Instruction: Update Metadata Accounts");
            process_update_metadata_accounts(
                program_id,
                accounts,
                args.data,
                args.update_authority,
                args.primary_sale_happened,
            )
        }
        MetadataInstruction::DeprecatedCreateMasterEdition(args) => {
            msg!("Instruction: Deprecated Create Master Edition");
            process_deprecated_create_master_edition(program_id, accounts, args.max_supply)
        }
        MetadataInstruction::DeprecatedMintNewEditionFromMasterEditionViaPrintingToken => {
            msg!("Instruction: Deprecated Mint New Edition from Master Edition Via Token");
            process_deprecated_mint_new_edition_from_master_edition_via_printing_token(
                program_id, accounts,
            )
        }
        MetadataInstruction::UpdatePrimarySaleHappenedViaToken => {
            msg!("Instruction: Update primary sale via token");
            process_update_primary_sale_happened_via_token(program_id, accounts)
        }
        MetadataInstruction::MintNewEditionFromMasterEditionViaVaultProxy(args) => {
            msg!("Instruction: Mint New Edition from Master Edition Via Vault Proxy");
            process_mint_new_edition_from_master_edition_via_vault_proxy(
                program_id,
                accounts,
                args.edition,
            )
        }
        MetadataInstruction::PuffMetadata => {
            msg!("Instruction: Puff Metadata");
            process_puff_metadata_account(program_id, accounts)
        }
    }
}

Here is the full code for the smart contract: https://github.com/metaplex-foundation/metaplex/tree/master/rust/token-metadata/program

Max Campbell
  • 595
  • 9
  • 22
  • I think you're missing some of the code. So the flow is like you pass in some integer along the transaction from the client. Then in the rust program you read this integer and call the corresponding instrcution. May I suggest you to look into [Anchor](https://project-serum.github.io/anchor/getting-started/introduction.html). This would make things a lot easier for writing solana programs. – munanadi Sep 12 '21 at 10:41

1 Answers1

2

The choice of "endpoint" to call on a smart contract in Solana is decided by that buffer that you passed in as the data of the instruction. Given that data, the program decides which instruction processor to call.

In your example, the choice of instruction is likely based on the first byte of the instruction, so 0 may correspond to MetadataInstruction::CreateMetadataAccount.

Your best bet is to use a package provided by the program developer. In the case of the metadata program, the instruction and type definitions live at: https://github.com/solana-labs/oyster/blob/e79c5a66ed5290d3fb752f4cd6b4e90f7974ec94/packages/common/src/actions/metadata.ts

Jon C
  • 7,019
  • 10
  • 17