At the execution stage of function createInitializeInstruction
I receive an error:
Error creating token for Token2022Form: TypeError: Cannot read properties of undefined (reading 'call')
at Hash.CipherBase (index.js:7:1)
at new Hash (browser.js:9:1)
at createHash (browser.js:29:1)
at splDiscriminate (splDiscriminate.ts:4:1)
at createInitializeInstruction (instruction.ts:51:1)
at createInitializeInstructionReact (createInitializeInstructionReact.js:21:1)
at Object.create (main.b9dcefd2038733fdf419.hot-update.js:218:495)
at async handleCreateToken2022 (index.jsx:140:1)
name
, symbol
, umi
have string values, mint
, metadata
, minyAuthority
, updateAuthority
have valid values.
Here's my code:
import { useState } from 'react';
import {
ComputeBudgetProgram,
Connection,
Keypair,
PublicKey,
sendAndConfirmRawTransaction,
SystemProgram,
Transaction,
BlockheightBasedTransactionConfirmationStrategy
} from '@solana/web3.js';
import {
createInitializeInterestBearingMintInstruction,
createInitializeMetadataPointerInstruction,
createInitializeMintCloseAuthorityInstruction,
createInitializeMintInstruction,
createInitializeNonTransferableMintInstruction,
createInitializePermanentDelegateInstruction,
createInitializeTransferFeeConfigInstruction,
createInitializeTransferHookInstruction,
createMintToInstruction,
createAssociatedTokenAccountInstruction,
getAssociatedTokenAddressSync,
ExtensionType,
getMintLen,
LENGTH_SIZE,
TOKEN_2022_PROGRAM_ID,
TYPE_SIZE} from '@solana/spl-token';
import { TokenMetadata, createInitializeInstruction, pack } from '@solana/spl-token-metadata';
import { useWallet } from "@solana/wallet-adapter-react";
import BigNumber from "bignumber.js";
import API_KEY from "../../action/API_KEY/api_key";
import bs58 from "bs58";
export const useToken22Minter = () => {
const network = 'devnet'
const [connection] = useState(new Connection(`https://${network}.helius-rpc.com/?api-key=${API_KEY}`, 'confirmed'));
const { publicKey } = useWallet();
const wallet = useWallet();
const toPublicKey = (k) => {
if (!k) {
return null;
} return new PublicKey(k);
};
const buildExtensionsInstructions = (mint, config, nonTransferableData) => {
const ixs = [];
const extensionsTypes = [ExtensionType.MetadataPointer];
const hasExtensions = Object.values(config).some(value => value);
if (hasExtensions) {
if (config.transferFee) {
ixs.push(
createInitializeTransferFeeConfigInstruction(
mint,
toPublicKey(config.transferFee.transferAuthority),
toPublicKey(config.transferFee.withdrawAuthority),
config.transferFee.basisPoints,
new BigNumber(config.transferFee.maximumFee.toString()),
TOKEN_2022_PROGRAM_ID
)
);
extensionsTypes.push(ExtensionType.TransferFeeConfig);
}
if (config.transferHook) {
ixs.push(
createInitializeTransferHookInstruction(
mint,
toPublicKey(config.transferHook.authority),
toPublicKey(config.transferHook.programId),
TOKEN_2022_PROGRAM_ID
)
);
extensionsTypes.push(ExtensionType.TransferHook);
}
if (config.permanentDelegate) {
ixs.push(
createInitializePermanentDelegateInstruction(
mint,
toPublicKey(config.permanentDelegate.authority),
TOKEN_2022_PROGRAM_ID
)
);
extensionsTypes.push(ExtensionType.PermanentDelegate);
}
if (config.mintCloseAuthority) {
ixs.push(
createInitializeMintCloseAuthorityInstruction(
mint,
toPublicKey(config.mintCloseAuthority.authority),
TOKEN_2022_PROGRAM_ID
)
);
extensionsTypes.push(ExtensionType.MintCloseAuthority);
}
if (config.interestBearing) {
ixs.push(
createInitializeInterestBearingMintInstruction(
mint,
toPublicKey(config.interestBearing.authority),
config.interestBearing.rate,
TOKEN_2022_PROGRAM_ID
)
);
extensionsTypes.push(ExtensionType.InterestBearingConfig);
}
if (nonTransferableData) {
ixs.push(createInitializeNonTransferableMintInstruction(mint, TOKEN_2022_PROGRAM_ID));
extensionsTypes.push(ExtensionType.NonTransferable);
}
}
return { ixs, extensionsTypes };
};
const create = async (metadata = { name: '', symbol: '', uri: '' }, extensionsConfig, amount, decimals2022) => {
const pubKey = publicKey;
const mint = Keypair.generate();
const ata = getAssociatedTokenAddressSync(mint.publicKey, pubKey, undefined, TOKEN_2022_PROGRAM_ID);
const decimals = decimals2022;
const metaData: TokenMetadata = {
mint: mint.publicKey,
name: metadata.name,
symbol: metadata.symbol,
uri: metadata.uri,
additionalMetadata: [],
};
const { ixs, extensionsTypes } = buildExtensionsInstructions(mint.publicKey, extensionsConfig, extensionsConfig.nonTransferable);
const priceIx = ComputeBudgetProgram.setComputeUnitPrice({ microLamports: 1000000 });
const mintLen = getMintLen(extensionsTypes);
const metadataLen = TYPE_SIZE + LENGTH_SIZE + pack(metaData).length;
const mintLamports = await connection.getMinimumBalanceForRentExemption(mintLen + metadataLen);
const hash = await connection.getLatestBlockhash('confirmed');
const mintTransaction = new Transaction({
feePayer: pubKey,
blockhash: hash.blockhash,
lastValidBlockHeight: hash.lastValidBlockHeight
}).add(
priceIx,
SystemProgram.createAccount({
fromPubkey: pubKey,
newAccountPubkey: mint.publicKey,
space: mintLen,
lamports: mintLamports,
programId: TOKEN_2022_PROGRAM_ID
}),
createInitializeMetadataPointerInstruction(mint.publicKey, pubKey, mint.publicKey, TOKEN_2022_PROGRAM_ID),
...ixs,
createInitializeMintInstruction(mint.publicKey, decimals, pubKey, null, TOKEN_2022_PROGRAM_ID),
createInitializeInstruction({
programId: TOKEN_2022_PROGRAM_ID,
mint: mint.publicKey,
metadata: mint.publicKey,
name: metaData.name,
symbol: metaData.symbol,
uri: metaData.uri,
mintAuthority: pubKey,
updateAuthority: pubKey,
}),
createAssociatedTokenAccountInstruction(pubKey, ata, pubKey, mint.publicKey, TOKEN_2022_PROGRAM_ID),
createMintToInstruction(mint.publicKey, ata, pubKey, new BigNumber(amount), undefined, TOKEN_2022_PROGRAM_ID)
);
mintTransaction.partialSign(mint);
const signedTx = await wallet.signTransaction(mintTransaction);
const rawTx = signedTx.serialize();
const confirmationStrategy: BlockheightBasedTransactionConfirmationStrategy = {
lastValidBlockHeight: hash.lastValidBlockHeight,
signature: bs58.encode(signedTx.signature),
blockhash: hash.blockhash,
};
const signature = await sendAndConfirmRawTransaction(connection, rawTx, confirmationStrategy);
return { mint: mint.publicKey.toString(), signature };
};
return { create };
};
The code for the createInitializeInstruction function in the @solana/spl-token-metadata library:
import type { StructToEncoderTuple } from '@solana/codecs-data-structures';
import { getBooleanEncoder, getBytesEncoder, getDataEnumCodec, getStructEncoder } from '@solana/codecs-data-structures';
import { getU64Encoder } from '@solana/codecs-numbers';
import { getStringEncoder } from '@solana/codecs-strings';
import { getOptionEncoder } from '@solana/options';
import { splDiscriminate } from '@solana/spl-type-length-value';
import type { PublicKey } from '@solana/web3.js';
import { TransactionInstruction } from '@solana/web3.js';
import type { Field } from './field.js';
import { getFieldCodec, getFieldConfig } from './field.js';
function packInstruction<T extends object>(
layout: StructToEncoderTuple<T>,
discriminator: Uint8Array,
values: T): Buffer {
const encoder = getStructEncoder(layout);
const data = encoder.encode(values);
return Buffer.concat([discriminator, data]);
}/** * Initializes a TLV entry with the basic token-metadata fields. * * Assumes that the provided mint is an SPL token mint, that the metadata * account is allocated and assigned to the program, and that the metadata * account has enough lamports to cover the rent-exempt reserve. */export interface InitializeInstructionArgs { programId: PublicKey;
metadata: PublicKey;
updateAuthority: PublicKey;
mint: PublicKey;
mintAuthority: PublicKey;
name: string;
symbol: string;
uri: string;
}
export function createInitializeInstruction(args: InitializeInstructionArgs): TransactionInstruction {
const { programId, metadata, updateAuthority, mint, mintAuthority, name, symbol, uri } = args;
return new TransactionInstruction({
programId,
keys: [
{ isSigner: false, isWritable: true, pubkey: metadata },
{ isSigner: false, isWritable: false, pubkey: updateAuthority },
{ isSigner: false, isWritable: false, pubkey: mint },
{ isSigner: true, isWritable: false, pubkey: mintAuthority },
],
data: packInstruction(
[
['name', getStringEncoder()],
['symbol', getStringEncoder()],
['uri', getStringEncoder()],
],
splDiscriminate('spl_token_metadata_interface:initialize_account'),
{ name, symbol, uri }
),
});
}/** * If the field does not exist on the account, it will be created. * If the field does exist, it will be overwritten. */export interface UpdateFieldInstruction {
programId: PublicKey;
metadata: PublicKey;
updateAuthority: PublicKey;
field: Field | string;
value: string;
}
export function createUpdateFieldInstruction(args: UpdateFieldInstruction): TransactionInstruction {
const { programId, metadata, updateAuthority, field, value } = args;
return new TransactionInstruction({
programId,
keys: [
{ isSigner: false, isWritable: true, pubkey: metadata },
{ isSigner: true, isWritable: false, pubkey: updateAuthority },
],
data: packInstruction(
[
['field', getDataEnumCodec(getFieldCodec())],
['value', getStringEncoder()],
],
splDiscriminate('spl_token_metadata_interface:updating_field'),
{ field: getFieldConfig(field), value }
),
});
}
export interface RemoveKeyInstructionArgs {
programId: PublicKey;
metadata: PublicKey;
updateAuthority: PublicKey;
key: string;
idempotent: boolean;
}
export function createRemoveKeyInstruction(args: RemoveKeyInstructionArgs) {
const { programId, metadata, updateAuthority, key, idempotent } = args;
return new TransactionInstruction({
programId,
keys: [
{ isSigner: false, isWritable: true, pubkey: metadata },
{ isSigner: true, isWritable: false, pubkey: updateAuthority },
],
data: packInstruction(
[
['idempotent', getBooleanEncoder()],
['key', getStringEncoder()],
],
splDiscriminate('spl_token_metadata_interface:remove_key_ix'),
{ idempotent, key }
),
});
}
export interface UpdateAuthorityInstructionArgs {
programId: PublicKey;
metadata: PublicKey;
oldAuthority: PublicKey;
newAuthority: PublicKey | null;
}
export function createUpdateAuthorityInstruction(args: UpdateAuthorityInstructionArgs): TransactionInstruction {
const { programId, metadata, oldAuthority, newAuthority } = args;
const newAuthorityBuffer = Buffer.alloc(32);
if (newAuthority) {
newAuthorityBuffer.set(newAuthority.toBuffer());
} else {
newAuthorityBuffer.fill(0);
}
return new TransactionInstruction({
programId,
keys: [
{ isSigner: false, isWritable: true, pubkey: metadata },
{ isSigner: true, isWritable: false, pubkey: oldAuthority },
],
data: packInstruction(
[['newAuthority', getBytesEncoder({ size: 32 })]],
splDiscriminate('spl_token_metadata_interface:update_the_authority'),
{ newAuthority: newAuthorityBuffer }
),
});
}
export interface EmitInstructionArgs {
programId: PublicKey;
metadata: PublicKey;
start?: bigint;
end?: bigint;
}
export function createEmitInstruction(args: EmitInstructionArgs): TransactionInstruction {
const { programId, metadata, start, end } = args;
return new TransactionInstruction({
programId,
keys: [{ isSigner: false, isWritable: false, pubkey: metadata }],
data: packInstruction(
[
['start', getOptionEncoder(getU64Encoder())],
['end', getOptionEncoder(getU64Encoder())],
],
splDiscriminate('spl_token_metadata_interface:emitter'),
{ start: start ?? null, end: end ?? null }
),
});}
I would be grateful for any help.
I'm stumped, I've looked through a bunch of guides, but the recommendations don't work for me
upd: config code:
const webpack = require("webpack");
const getCacheIdentifier = require("react-dev-utils/getCacheIdentifier");
module.exports = function override(config, webpackEnv) {
console.log("Overriding webpack config...");
// Set up environment flags
const isEnvDevelopment = webpackEnv === "development";
const isEnvProduction = webpackEnv === "production";
const shouldUseSourceMap = process.env.GENERATE_SOURCEMAP !== "false";
// Configure fallbacks for Node environment
const fallback = config.resolve.fallback || {};
Object.assign(fallback, {
crypto: require.resolve("crypto-browserify"),
stream: require.resolve("stream-browserify"),
assert: require.resolve("assert"),
http: require.resolve("stream-http"),
https: require.resolve("https-browserify"),
os: require.resolve("os-browserify"),
url: require.resolve("url"),
zlib: require.resolve("browserify-zlib"),
});
config.resolve.fallback = fallback;
// Configure plugins
config.plugins = (config.plugins || []).concat([
new webpack.ProvidePlugin({
process: "process/browser",
Buffer: ["buffer", "Buffer"],
}),
]);
// Ignore certain warnings
config.ignoreWarnings = [/Failed to parse source map/];
// Add source-map loader
config.module.rules.push({
test: /\.(js|mjs|jsx)$/,
enforce: "pre",
loader: require.resolve("source-map-loader"),
resolve: {
fullySpecified: false,
},
});
// Modify Babel loader configuration
const loaders = config.module.rules.find((rule) =>
Array.isArray(rule.oneOf)
).oneOf;
loaders.splice(loaders.length - 1, 0, {
test: /\.(js|mjs|cjs)$/,
exclude: /@babel(?:\/|\\{1,2})runtime/,
loader: require.resolve("babel-loader"),
options: {
babelrc: false,
configFile: false,
compact: false,
presets: [
[
require.resolve("babel-preset-react-app/dependencies"),
{ helpers: true },
],
],
cacheDirectory: true,
cacheCompression: false,
cacheIdentifier: getCacheIdentifier(
isEnvProduction ? "production" : isEnvDevelopment && "development",
[
"babel-plugin-named-asset-import",
"babel-preset-react-app",
"react-dev-utils",
"react-scripts",
]
),
sourceMaps: shouldUseSourceMap,
inputSourceMap: shouldUseSourceMap,
},
});
return config;
};
package.json:
{
"name": "token_minter",
"version": "0.1.0",
"private": true,
"dependencies": {
"@metaplex-foundation/mpl-token-metadata": "^3.2.1",
"@metaplex-foundation/umi": "^0.9.1",
"@metaplex-foundation/umi-bundle-defaults": "^0.9.1",
"@metaplex-foundation/umi-signer-wallet-adapters": "^0.9.1",
"@metaplex-foundation/umi-web3js-adapters": "^0.9.1",
"@solana/pay": "^0.2.5",
"@solana/spl-token": "^0.4.3",
"@solana/spl-token-metadata": "^0.1.2",
"@solana/wallet-adapter-base": "^0.9.23",
"@solana/wallet-adapter-react": "^0.15.35",
"@solana/wallet-adapter-react-ui": "^0.9.35",
"@solana/wallet-adapter-wallets": "^0.19.32",
"@solana/web3.js": "^1.91.1",
"@testing-library/jest-dom": "^5.17.0",
"@testing-library/react": "^13.4.0",
"@testing-library/user-event": "^13.5.0",
"axios": "^1.6.8",
"browserify": "^17.0.0",
"bs58": "^5.0.0",
"buffer": "^6.0.3",
"copy-to-clipboard": "^3.3.3",
"crypto-browserify": "^3.12.0",
"express": "^4.19.2",
"http-browserify": "^1.7.0",
"https-browserify": "^1.0.0",
"js-cookie": "^3.0.5",
"process": "^0.11.10",
"react": "^18.2.0",
"react-copy-to-clipboard": "^5.1.0",
"react-dev-utils": "^12.0.1",
"react-dom": "^18.2.0",
"react-router-dom": "^6.6.0",
"react-scripts": "5.0.1",
"stream": "^0.0.2",
"stream-browserify": "^3.0.0",
"stream-http": "^3.2.0",
"web-vitals": "^2.1.4",
"webpack": "^5.91.0",
"zlib-browserify": "^0.0.3"
},
"scripts": {
"start": "react-app-rewired start",
"build": "react-app-rewired build",
"test": "react-app-rewired test",
"eject": "react-scripts eject"
},
"eslintConfig": {
"extends": [
"react-app",
"react-app/jest"
]
},
"browserslist": {
"production": [
">0.2%",
"not dead",
"not op_mini all"
],
"development": [
"last 1 chrome version",
"last 1 firefox version",
"last 1 safari version"
]
},
"devDependencies": {
"@craco/craco": "^7.1.0",
"@types/node": "^20.11.30",
"@types/react": "^18.2.70",
"customize-cra": "^1.0.0",
"node-loader": "^2.0.0",
"react-app-rewired": "^2.2.1",
"webpack-cli": "^5.1.4",
"webpack-node-externals": "^3.0.0"
},
"browser": {
"path": false,
"stream": false,
"http": false,
"https": false
},
"resolve": {
"fallback": {
"crypto": "crypto-browserify",
"http": "http-browserify",
"https": "https-browserify",
"zlib": "zlib-browserify"
}
}
}
I found the problem and its solution. In general, the problem is that CRA has a horrible builder, migrating to vite helped