Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Leant/update mpl deps #63

Open
wants to merge 2 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 7 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -21,8 +21,13 @@
"license": "MIT",
"dependencies": {
"@coral-xyz/anchor": "^0.26.0",
"@metaplex-foundation/mpl-auction-house": "^2.1.1",
"@metaplex-foundation/mpl-bubblegum": "^0.7.0",
"@metaplex-foundation/mpl-auction-house": "^2.5.1",
"@metaplex-foundation/mpl-bubblegum": "^4.2.0",
"@metaplex-foundation/mpl-token-metadata": "^3.2.1",
"@metaplex-foundation/umi": "^0.9.2",
"@metaplex-foundation/umi-bundle-defaults": "^0.9.2",
"@metaplex-foundation/umi-serializers": "^0.9.0",
"@metaplex-foundation/umi-web3js-adapters": "^0.9.2",
"@solana/spl-account-compression": "^0.1.4",
"@solana/spl-token": "^0.3.7",
"@solana/web3.js": "^1.91.1",
Expand Down
4 changes: 2 additions & 2 deletions src/metaplex/pdas/bubblegum.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import {
getMetadataArgsSerializer,
MetadataArgs,
metadataArgsBeet,
} from '@metaplex-foundation/mpl-bubblegum';
import { PublicKey } from '@solana/web3.js';
import BN from 'bn.js';
Expand All @@ -11,7 +11,7 @@ export const BUBBLEGUM_PROGRAM_ID = new PublicKey(
);

export function computeMetadataArgsHash(metadata: MetadataArgs): Buffer {
const [serializedMetadata] = metadataArgsBeet.serialize(metadata);
const serializedMetadata = getMetadataArgsSerializer().serialize(metadata);
return Buffer.from(keccak_256.digest(serializedMetadata));
}

Expand Down
20 changes: 7 additions & 13 deletions src/metaplex/token_metadata.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
import { Metadata } from '@metaplex-foundation/mpl-token-metadata';
import { Key, Metadata, fetchMetadata as fetchMetadataMplx } from '@metaplex-foundation/mpl-token-metadata';
import { Connection, PublicKey } from '@solana/web3.js';
import { findMetadataPda } from './pdas';

import { findMetadataPda } from './pdas';
import { publicKey } from '@metaplex-foundation/umi';
import { createUmi } from "@metaplex-foundation/umi-bundle-defaults"
export const findMetadataFromMint = (mint: string | PublicKey) => {
return findMetadataPda(new PublicKey(mint))[0];
};
Expand Down Expand Up @@ -34,24 +35,17 @@ export const getMetadataErrType = (err: any) => {
return MetadataErrType.Unknown;
};

/** Handles burned but non-empty metadata accounts */
export const deserializeMeta = (data: Uint8Array | Buffer): Metadata | null => {
// NFT + metadata has been burned. The account may not be empty yet b/c 0.01 fee has not been collected yet.
if (data[0] === 0) return null;
return Metadata.deserialize(Buffer.from(data))[0];
};

/** Fetches Metadata account and handles zero'ed out accounts w/ Metaplex fee remaining */
export const fetchMetadata = async (
conn: Connection,
address: PublicKey,
): Promise<Metadata | null> => {
try {
const acct = await conn.getAccountInfo(address);
if (!acct) {
const acct = await fetchMetadataMplx(createUmi(conn.rpcEndpoint), publicKey(address));
if (!acct || acct.key === Key.Uninitialized) {
return null;
}
return deserializeMeta(acct.data);
return acct;
} catch (err: any) {
const errType = getMetadataErrType(err);
switch (errType) {
Expand Down
109 changes: 63 additions & 46 deletions src/metaplex/token_rules.ts
Original file line number Diff line number Diff line change
@@ -1,22 +1,46 @@
import {
AuthorizationData,
createTransferInstruction,
transferV1,
Metadata,
TokenStandard,
TransferArgs,
TransferInstructionAccounts,
TransferInstructionArgs,
TransferV1InstructionAccounts,
TransferV1InstructionArgs,
Creator,
PayloadType,
} from '@metaplex-foundation/mpl-token-metadata';
import { ASSOCIATED_TOKEN_PROGRAM_ID } from '@solana/spl-token';
import {
Connection,
PublicKey,
SystemProgram,
SYSVAR_INSTRUCTIONS_PUBKEY,
TransactionInstruction,
} from '@solana/web3.js';
import { AUTH_PROGRAM_ID, findEditionPda, findTokenRecordPda } from './pdas';
import { publicKey, createNoopSigner, unwrapOption, isSome, none } from '@metaplex-foundation/umi';
import { findEditionPda, findTokenRecordPda } from './pdas';
import { fetchMetadataByMint } from './token_metadata';
import { defaultUmi } from '../utils';
import { toWeb3JsInstruction } from '@metaplex-foundation/umi-web3js-adapters';
export { AuthorizationData } from '@metaplex-foundation/mpl-token-metadata';

export type PnftAccountsReturn = {
meta: {
address: PublicKey;
metadata: Metadata | null;
};
creators: Creator[];
ruleSet?: PublicKey;
ownerTokenRecordBump: number;
ownerTokenRecordPda: PublicKey;
destTokenRecordBump: number;
destTokenRecordPda: PublicKey;
nftEditionPda: PublicKey;
authDataSerialized?: {
payload: {
name: string;
payload: PayloadType;
}[];
} | null;
}

export const prepPnftAccounts = async ({
connection,
meta,
Expand All @@ -35,7 +59,7 @@ export const prepPnftAccounts = async ({
sourceAta: PublicKey;
destAta: PublicKey;
authData?: AuthorizationData | null;
}) => {
}): Promise<PnftAccountsReturn> => {
if (!meta) {
const { address, metadata } = await fetchMetadataByMint(
connection,
Expand All @@ -48,8 +72,8 @@ export const prepPnftAccounts = async ({
metadata,
};
}
const creators = meta.metadata.data.creators ?? [];
const ruleSet = meta.metadata.programmableConfig?.ruleSet ?? undefined;
const creators = meta.metadata.creators ?? [];
const ruleSet = unwrapOption(meta.metadata.programmableConfig)?.ruleSet ?? undefined;

const [ownerTokenRecordPda, ownerTokenRecordBump] = findTokenRecordPda(
nftMint,
Expand All @@ -74,8 +98,8 @@ export const prepPnftAccounts = async ({

return {
meta,
creators,
ruleSet,
creators: unwrapOption(creators) ?? [],
ruleSet: ruleSet && isSome(ruleSet) ? new PublicKey(unwrapOption(ruleSet)!) : undefined,
ownerTokenRecordBump,
ownerTokenRecordPda,
destTokenRecordBump,
Expand Down Expand Up @@ -105,7 +129,7 @@ export const makePnftTransferIx = async ({
fromAddr: PublicKey;
toAddr: PublicKey;
tokenProgram: PublicKey;
}) => {
}): Promise<TransactionInstruction> => {
const {
meta,
ruleSet,
Expand All @@ -119,44 +143,37 @@ export const makePnftTransferIx = async ({
destAta: toAddr,
});

const transferAcccounts: TransferInstructionAccounts = {
authority: authority ?? tokenOwner,
tokenOwner,
token: fromAddr,
mint,
metadata: meta.address,
edition: nftEditionPda,
destinationOwner,
destination: toAddr,
payer: tokenOwner,
splTokenProgram: tokenProgram,
splAtaProgram: ASSOCIATED_TOKEN_PROGRAM_ID,
systemProgram: SystemProgram.programId,
sysvarInstructions: SYSVAR_INSTRUCTIONS_PUBKEY,
authorizationRules: ruleSet,
authorizationRulesProgram: AUTH_PROGRAM_ID,
ownerTokenRecord: ownerTokenRecordPda,
destinationTokenRecord: destTokenRecordPda,
const transferAcccounts: TransferV1InstructionAccounts = {
authority: authority ? createNoopSigner(publicKey(authority)) : createNoopSigner(publicKey(tokenOwner)),
tokenOwner: publicKey(tokenOwner),
token: publicKey(fromAddr),
mint: publicKey(mint),
metadata: publicKey(meta.address),
edition: publicKey(nftEditionPda),
destinationOwner: publicKey(destinationOwner),
destinationToken: publicKey(toAddr),
payer: createNoopSigner(publicKey(tokenOwner)),
splTokenProgram: publicKey(tokenProgram),
authorizationRules: ruleSet ? publicKey(ruleSet) : undefined,
tokenRecord: publicKey(ownerTokenRecordPda),
destinationTokenRecord: publicKey(destTokenRecordPda),
};

if (!args) {
args = {
__kind: 'V1',
amount: 1,
authorizationData: null,
};
}

// not sure needed (keeping around in case changes, to quickly remember command)
// const modifyComputeUnits = ComputeBudgetProgram.setComputeUnitLimit({
// units: 400_000,
// });

const transferArgs: TransferInstructionArgs = {
transferArgs: args,
};

const transferIx = createTransferInstruction(transferAcccounts, transferArgs);

return transferIx;
// TODO: could be ProgrammableNonFungibleEdition?
// unsure if that was triaged within createTransferInstruction before?
const transferArgs: TransferV1InstructionArgs = args ?
{
...args,
tokenStandard: TokenStandard.ProgrammableNonFungible,
} : {
amount: 1,
tokenStandard: TokenStandard.ProgrammableNonFungible,
}
const transferIx = transferV1(defaultUmi, {...transferAcccounts, ...transferArgs}).getInstructions()[0];
return toWeb3JsInstruction(transferIx);
};
14 changes: 8 additions & 6 deletions src/programs/auction_house/accept_bid.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import {
createExecuteSaleInstruction,
createSellInstruction,
} from '@metaplex-foundation/mpl-auction-house';
import { Metadata } from '@metaplex-foundation/mpl-token-metadata';
import { fetchMetadata } from '@metaplex-foundation/mpl-token-metadata';
import {
createAssociatedTokenAccountInstruction,
getAssociatedTokenAddress,
Expand All @@ -30,6 +30,8 @@ import {
import { buildTx } from '../../solana_contrib';
import { TxWithHeight } from '../../solana_contrib/types';
import { getQuantityWithMantissa } from './shared';
import { publicKey, unwrapOption } from '@metaplex-foundation/umi';
import { defaultUmi } from 'src/utils';

export const makeAHAcceptBidTx = async (
connections: Array<Connection>,
Expand Down Expand Up @@ -164,14 +166,14 @@ export const makeAHAcceptBidTx = async (
);

//add creators for royalty payments
const metadataDecoded = await Metadata.fromAccountAddress(
connection,
metadata,
const metadataDecoded = await fetchMetadata(
defaultUmi,
publicKey(metadata),
);

for (let i = 0; i < metadataDecoded.data.creators!.length; i++) {
for (let i = 0; i < unwrapOption(metadataDecoded.creators)!.length; i++) {
execSaleIx.keys.push({
pubkey: new PublicKey(metadataDecoded.data.creators![i].address),
pubkey: new PublicKey(unwrapOption(metadataDecoded.creators)![i].address),
isWritable: true,
isSigner: false,
});
Expand Down
15 changes: 8 additions & 7 deletions src/programs/auction_house/buy.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ import {
createExecuteSaleInstruction,
PROGRAM_ID,
} from '@metaplex-foundation/mpl-auction-house';
import { Metadata } from '@metaplex-foundation/mpl-token-metadata';
import { fetchMetadata } from '@metaplex-foundation/mpl-token-metadata';
import {
createAssociatedTokenAccountInstruction,
getAccount,
Expand All @@ -22,7 +22,6 @@ import {
Keypair,
PublicKey,
SystemProgram,
Transaction,
TransactionInstruction,
} from '@solana/web3.js';
import BN from 'bn.js';
Expand All @@ -35,6 +34,8 @@ import {
findAuctionHouseTradeStatePda,
findMetadataPda,
} from '../../metaplex';
import { defaultUmi } from 'src/utils';
import { publicKey, unwrapOption } from '@metaplex-foundation/umi';

export const makeAHBuyTx = async (
connections: Array<Connection>,
Expand Down Expand Up @@ -195,14 +196,14 @@ export const makeAHBuyTx = async (
);

//add creators for royalty payments
const metadataDecoded = await Metadata.fromAccountAddress(
connection,
metadata,
const metadataDecoded = await fetchMetadata(
defaultUmi,
publicKey(metadata),
);

for (let i = 0; i < metadataDecoded.data.creators!.length; i++) {
for (let i = 0; i < unwrapOption(metadataDecoded.creators)!.length; i++) {
execSaleIx.keys.push({
pubkey: new PublicKey(metadataDecoded.data.creators![i].address),
pubkey: new PublicKey(unwrapOption(metadataDecoded.creators)![i].address),
isWritable: true,
isSigner: false,
});
Expand Down
11 changes: 6 additions & 5 deletions src/programs/solanart/buy.ts
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ import {
findDataEscrowPda,
findRoyaltiesPda,
} from './shared';
import { isSome, unwrapOption } from '@metaplex-foundation/umi';

export const makeSolanartBuyTx = async ({
connections,
Expand Down Expand Up @@ -169,15 +170,15 @@ export const makeSolanartBuyTx = async ({
/// + `[writable]` Creator wallets (up to 5) - all creators
///

metadata.data.creators?.forEach((creator) => {
unwrapOption(metadata.creators)?.forEach((creator) => {
instructionAccounts.push({
pubkey: creator.address,
pubkey: new PublicKey(creator.address),
isSigner: false,
isWritable: true,
});
});

if (metadata.tokenStandard === TokenStandard.ProgrammableNonFungible) {
if (unwrapOption(metadata.tokenStandard) === TokenStandard.ProgrammableNonFungible) {
const { ruleSet, nftEditionPda, ownerTokenRecordPda, destTokenRecordPda } =
await prepPnftAccounts({
connection,
Expand Down Expand Up @@ -227,9 +228,9 @@ export const makeSolanartBuyTx = async ({
],
);

if (ruleSet) {
if (ruleSet && ruleSet) {
instructionAccounts.push({
pubkey: ruleSet,
pubkey: new PublicKey(ruleSet),
isSigner: false,
isWritable: false,
});
Expand Down
Loading
Loading