IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 区块链 -> 150-Solana入门(十四)- 创建初始化Mint -> 正文阅读

[区块链]150-Solana入门(十四)- 创建初始化Mint

今天来看一个很重要的问题

就是创建账户,初始化Mint,创建Token账户

我们先来看客户端中的tx

    const mint_tx = new anchor.web3.Transaction().add(
        anchor.web3.SystemProgram.createAccount({
            fromPubkey: provider.wallet.publicKey,
            newAccountPubkey: mintKey.publicKey,
            space: MINT_SIZE,
            programId: TOKEN_PROGRAM_ID,
            lamports,
        }),
        createInitializeMintInstruction(
            mintKey.publicKey,
            0,
            provider.wallet.publicKey,
            provider.wallet.publicKey,
        ),
        createAssociatedTokenAccountInstruction(
            provider.wallet.publicKey,
            nftTokenAccount,
            provider.wallet.publicKey,
            mintKey.publicKey
        )
    );
    const res = await program.provider.sendAndConfirm(mint_tx, [mintKey]);

那么我们需要把

createAccount
createInitializeMintInstruction
createAssociatedTokenAccountInstruction

这三个指令放到合约中去调用

试试看吧

试了很久很久

试了很多很多很多很多次

算是成功了一半

invoke的方式或者是anchor cpi的方式

分开调用的情况下都是成功的

但是合在一起就是不成功

真的很头疼

先看看invoke的方式

use anchor_lang::prelude::*;
use anchor_lang::solana_program;
use anchor_spl::token::spl_token;

use crate::solana_program::program::invoke;

declare_id!("HzMAyAPXaDKvtApQVqz1CSL8vHKRxF3FiM86WraCHgSs");

#[program]
pub mod game01_create_mint {
    use super::*;

    pub fn create(
        ctx: Context<Create>,
        lamports: u64,
        space: u64,
    ) -> Result<()> {
        let account_infos = vec![
            ctx.accounts.system_program.to_account_info(),
            ctx.accounts.token_program.to_account_info(),
            ctx.accounts.from.to_account_info(),
            ctx.accounts.to.to_account_info(),
        ];
        invoke(
            &solana_program::system_instruction::create_account(
                &ctx.accounts.from.key(),
                &ctx.accounts.to.key(),
                lamports,
                space,
                &ctx.accounts.token_program.key(),
            ),
            account_infos.as_slice(),
        )?;

        Ok(())
    }

    pub fn init_mint(
        ctx: Context<InitMint>,
    ) -> Result<()> {
        let account_infos = vec![
            ctx.accounts.system_program.to_account_info(),
            ctx.accounts.token_program.to_account_info(),
            ctx.accounts.mint.to_account_info(),
            ctx.accounts.rent.to_account_info(),
            ctx.accounts.authority.to_account_info(),
            ctx.accounts.freeze_authority.to_account_info(),
        ];
        invoke(
            &spl_token::instruction::initialize_mint(
                ctx.accounts.token_program.key,
                ctx.accounts.mint.key,
                ctx.accounts.authority.key,
                Some(ctx.accounts.freeze_authority.key),
                9,
            )?,
            account_infos.as_slice(),
        )?;

        Ok(())
    }

    pub fn create_init_01(
        ctx: Context<CreateInit01>,
        lamports: u64,
        space: u64,
    ) -> Result<()> {
        msg!("Create Account");
        let account_infos = vec![
            ctx.accounts.system_program.to_account_info(),
            ctx.accounts.token_program.to_account_info(),
            ctx.accounts.from.to_account_info(),
            ctx.accounts.to.to_account_info(),
        ];
        invoke(
            &solana_program::system_instruction::create_account(
                &ctx.accounts.from.key(),
                &ctx.accounts.to.key(),
                lamports,
                space,
                &ctx.accounts.token_program.key(),
            ),
            account_infos.as_slice(),
        )?;

        msg!("Initialize Mint");
        let account_infos = vec![
            ctx.accounts.system_program.to_account_info(),
            ctx.accounts.token_program.to_account_info(),
            ctx.accounts.mint.to_account_info(),
            ctx.accounts.rent.to_account_info(),
            ctx.accounts.authority.to_account_info(),
            ctx.accounts.freeze_authority.to_account_info(),
        ];
        invoke(
            &spl_token::instruction::initialize_mint(
                ctx.accounts.token_program.key,
                ctx.accounts.mint.key,
                ctx.accounts.authority.key,
                Some(ctx.accounts.freeze_authority.key),
                9,
            )?,
            account_infos.as_slice(),
        )?;

        Ok(())
    }
}

#[derive(Accounts)]
pub struct Create<'info> {
    pub system_program: Program<'info, System>,

    /// CHECK: This is not dangerous because we don't read or write from this account
    pub token_program: AccountInfo<'info>,

    /// CHECK: This is not dangerous because we don't read or write from this account
    pub from: AccountInfo<'info>,
    /// CHECK: This is not dangerous because we don't read or write from this account
    pub to: AccountInfo<'info>,


    pub signer: Signer<'info>,
}

#[derive(Accounts)]
pub struct InitMint<'info> {
    pub system_program: Program<'info, System>,

    /// CHECK: This is not dangerous because we don't read or write from this account
    pub token_program: AccountInfo<'info>,
    /// CHECK: This is not dangerous because we don't read or write from this account
    pub rent: AccountInfo<'info>,

    /// CHECK: This is not dangerous because we don't read or write from this account
    pub mint: AccountInfo<'info>,
    /// CHECK: This is not dangerous because we don't read or write from this account
    pub authority: AccountInfo<'info>,
    /// CHECK: This is not dangerous because we don't read or write from this account
    pub freeze_authority: AccountInfo<'info>,


    pub signer: Signer<'info>,
}

#[derive(Accounts)]
pub struct CreateInit01<'info> {
    pub system_program: Program<'info, System>,

    /// CHECK: This is not dangerous because we don't read or write from this account
    pub token_program: AccountInfo<'info>,
    /// CHECK: This is not dangerous because we don't read or write from this account
    pub rent: AccountInfo<'info>,

    /// CHECK: This is not dangerous because we don't read or write from this account
    pub mint: AccountInfo<'info>,
    /// CHECK: This is not dangerous because we don't read or write from this account
    pub authority: AccountInfo<'info>,
    /// CHECK: This is not dangerous because we don't read or write from this account
    pub freeze_authority: AccountInfo<'info>,

    /// CHECK: This is not dangerous because we don't read or write from this account
    pub from: AccountInfo<'info>,
    /// CHECK: This is not dangerous because we don't read or write from this account
    pub to: AccountInfo<'info>,

    pub signer: Signer<'info>,
}
 

然后是anchro cpi的方式

use anchor_lang::prelude::*;
use anchor_lang::system_program::{create_account, CreateAccount};
use anchor_spl::token::{initialize_mint, InitializeMint};

declare_id!("HzMAyAPXaDKvtApQVqz1CSL8vHKRxF3FiM86WraCHgSs");

#[program]
pub mod game01_create_mint {
    use super::*;

    pub fn create(
        ctx: Context<Create>,
        lamports: u64,
        space: u64,
    ) -> Result<()> {
        let cpi_accounts = CreateAccount {
            from: ctx.accounts.from.to_account_info(),
            to: ctx.accounts.to.to_account_info(),
        };
        let cpi_program = ctx.accounts.system_program.to_account_info();
        let cpi_ctx = CpiContext::new(cpi_program, cpi_accounts);
        create_account(cpi_ctx, lamports, space, ctx.accounts.token_program.key)?;

        Ok(())
    }

    pub fn init_mint(
        ctx: Context<InitMint>,
    ) -> Result<()> {
        let cpi_accounts = InitializeMint {
            mint: ctx.accounts.mint.to_account_info(),
            rent: ctx.accounts.rent.to_account_info(),
        };
        let cpi_program = ctx.accounts.token_program.to_account_info();
        let cpi_ctx = CpiContext::new(cpi_program, cpi_accounts);
        initialize_mint(cpi_ctx, 9, ctx.accounts.authority.key, None)?;

        Ok(())
    }

    pub fn create_init_01(
        ctx: Context<CreateInit01>,
        lamports: u64,
        space: u64,
    ) -> Result<()> {
        msg!("Create Account");
        let cpi_accounts = CreateAccount {
            from: ctx.accounts.authority.to_account_info(),
            to: ctx.accounts.mint.to_account_info(),
        };
        let cpi_program = ctx.accounts.system_program.to_account_info();
        let cpi_ctx = CpiContext::new(cpi_program, cpi_accounts);
        create_account(cpi_ctx, lamports, space, ctx.accounts.token_program.key)?;

        msg!("Initialize Mint");
        let cpi_accounts = InitializeMint {
            mint: ctx.accounts.mint.to_account_info(),
            rent: ctx.accounts.rent.to_account_info(),
        };
        let cpi_program = ctx.accounts.token_program.to_account_info();
        let cpi_ctx = CpiContext::new(cpi_program, cpi_accounts);
        initialize_mint(cpi_ctx, 9, ctx.accounts.authority.key, None)?;

        Ok(())
    }
}

#[derive(Accounts)]
pub struct Create<'info> {
    pub system_program: Program<'info, System>,

    /// CHECK: This is not dangerous because we don't read or write from this account
    pub token_program: AccountInfo<'info>,

    /// CHECK: This is not dangerous because we don't read or write from this account
    pub from: AccountInfo<'info>,
    /// CHECK: This is not dangerous because we don't read or write from this account
    pub to: AccountInfo<'info>,

    #[account(mut)]
    pub signer: Signer<'info>,
}

#[derive(Accounts)]
pub struct InitMint<'info> {
    pub system_program: Program<'info, System>,

    /// CHECK: This is not dangerous because we don't read or write from this account
    pub token_program: AccountInfo<'info>,
    /// CHECK: This is not dangerous because we don't read or write from this account
    pub rent: AccountInfo<'info>,

    /// CHECK: This is not dangerous because we don't read or write from this account
    pub mint: AccountInfo<'info>,
    /// CHECK: This is not dangerous because we don't read or write from this account
    pub authority: AccountInfo<'info>,
    /// CHECK: This is not dangerous because we don't read or write from this account
    pub freeze_authority: AccountInfo<'info>,

    #[account(mut)]
    pub signer: Signer<'info>,
}

#[derive(Accounts)]
pub struct CreateInit01<'info> {
    pub system_program: Program<'info, System>,

    /// CHECK: This is not dangerous because we don't read or write from this account
    pub token_program: AccountInfo<'info>,
    /// CHECK: This is not dangerous because we don't read or write from this account
    pub rent: AccountInfo<'info>,

    #[account(mut)]
    pub mint: Signer<'info>,

    #[account(mut)]
    pub authority: Signer<'info>,
}

但是我用纯原生rust合约试了一下

是成功的

pub fn process_init(
    program_id: &Pubkey,
    accounts: &[AccountInfo],
) -> ProgramResult {
    let account_info_iter = &mut accounts.iter();
    let authority_info = next_account_info(account_info_iter)?;
    let signer_info = next_account_info(account_info_iter)?;
    let mint_info = next_account_info(account_info_iter)?;
    let token_program_info = next_account_info(account_info_iter)?;
    let rent_info = next_account_info(account_info_iter)?;
    let system_info = next_account_info(account_info_iter)?;

    assert_signer(&signer_info)?;
    let size = 82;
    let rent = &Rent::from_account_info(&rent_info)?;
    let required_lamports = rent.minimum_balance(size);

    
    msg!("create_account create");
    invoke(
        &system_instruction::create_account(
            signer_info.key,
            mint_info.key,
            required_lamports,
            size as u64,
            token_program_info.key,
        ),
        &[signer_info.clone(), mint_info.clone()],
    )?;
    msg!("initialize_mint");
    invoke(
        &initialize_mint(
            token_program_info.key,
            mint_info.key,
            authority_info.key,
            Some(authority_info.key),
            9,
        )?,
        &[authority_info.clone(), mint_info.clone(),rent_info.clone(),token_program_info.clone(),],
    )?;

    msg!("initialize_mint::{:?} complete",mint_info.key.clone());

    Ok(())
}

相比较起来

原生的和anchor中调用invoke

已经几乎是一一对应了

但是原生成功,anchor失败

我真的很无语

  区块链 最新文章
盘点具备盈利潜力的几大加密板块,以及潜在
阅读笔记|让区块空间成为商品,打造Web3云
区块链1.0-比特币的数据结构
Team Finance被黑分析|黑客自建Token“瞒天
区块链≠绿色?波卡或成 Web3“生态环保”标
期货从入门到高深之手动交易系列D1课
以太坊基础---区块验证
进入以太坊合并的五个数字
经典同态加密算法Paillier解读 - 原理、实现
IPFS/Filecoin学习知识科普(四)
上一篇文章           查看所有文章
加:2022-05-25 11:37:56  更:2022-05-25 11:37:58 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年12日历 -2024/12/28 4:33:42-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码
数据统计