1
const {
    Connection,
    Keypair,
    PublicKey,
    SystemProgram,
    SYSVAR_RENT_PUBKEY,
    TransactionInstruction,
    Transaction,
    sendAndConfirmTransaction,
} = require('@solana/web3.js');
const {
    ASSOCIATED_TOKEN_PROGRAM_ID,
    getAssociatedTokenAddress,
    TOKEN_PROGRAM_ID,
} = require('@solana/spl-token');
const { Buffer } = require('buffer');
const {
    CreateTokenArgs,
    MintSplArgs,
    TransferTokensArgs,
    WhiteListArgs,
    MyInstruction,
} = require('./instruction');
const { BN } = require('bn.js');
const fs = require('fs');
const { publicKey } = require('@project-serum/borsh');

function createKeypairFromFile(path) {
    return Keypair.fromSecretKey(
        Buffer.from(JSON.parse(fs.readFileSync(path, 'utf-8')))
    );
}

describe('Intitial Coin Offering!', () => {
    const connection = new Connection(
        `https://api.devnet.solana.com/`,
        'confirmed'
    );
    const payer = createKeypairFromFile(
        require('os').homedir() + '/.config/solana/id.json'
    );
    const program = createKeypairFromFile(
        './ico/target/deploy/ico-keypair.json'
    );

    const tokenMintKeypair = Keypair.generate();

    const recipientWallet = Keypair.generate();


    it('Create a Token!', async () => {
        const instructionData = new CreateTokenArgs({
            instruction: MyInstruction.Create,
            decimals: 9,
        });

        let ix = new TransactionInstruction({
            keys: [
                {
                    pubkey: tokenMintKeypair.publicKey,
                    isSigner: true,
                    isWritable: true,
                },
                { pubkey: payer.publicKey, isSigner: false, isWritable: true },
                { pubkey: payer.publicKey, isSigner: true, isWritable: true },
                {
                    pubkey: SYSVAR_RENT_PUBKEY,
                    isSigner: false,
                    isWritable: false,
                },
                {
                    pubkey: SystemProgram.programId,
                    isSigner: false,
                    isWritable: false,
                },
                {
                    pubkey: TOKEN_PROGRAM_ID,
                    isSigner: false,
                    isWritable: false,
                },
            ],
            programId: program.publicKey,
            data: instructionData.toBuffer(),
        });

        const ts = new Transaction().add(ix);

        const sx = await sendAndConfirmTransaction(connection, ts, [
            payer,
            tokenMintKeypair,
        ]);

        console.log('Success!');
        console.log(`Mint Address: ${tokenMintKeypair.publicKey}`);
        console.log(`Tx Signature: ${sx}`);
    });

    it('Mint tokens!', async () => {
        const associatedTokenAccountAddress = await getAssociatedTokenAddress(
            tokenMintKeypair.publicKey,
            payer.publicKey
        );

        const instructionData = new MintSplArgs({
            instruction: MyInstruction.MintSpl,
            quantity: new BN(150),
        });

        let ix = new TransactionInstruction({
            keys: [
                {
                    pubkey: tokenMintKeypair.publicKey,
                    isSigner: false,
                    isWritable: true,
                },
                { pubkey: payer.publicKey, isSigner: false, isWritable: true },
                {
                    pubkey: associatedTokenAccountAddress,
                    isSigner: false,
                    isWritable: true,
                },
                { pubkey: payer.publicKey, isSigner: true, isWritable: true },
                {
                    pubkey: SystemProgram.programId,
                    isSigner: false,
                    isWritable: true,
                },
                {
                    pubkey: TOKEN_PROGRAM_ID,
                    isSigner: false,
                    isWritable: false,
                },
                {
                    pubkey: ASSOCIATED_TOKEN_PROGRAM_ID,
                    isSigner: false,
                    isWritable: false,
                },
            ],
            programId: program.publicKey,
            data: instructionData.toBuffer(),
        });

        const ts = new Transaction().add(ix);

        const sx = await sendAndConfirmTransaction(connection, ts, [payer]);

        console.log('Success!');
        console.log(`ATA Address: ${associatedTokenAccountAddress}`);
        console.log(`Tx Signature: ${sx}`);
    });

    it('Transfer tokens!', async () => {
        const fromAssociatedTokenAddress = await getAssociatedTokenAddress(
            tokenMintKeypair.publicKey,
            payer.publicKey
        );

        console.log(`Owner Token Address: ${fromAssociatedTokenAddress}`);

        const toAssociatedTokenAddress = await getAssociatedTokenAddress(
            tokenMintKeypair.publicKey,
            recipientWallet.publicKey
        );

        console.log(`Recipient Token Address: ${toAssociatedTokenAddress}`);

        const transferToInstructionData = new TransferTokensArgs({
            instruction: MyInstruction.TransferTokens,
            quantity: new BN(15),
        });

        let ix = new TransactionInstruction({
            keys: [
                {
                    pubkey: tokenMintKeypair.publicKey,
                    isSigner: false,
                    isWritable: true,
                },
                {
                    pubkey: fromAssociatedTokenAddress,
                    isSigner: false,
                    isWritable: true,
                },
                {
                    pubkey: toAssociatedTokenAddress,
                    isSigner: false,
                    isWritable: true,
                },
                { pubkey: payer.publicKey, isSigner: true, isWritable: true },
                {
                    pubkey: recipientWallet.publicKey,
                    isSigner: true,
                    isWritable: true,
                },
                { pubkey: payer.publicKey, isSigner: true, isWritable: true },
                {
                    pubkey: SystemProgram.programId,
                    isSigner: false,
                    isWritable: false,
                },
                {
                    pubkey: TOKEN_PROGRAM_ID,
                    isSigner: false,
                    isWritable: false,
                },
                {
                    pubkey: ASSOCIATED_TOKEN_PROGRAM_ID,
                    isSigner: false,
                    isWritable: false,
                },
            ],
            programId: program.publicKey,
            data: transferToInstructionData.toBuffer(),
        });

        const ts = new Transaction().add(ix);

        const sx = await sendAndConfirmTransaction(
            connection,
            ts,
            [payer, recipientWallet],
            { skipPreflight: true }
        );

        console.log(`Tx Signature: ${sx}`);
    });

    const proofHex = "0x412b9d8019f394578aca609f04c8bba89bb4f6224f46bc820a80aadce9b8cc21";

    const proofBytes = Buffer.from(proofHex.slice(2), 'hex');

    const rootHex = "0x37dac779c9bf9ee6a8a9a871cb86b5123c46ebaae6854ab859ef9cd184fb8d84";
    const rootBytes = Buffer.from(rootHex.slice(2), 'hex');

    const whiteListAccount1 = new PublicKey("A8CsNURcarxW5JEhLdwtPS2eAxF86sbfaLzfTcJBTXBa");


    it('Check Whitelist Account!', async () => {
        const args = new WhiteListArgs({
            instruction: MyInstruction.WhiteList,
            accounts: 
                whiteListAccount1.toBuffer(), 
            
            proof: proofBytes,
            merkle_root: rootBytes, 
        });
        console.log(args);
    
        let ix = new TransactionInstruction({
            keys: [
                {
                    pubkey: whiteListAccount1,
                    isSigner: true,
                    isWritable: true,
                },
            ],
            programId: program.publicKey,
            data: args.toBuffer(),
        });
    
        const ts = new Transaction().add(ix);
        console.log(ts);
        const signature = await sendAndConfirmTransaction(connection, ts, [
            payer,
            whiteListAccount1,
        ]);
    
        console.log(`Tx Signature: ${signature}`);
    });
});

jest.setTimeout(30000);
1
  • Could you please share more details about your issue?
    – AJackTi
    Commented Apr 29 at 12:02

1 Answer 1

2

This looks like one of the public keys you are logging is null. I would double check all the accounts especially the path to the keypair and the program.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.