From 44d33c56c1bdcf348d37bb838c1d5f6e1dfc4095 Mon Sep 17 00:00:00 2001 From: Jesse Cruz Wright Date: Fri, 10 Nov 2023 09:17:16 +0000 Subject: [PATCH] Transition from `@bundlr-network/client` to `@irys/sdk` (#91) * refactor: :truck: Rename umi-uploader-bundlr -> umi-uploader-irys * feat: :sparkles: Transition umi-uploader-bundlr to umi-uploader-irys * feat: :truck: Restore umi-uploader-bundlr * chore: :memo: Add changeset for umi-uploader-irys * chore: :memo: Update PNPM lock, add Bundlr back to implementations list * chore: :fire: Remove umi-uploader-irys changelog * chore: :art: Apply linting & formatting --- .changeset/rich-camels-roll.md | 5 + docs/implementations.md | 3 +- packages/umi-uploader-irys/README.md | 9 + packages/umi-uploader-irys/babel.config.json | 3 + packages/umi-uploader-irys/package.json | 72 +++ packages/umi-uploader-irys/rollup.config.js | 16 + .../src/createIrysUploader.ts | 391 ++++++++++++++++ packages/umi-uploader-irys/src/errors.ts | 54 +++ packages/umi-uploader-irys/src/index.ts | 3 + packages/umi-uploader-irys/src/plugin.ts | 8 + .../test/IrysUploader.test.ts | 53 +++ .../test/modules/cjs.test.cjs | 30 ++ .../test/modules/esm.test.mjs | 28 ++ packages/umi-uploader-irys/test/tsconfig.json | 11 + packages/umi-uploader-irys/tsconfig.json | 8 + pnpm-lock.yaml | 443 ++++++++++++++++-- 16 files changed, 1097 insertions(+), 40 deletions(-) create mode 100644 .changeset/rich-camels-roll.md create mode 100644 packages/umi-uploader-irys/README.md create mode 100644 packages/umi-uploader-irys/babel.config.json create mode 100644 packages/umi-uploader-irys/package.json create mode 100644 packages/umi-uploader-irys/rollup.config.js create mode 100644 packages/umi-uploader-irys/src/createIrysUploader.ts create mode 100644 packages/umi-uploader-irys/src/errors.ts create mode 100644 packages/umi-uploader-irys/src/index.ts create mode 100644 packages/umi-uploader-irys/src/plugin.ts create mode 100644 packages/umi-uploader-irys/test/IrysUploader.test.ts create mode 100644 packages/umi-uploader-irys/test/modules/cjs.test.cjs create mode 100644 packages/umi-uploader-irys/test/modules/esm.test.mjs create mode 100644 packages/umi-uploader-irys/test/tsconfig.json create mode 100644 packages/umi-uploader-irys/tsconfig.json diff --git a/.changeset/rich-camels-roll.md b/.changeset/rich-camels-roll.md new file mode 100644 index 00000000..73e1b876 --- /dev/null +++ b/.changeset/rich-camels-roll.md @@ -0,0 +1,5 @@ +--- +'@metaplex-foundation/umi-uploader-irys': patch +--- + +Add new Irys uploader to replace the deprecated Bundlr uploader diff --git a/docs/implementations.md b/docs/implementations.md index de8e39cb..99c2f1ca 100644 --- a/docs/implementations.md +++ b/docs/implementations.md @@ -41,9 +41,10 @@ The page aims to list all the available implementations of [the interfaces defin | Description | Maintainer | Links | | --- | --- | --- | | Uses AWS | Metaplex | [GitHub](https://github.com/metaplex-foundation/umi/tree/main/packages/umi-uploader-aws) / [NPM](https://www.npmjs.com/package/@metaplex-foundation/umi-uploader-aws) | -| Uses Bundlr Network | Metaplex | [GitHub](https://github.com/metaplex-foundation/umi/tree/main/packages/umi-uploader-bundlr) / [NPM](https://www.npmjs.com/package/@metaplex-foundation/umi-uploader-bundlr) | +| Uses Irys.xyz | Metaplex | [GitHub](https://github.com/metaplex-foundation/umi/tree/main/packages/umi-uploader-irys) / [NPM](https://www.npmjs.com/package/@metaplex-foundation/umi-uploader-irys) | | Uses NFT.Storage | Metaplex | [GitHub](https://github.com/metaplex-foundation/umi/tree/main/packages/umi-uploader-nft-storage) / [NPM](https://www.npmjs.com/package/@metaplex-foundation/umi-uploader-nft-storage) | | Uses a local cache to mock uploads and downloads | Metaplex | [GitHub](https://github.com/metaplex-foundation/umi/tree/main/packages/umi-storage-mock) / [NPM](https://www.npmjs.com/package/@metaplex-foundation/umi-storage-mock) | +| Uses Bundlr.network (Deprecated - use `umi-uploader-irys`) | Metaplex | [GitHub](https://github.com/metaplex-foundation/umi/tree/main/packages/umi-uploader-bundlr) / [NPM](https://www.npmjs.com/package/@metaplex-foundation/umi-uploader-bundlr) | ## Downloader Interface diff --git a/packages/umi-uploader-irys/README.md b/packages/umi-uploader-irys/README.md new file mode 100644 index 00000000..c0616c6a --- /dev/null +++ b/packages/umi-uploader-irys/README.md @@ -0,0 +1,9 @@ +# umi-uploader-irys + +An uploader implementation relying on Irys. + +## Installation + +```sh +npm install @metaplex-foundation/umi-uploader-irys +``` diff --git a/packages/umi-uploader-irys/babel.config.json b/packages/umi-uploader-irys/babel.config.json new file mode 100644 index 00000000..ac08da0a --- /dev/null +++ b/packages/umi-uploader-irys/babel.config.json @@ -0,0 +1,3 @@ +{ + "extends": "../../babel.config.json" +} diff --git a/packages/umi-uploader-irys/package.json b/packages/umi-uploader-irys/package.json new file mode 100644 index 00000000..6360b7c3 --- /dev/null +++ b/packages/umi-uploader-irys/package.json @@ -0,0 +1,72 @@ +{ + "name": "@metaplex-foundation/umi-uploader-irys", + "version": "0.8.9", + "description": "An uploader implementation relying on Irys", + "license": "MIT", + "sideEffects": false, + "module": "dist/esm/index.mjs", + "main": "dist/cjs/index.cjs", + "types": "dist/types/index.d.ts", + "exports": { + ".": { + "types": "./dist/types/index.d.ts", + "import": "./dist/esm/index.mjs", + "require": "./dist/cjs/index.cjs" + } + }, + "files": [ + "/dist/cjs", + "/dist/esm", + "/dist/types", + "/src" + ], + "scripts": { + "lint": "eslint --ext js,ts,tsx src", + "lint:fix": "eslint --fix --ext js,ts,tsx src", + "clean": "rimraf dist", + "build": "pnpm clean && tsc && tsc -p test/tsconfig.json && rollup -c", + "test": "ava" + }, + "dependencies": { + "@irys/sdk": "^0.0.2", + "@metaplex-foundation/umi-web3js-adapters": "workspace:^", + "bignumber.js": "^9.0.2", + "buffer": "^6.0.3" + }, + "peerDependencies": { + "@metaplex-foundation/umi": "workspace:^", + "@solana/web3.js": "^1.72.0" + }, + "devDependencies": { + "@ava/typescript": "^3.0.1", + "@metaplex-foundation/umi": "workspace:^", + "@metaplex-foundation/umi-downloader-http": "workspace:^", + "@metaplex-foundation/umi-eddsa-web3js": "workspace:^", + "@metaplex-foundation/umi-http-fetch": "workspace:^", + "@metaplex-foundation/umi-rpc-web3js": "workspace:^", + "@solana/web3.js": "^1.72.0", + "ava": "^5.1.0" + }, + "publishConfig": { + "access": "public" + }, + "author": "Metaplex Maintainers ", + "homepage": "https://metaplex.com", + "repository": { + "url": "https://github.com/metaplex-foundation/umi.git" + }, + "typedoc": { + "entryPoint": "./src/index.ts", + "readmeFile": "./README.md", + "displayName": "umi-uploader-irys" + }, + "ava": { + "typescript": { + "compile": false, + "rewritePaths": { + "src/": "dist/test/src/", + "test/": "dist/test/test/" + } + } + } +} \ No newline at end of file diff --git a/packages/umi-uploader-irys/rollup.config.js b/packages/umi-uploader-irys/rollup.config.js new file mode 100644 index 00000000..ba38fd10 --- /dev/null +++ b/packages/umi-uploader-irys/rollup.config.js @@ -0,0 +1,16 @@ +import { createConfigs } from '../../rollup.config'; +import pkg from './package.json'; + +export default createConfigs({ + pkg, + builds: [ + { + dir: 'dist/esm', + format: 'es', + }, + { + dir: 'dist/cjs', + format: 'cjs', + }, + ], +}); diff --git a/packages/umi-uploader-irys/src/createIrysUploader.ts b/packages/umi-uploader-irys/src/createIrysUploader.ts new file mode 100644 index 00000000..99d5602d --- /dev/null +++ b/packages/umi-uploader-irys/src/createIrysUploader.ts @@ -0,0 +1,391 @@ +// eslint-disable-next-line import/no-named-default +import type { default as NodeIrys, WebIrys } from '@irys/sdk'; +import { + Commitment, + Context, + GenericFile, + GenericFileTag, + Keypair, + Signer, + SolAmount, + UploaderInterface, + base58, + createGenericFileFromJson, + createSignerFromKeypair, + isKeypairSigner, + lamports, + publicKey, + signTransaction, +} from '@metaplex-foundation/umi'; +import { + fromWeb3JsKeypair, + fromWeb3JsLegacyTransaction, + toWeb3JsLegacyTransaction, + toWeb3JsPublicKey, +} from '@metaplex-foundation/umi-web3js-adapters'; +import { + Connection as Web3JsConnection, + Keypair as Web3JsKeypair, + PublicKey as Web3JsPublicKey, + SendOptions as Web3JsSendOptions, + Signer as Web3JsSigner, + Transaction as Web3JsTransaction, + TransactionSignature as Web3JsTransactionSignature, +} from '@solana/web3.js'; +import BigNumber from 'bignumber.js'; +import { Buffer } from 'buffer'; +import { + AssetUploadFailedError, + IrysWithdrawError, + FailedToConnectToIrysAddressError, + FailedToInitializeIrysError, +} from './errors'; + +/** + * This method is necessary to import the Irys package on both ESM and CJS modules. + * Without this, we get a different structure on each module: + * - CJS: { default: [Getter], WebIrys: [Getter] } + * - ESM: { default: { default: [Getter], WebIrys: [Getter] } } + * This method fixes this by ensure there is not double default in the imported package. + */ +// eslint-disable-next-line @typescript-eslint/naming-convention +function _removeDoubleDefault(pkg: T): T { + if ( + pkg && + typeof pkg === 'object' && + 'default' in pkg && + 'default' in (pkg as any).default + ) { + return (pkg as any).default; + } + + return pkg; +} + +export type IrysUploader = UploaderInterface & { + irys: () => Promise; + getUploadPriceFromBytes: (bytes: number) => Promise; + getBalance: () => Promise; + fund: (amount: SolAmount, skipBalanceCheck: boolean) => Promise; + withdrawAll: (amount: SolAmount) => Promise; + withdraw: (amount: SolAmount) => Promise; +}; + +export type IrysUploaderOptions = { + address?: string; + timeout?: number; + providerUrl?: string; + priceMultiplier?: number; + payer?: Signer; +}; + +export type IrysWalletAdapter = { + publicKey: Web3JsPublicKey | null; + signMessage?: (message: Uint8Array) => Promise; + signTransaction?: ( + transaction: Web3JsTransaction + ) => Promise; + signAllTransactions?: ( + transactions: Web3JsTransaction[] + ) => Promise; + sendTransaction: ( + transaction: Web3JsTransaction, + connection: Web3JsConnection, + options?: Web3JsSendOptions & { signers?: Web3JsSigner[] } + ) => Promise; +}; + +// Size of Irys transaction header. +const HEADER_SIZE = 2_000; + +// Minimum file size for cost calculation. +const MINIMUM_SIZE = 80_000; + +export function createIrysUploader( + context: Pick, + options: IrysUploaderOptions = {} +): IrysUploader { + // eslint-disable-next-line @typescript-eslint/naming-convention + let _irys: WebIrys | NodeIrys | null = null; + options = { + providerUrl: context.rpc.getEndpoint(), + ...options, + }; + + const getUploadPriceFromBytes = async (bytes: number): Promise => { + const irys = await getIrys(); + const price = await irys.getPrice(bytes); + + return bigNumberToAmount( + price.multipliedBy(options.priceMultiplier ?? 1.1) + ); + }; + + const getUploadPrice = async (files: GenericFile[]): Promise => { + const bytes: number = files.reduce( + (sum, file) => + sum + HEADER_SIZE + Math.max(MINIMUM_SIZE, file.buffer.byteLength), + 0 + ); + + return getUploadPriceFromBytes(bytes); + }; + + const upload = async (files: GenericFile[]): Promise => { + const irys = await getIrys(); + const amount = await getUploadPrice(files); + await fund(amount); + + const promises = files.map(async (file) => { + const buffer = Buffer.from(file.buffer); + const irysTx = irys.createTransaction(buffer, { + tags: getGenericFileTagsWithContentType(file), + }); + await irysTx.sign(); + + const { status, data } = await irys.uploader.uploadTransaction(irysTx); + + if (status >= 300) { + throw new AssetUploadFailedError(status); + } + + return `https://arweave.net/${data.id}`; + }); + + return Promise.all(promises); + }; + + const uploadJson = async (json: T): Promise => { + const file = createGenericFileFromJson(json); + const uris = await upload([file]); + return uris[0]; + }; + + const getBalance = async (): Promise => { + const irys = await getIrys(); + const balance = await irys.getLoadedBalance(); + + return bigNumberToAmount(balance); + }; + + const fund = async ( + amount: SolAmount, + skipBalanceCheck = false + ): Promise => { + const irys = await getIrys(); + let toFund = amountToBigNumber(amount); + + if (!skipBalanceCheck) { + const balance = await irys.getLoadedBalance(); + + toFund = toFund.isGreaterThan(balance) + ? toFund.minus(balance) + : new BigNumber(0); + } + + if (toFund.isLessThanOrEqualTo(0)) { + return; + } + + await irys.fund(toFund); + }; + + const withdrawAll = async (): Promise => { + // TODO(loris): Replace with "withdrawAll" when available on Irys. + const irys = await getIrys(); + const balance = await irys.getLoadedBalance(); + const minimumBalance = new BigNumber(5000); + + if (balance.isLessThan(minimumBalance)) { + return; + } + + const balanceToWithdraw = balance.minus(minimumBalance); + await withdraw(bigNumberToAmount(balanceToWithdraw)); + }; + + const withdraw = async (amount: SolAmount): Promise => { + const irys = await getIrys(); + try { + await irys.withdrawBalance(amountToBigNumber(amount)); + } catch (e: any) { + throw new IrysWithdrawError( + e instanceof Error ? e.message : e.toString() + ); + } + }; + + const getIrys = async (): Promise => { + const oldPayer = _irys?.getSigner().publicKey; + const newPayer = options.payer ?? context.payer; + if ( + oldPayer && + publicKey(new Uint8Array(oldPayer)) !== newPayer.publicKey + ) { + _irys = null; + } + + if (!_irys) { + _irys = await initIrys(); + } + + return _irys; + }; + + const initIrys = async (): Promise => { + const currency = 'solana'; + const defaultAddress = + context.rpc.getCluster() === 'devnet' + ? 'https://devnet.irys.xyz' + : 'https://node1.irys.xyz'; + const address = options?.address ?? defaultAddress; + const irysOptions = { + timeout: options.timeout, + providerUrl: options.providerUrl, + }; + + const payer: Signer = options.payer ?? context.payer; + + // If in node use node irys, else use web irys. + const isNode = + // eslint-disable-next-line no-prototype-builtins + typeof window === 'undefined' || window.process?.hasOwnProperty('type'); + + let irys; + if (isNode && isKeypairSigner(payer)) + irys = await initNodeIrys(address, currency, payer, irysOptions); + else { + irys = await initWebIrys(address, currency, payer, irysOptions); + } + + try { + // Check for valid irys node. + await irys.utils.getBundlerAddress(currency); + } catch (error) { + throw new FailedToConnectToIrysAddressError(address, error as Error); + } + + return irys; + }; + + const initNodeIrys = async ( + address: string, + currency: string, + keypair: Keypair, + options: any + ): Promise => { + const bPackage = _removeDoubleDefault(await import('@irys/sdk')); + // eslint-disable-next-line new-cap + return new bPackage.default({ + url: address, + token: currency, + key: keypair.secretKey, + config: options, + }); + }; + + const initWebIrys = async ( + address: string, + currency: string, + payer: Signer, + options: any + ): Promise => { + const wallet: IrysWalletAdapter = { + publicKey: toWeb3JsPublicKey(payer.publicKey), + signMessage: (message: Uint8Array) => payer.signMessage(message), + signTransaction: async (web3JsTransaction: Web3JsTransaction) => + toWeb3JsLegacyTransaction( + await payer.signTransaction( + fromWeb3JsLegacyTransaction(web3JsTransaction) + ) + ), + signAllTransactions: async (web3JsTransactions: Web3JsTransaction[]) => { + const transactions = web3JsTransactions.map( + fromWeb3JsLegacyTransaction + ); + const signedTransactions = await payer.signAllTransactions( + transactions + ); + return signedTransactions.map(toWeb3JsLegacyTransaction); + }, + sendTransaction: async ( + web3JsTransaction: Web3JsTransaction, + connection: Web3JsConnection, + options: Web3JsSendOptions & { signers?: Web3JsSigner[] } = {} + ): Promise => { + const { signers: web3JsSigners = [], ...sendOptions } = options; + const signers = web3JsSigners.map((web3JsSigner) => + createSignerFromKeypair( + context, + fromWeb3JsKeypair( + Web3JsKeypair.fromSecretKey(web3JsSigner.secretKey) + ) + ) + ); + + let transaction = fromWeb3JsLegacyTransaction(web3JsTransaction); + transaction = await signTransaction(transaction, [payer, ...signers]); + + const signature = await context.rpc.sendTransaction(transaction, { + ...sendOptions, + preflightCommitment: sendOptions.preflightCommitment as Commitment, + }); + + return base58.deserialize(signature)[0]; + }, + }; + + const bPackage = _removeDoubleDefault(await import('@irys/sdk')); + const irys = new bPackage.WebIrys({ + url: address, + token: currency, + wallet: { provider: wallet }, + config: options, + }); + + try { + // Try to initiate irys. + await irys.ready(); + } catch (error) { + throw new FailedToInitializeIrysError(error as Error); + } + + return irys; + }; + + return { + getUploadPriceFromBytes, + getUploadPrice, + upload, + uploadJson, + getBalance, + fund, + withdrawAll, + withdraw, + irys: getIrys, + }; +} + +export const isIrysUploader = ( + uploader: UploaderInterface +): uploader is IrysUploader => + 'irys' in uploader && + 'getBalance' in uploader && + 'fund' in uploader && + 'withdrawAll' in uploader; + +const bigNumberToAmount = (bigNumber: BigNumber): SolAmount => + lamports(bigNumber.decimalPlaces(0).toString()); + +const amountToBigNumber = (amount: SolAmount): BigNumber => + new BigNumber(amount.basisPoints.toString()); + +const getGenericFileTagsWithContentType = ( + file: GenericFile +): GenericFileTag[] => { + if (!file.contentType) { + return file.tags; + } + + return [{ name: 'Content-Type', value: file.contentType }, ...file.tags]; +}; diff --git a/packages/umi-uploader-irys/src/errors.ts b/packages/umi-uploader-irys/src/errors.ts new file mode 100644 index 00000000..713e5218 --- /dev/null +++ b/packages/umi-uploader-irys/src/errors.ts @@ -0,0 +1,54 @@ +import { UmiError } from '@metaplex-foundation/umi'; + +export class IrysError extends UmiError { + readonly name: string = 'IrysError'; + + constructor(message: string, cause?: Error) { + super(message, 'plugin', 'Irys', cause); + } +} + +export class FailedToInitializeIrysError extends IrysError { + readonly name: string = 'FailedToInitializeIrysError'; + + constructor(cause: Error) { + const message = + 'Irys could not be initialized. ' + + 'Please check the underlying error below for more details.'; + super(message, cause); + } +} + +export class FailedToConnectToIrysAddressError extends IrysError { + readonly name: string = 'FailedToConnectToIrysAddressError'; + + constructor(address: string, cause: Error) { + const message = + `Irys could not connect to the provided address [${address}]. ` + + 'Please ensure the provided address is valid. Some valid addresses include: ' + + '"https://node1.irys.xyz" for mainnet and "https://devnet.irys.xyz" for devnet'; + super(message, cause); + } +} + +export class AssetUploadFailedError extends IrysError { + readonly name: string = 'AssetUploadFailedError'; + + constructor(status: number) { + const message = + `The asset could not be uploaded to the Irys network and ` + + `returned the following status code [${status}].`; + super(message); + } +} + +export class IrysWithdrawError extends IrysError { + readonly name: string = 'IrysWithdrawError'; + + constructor(error: string) { + const message = + `The balance could not be withdrawn from the Irys network and ` + + `returned the following error: ${error}.`; + super(message); + } +} diff --git a/packages/umi-uploader-irys/src/index.ts b/packages/umi-uploader-irys/src/index.ts new file mode 100644 index 00000000..0f1fca39 --- /dev/null +++ b/packages/umi-uploader-irys/src/index.ts @@ -0,0 +1,3 @@ +export * from './createIrysUploader'; +export * from './errors'; +export * from './plugin'; diff --git a/packages/umi-uploader-irys/src/plugin.ts b/packages/umi-uploader-irys/src/plugin.ts new file mode 100644 index 00000000..c9980d74 --- /dev/null +++ b/packages/umi-uploader-irys/src/plugin.ts @@ -0,0 +1,8 @@ +import type { UmiPlugin } from '@metaplex-foundation/umi'; +import { IrysUploaderOptions, createIrysUploader } from './createIrysUploader'; + +export const irysUploader = (options?: IrysUploaderOptions): UmiPlugin => ({ + install(umi) { + umi.uploader = createIrysUploader(umi, options); + }, +}); diff --git a/packages/umi-uploader-irys/test/IrysUploader.test.ts b/packages/umi-uploader-irys/test/IrysUploader.test.ts new file mode 100644 index 00000000..7dcd0167 --- /dev/null +++ b/packages/umi-uploader-irys/test/IrysUploader.test.ts @@ -0,0 +1,53 @@ +import { + Context, + createGenericFile, + createUmi, + generatedSignerIdentity, + sol, + utf8, +} from '@metaplex-foundation/umi'; +import { httpDownloader } from '@metaplex-foundation/umi-downloader-http'; +import { web3JsEddsa } from '@metaplex-foundation/umi-eddsa-web3js'; +import { fetchHttp } from '@metaplex-foundation/umi-http-fetch'; +import { web3JsRpc } from '@metaplex-foundation/umi-rpc-web3js'; +import test from 'ava'; +import { irysUploader, IrysUploaderOptions } from '../src'; + +test('example test', async (t) => { + t.is(typeof irysUploader, 'function'); +}); + +// TODO(loris): Unskip these tests when we can mock the Irys API. + +const getContext = async (options?: IrysUploaderOptions): Promise => { + const context = createUmi().use({ + install(umi) { + umi.use(web3JsRpc('https://metaplex.devnet.rpcpool.com/')); + umi.use(web3JsEddsa()); + umi.use(fetchHttp()); + umi.use(httpDownloader()); + umi.use(irysUploader(options)); + umi.use(generatedSignerIdentity()); + }, + }); + await context.rpc.airdrop(context.payer.publicKey, sol(1)); + return context; +}; + +test.skip('it can upload one file', async (t) => { + // Given a Context using NFT.Storage. + const context = await getContext(); + + // When we upload some asset. + const [uri] = await context.uploader.upload([ + createGenericFile('some-image', 'some-image.jpg'), + ]); + + // Then the URI should be a valid IPFS URI. + t.truthy(uri); + t.true(uri.startsWith('https://nftstorage.link/ipfs/')); + + // and it should point to the uploaded asset. + const [asset] = await context.downloader.download([uri]); + t.is(utf8.deserialize(asset.buffer)[0], 'some-image'); +}); diff --git a/packages/umi-uploader-irys/test/modules/cjs.test.cjs b/packages/umi-uploader-irys/test/modules/cjs.test.cjs new file mode 100644 index 00000000..8d661ce7 --- /dev/null +++ b/packages/umi-uploader-irys/test/modules/cjs.test.cjs @@ -0,0 +1,30 @@ +/* eslint-disable import/no-extraneous-dependencies */ +const test = require('ava'); +const { + createUmi, + generatedSignerIdentity, +} = require('@metaplex-foundation/umi'); +const { web3JsRpc } = require('@metaplex-foundation/umi-rpc-web3js'); +const { web3JsEddsa } = require('@metaplex-foundation/umi-eddsa-web3js'); +const exported = require('../../dist/cjs/index.cjs'); + +test('it successfully exports commonjs named exports', (t) => { + const exportedKeys = Object.keys(exported); + + t.true(exportedKeys.includes('createIrysUploader')); +}); + +test('it can import the Irys client', async (t) => { + const { createIrysUploader } = exported; + const context = createUmi() + .use(web3JsRpc('http://localhost:8899')) + .use(web3JsEddsa()) + .use(generatedSignerIdentity()); + const irysUploader = createIrysUploader(context); + const irys = await irysUploader.irys(); + t.true(typeof irys === 'object', 'Irys is an object'); + t.true('uploader' in irys, 'Irys can upload'); + t.true('getLoadedBalance' in irys, 'Irys can get the loaded balance'); + t.true('fund' in irys, 'Irys can fund'); + t.true('withdrawBalance' in irys, 'Irys can withdraw'); +}); diff --git a/packages/umi-uploader-irys/test/modules/esm.test.mjs b/packages/umi-uploader-irys/test/modules/esm.test.mjs new file mode 100644 index 00000000..7151ffb1 --- /dev/null +++ b/packages/umi-uploader-irys/test/modules/esm.test.mjs @@ -0,0 +1,28 @@ +/* eslint-disable import/extensions */ +/* eslint-disable import/no-extraneous-dependencies */ +import test from 'ava'; +import { createUmi, generatedSignerIdentity } from '@metaplex-foundation/umi'; +import { web3JsRpc } from '@metaplex-foundation/umi-rpc-web3js'; +import { web3JsEddsa } from '@metaplex-foundation/umi-eddsa-web3js'; +import * as exported from '../../dist/esm/index.mjs'; + +test('it successfully exports esm named exports', (t) => { + const exportedKeys = Object.keys(exported); + + t.true(exportedKeys.includes('createIrysUploader')); +}); + +test('it can import the Irys client', async (t) => { + const { createIrysUploader } = exported; + const context = createUmi() + .use(web3JsRpc('http://localhost:8899')) + .use(web3JsEddsa()) + .use(generatedSignerIdentity()); + const irysUploader = createIrysUploader(context); + const irys = await irysUploader.irys(); + t.true(typeof irys === 'object', 'Irys is an object'); + t.true('uploader' in irys, 'Irys can upload'); + t.true('getLoadedBalance' in irys, 'Irys can get the loaded balance'); + t.true('fund' in irys, 'Irys can fund'); + t.true('withdrawBalance' in irys, 'Irys can withdraw'); +}); diff --git a/packages/umi-uploader-irys/test/tsconfig.json b/packages/umi-uploader-irys/test/tsconfig.json new file mode 100644 index 00000000..2390f598 --- /dev/null +++ b/packages/umi-uploader-irys/test/tsconfig.json @@ -0,0 +1,11 @@ +{ + "extends": "../../../tsconfig.json", + "include": ["./**/*"], + "compilerOptions": { + "module": "commonjs", + "outDir": "../dist/test", + "declarationDir": null, + "declaration": false, + "emitDeclarationOnly": false + } +} diff --git a/packages/umi-uploader-irys/tsconfig.json b/packages/umi-uploader-irys/tsconfig.json new file mode 100644 index 00000000..89a681d0 --- /dev/null +++ b/packages/umi-uploader-irys/tsconfig.json @@ -0,0 +1,8 @@ +{ + "extends": "../../tsconfig.json", + "include": ["src"], + "compilerOptions": { + "outDir": "dist/esm", + "declarationDir": "dist/types" + } +} diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 30f721f5..05f0d5c6 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -1,5 +1,9 @@ lockfileVersion: '6.0' +settings: + autoInstallPeers: true + excludeLinksFromLockfile: false + patchedDependencies: '@changesets/assemble-release-plan@5.2.3': hash: psjonfb234vefryc6hzdzm5ple @@ -566,6 +570,46 @@ importers: specifier: ^5.1.0 version: 5.1.0(@ava/typescript@3.0.1) + packages/umi-uploader-irys: + dependencies: + '@irys/sdk': + specifier: ^0.0.2 + version: 0.0.2(arweave@1.12.4) + '@metaplex-foundation/umi-web3js-adapters': + specifier: workspace:^ + version: link:../umi-web3js-adapters + bignumber.js: + specifier: ^9.0.2 + version: 9.1.1 + buffer: + specifier: ^6.0.3 + version: 6.0.3 + devDependencies: + '@ava/typescript': + specifier: ^3.0.1 + version: 3.0.1 + '@metaplex-foundation/umi': + specifier: workspace:^ + version: link:../umi + '@metaplex-foundation/umi-downloader-http': + specifier: workspace:^ + version: link:../umi-downloader-http + '@metaplex-foundation/umi-eddsa-web3js': + specifier: workspace:^ + version: link:../umi-eddsa-web3js + '@metaplex-foundation/umi-http-fetch': + specifier: workspace:^ + version: link:../umi-http-fetch + '@metaplex-foundation/umi-rpc-web3js': + specifier: workspace:^ + version: link:../umi-rpc-web3js + '@solana/web3.js': + specifier: ^1.72.0 + version: 1.72.0 + ava: + specifier: ^5.1.0 + version: 5.1.0(@ava/typescript@3.0.1) + packages/umi-uploader-nft-storage: dependencies: '@ipld/dag-pb': @@ -2947,13 +2991,14 @@ packages: /@bundlr-network/client@0.8.9: resolution: {integrity: sha512-SJ7BAt/KhONeFQ0+nbqrw2DUWrsev6y6cmlXt+3x7fPCkw7OJwudtxV/h2nBteZd65NXjqw8yzkmLiLfZ7CCRA==} + deprecated: Bundlr is now Irys - please switch to @irys/sdk - this package will remain compatible with Irys for the foreseeable future. hasBin: true dependencies: - '@solana/wallet-adapter-base': 0.9.20(@solana/web3.js@1.72.0) + '@solana/wallet-adapter-base': 0.9.23(@solana/web3.js@1.72.0) '@solana/web3.js': 1.72.0 - '@supercharge/promise-pool': 2.3.2 + '@supercharge/promise-pool': 2.4.0 algosdk: 1.24.1 - arbundles: 0.6.22(@solana/web3.js@1.72.0) + arbundles: 0.6.23(@solana/web3.js@1.72.0) arweave: 1.12.4 async-retry: 1.3.3 axios: 0.25.0(debug@4.3.4) @@ -2961,7 +3006,7 @@ packages: bignumber.js: 9.1.1 bs58: 4.0.1 commander: 8.3.0 - csv: 6.2.6 + csv: 6.3.5 ethers: 5.7.2 inquirer: 8.2.5 js-sha256: 0.9.0 @@ -3811,6 +3856,67 @@ packages: multiformats: 9.9.0 dev: false + /@irys/arweave@0.0.2: + resolution: {integrity: sha512-ddE5h4qXbl0xfGlxrtBIwzflaxZUDlDs43TuT0u1OMfyobHul4AA1VEX72Rpzw2bOh4vzoytSqA1jCM7x9YtHg==} + dependencies: + asn1.js: 5.4.1 + async-retry: 1.3.3 + axios: 1.5.1 + base64-js: 1.5.1 + bignumber.js: 9.1.1 + transitivePeerDependencies: + - debug + dev: false + + /@irys/query@0.0.1: + resolution: {integrity: sha512-7TCyR+Qn+F54IQQx5PlERgqNwgIQik8hY55iZl/silTHhCo1MI2pvx5BozqPUVCc8/KqRsc2nZd8Bc29XGUjRQ==} + engines: {node: '>=16.10.0'} + dependencies: + async-retry: 1.3.3 + axios: 1.5.1 + transitivePeerDependencies: + - debug + dev: false + + /@irys/sdk@0.0.2(arweave@1.12.4): + resolution: {integrity: sha512-un/e/CmTpgT042gDwCN3AtISrR9OYGMY6V+442pFmSWKrwrsDoIXZ8VlLiYKnrtTm+yquGhjfYy0LDqGWq41pA==} + engines: {node: '>=16.10.0'} + hasBin: true + dependencies: + '@ethersproject/bignumber': 5.7.0 + '@ethersproject/contracts': 5.7.0 + '@ethersproject/providers': 5.7.2 + '@ethersproject/wallet': 5.7.0 + '@irys/query': 0.0.1 + '@near-js/crypto': 0.0.3 + '@near-js/keystores-browser': 0.0.3 + '@near-js/providers': 0.0.4 + '@near-js/transactions': 0.1.1 + '@solana/web3.js': 1.72.0 + '@supercharge/promise-pool': 3.1.0 + algosdk: 1.24.1 + aptos: 1.8.5 + arbundles: 0.10.0(arweave@1.12.4) + async-retry: 1.3.3 + axios: 1.5.1 + base64url: 3.0.1 + bignumber.js: 9.1.1 + bs58: 5.0.0 + commander: 8.3.0 + csv: 5.5.3 + inquirer: 8.2.5 + js-sha256: 0.9.0 + mime-types: 2.1.35 + near-seed-phrase: 0.2.0 + transitivePeerDependencies: + - arweave + - bufferutil + - debug + - encoding + - supports-color + - utf-8-validate + dev: false + /@jridgewell/gen-mapping@0.1.1: resolution: {integrity: sha512-sQXCasFk+U8lWYEe66WxRDOE9PjVz4vSM51fTu3Hw+ClTpUSQb718772vH3pyS5pShp6lvQM7SxgIDXXXmOX7w==} engines: {node: '>=6.0.0'} @@ -3987,6 +4093,130 @@ packages: murmurhash3js-revisited: 3.0.0 dev: false + /@near-js/crypto@0.0.3: + resolution: {integrity: sha512-3WC2A1a1cH8Cqrx+0iDjp1ASEEhxN/KHEMENYb0KZH6Hp5bXIY7Akt4quC7JlgJS5ESvEiLa40tS5h0zAhBWGw==} + dependencies: + '@near-js/types': 0.0.3 + bn.js: 5.2.1 + borsh: 0.7.0 + tweetnacl: 1.0.3 + dev: false + + /@near-js/crypto@0.0.4: + resolution: {integrity: sha512-2mSIVv6mZway1rQvmkktrXAFoUvy7POjrHNH3LekKZCMCs7qMM/23Hz2+APgxZPqoV2kjarSNOEYJjxO7zQ/rQ==} + dependencies: + '@near-js/types': 0.0.4 + bn.js: 5.2.1 + borsh: 0.7.0 + tweetnacl: 1.0.3 + dev: false + + /@near-js/keystores-browser@0.0.3: + resolution: {integrity: sha512-Ve/JQ1SBxdNk3B49lElJ8Y54AoBY+yOStLvdnUIpe2FBOczzwDCkcnPcMDV0NMwVlHpEnOWICWHbRbAkI5Vs+A==} + dependencies: + '@near-js/crypto': 0.0.3 + '@near-js/keystores': 0.0.3 + dev: false + + /@near-js/keystores@0.0.3: + resolution: {integrity: sha512-mnwLYUt4Td8u1I4QE1FBx2d9hMt3ofiriE93FfOluJ4XiqRqVFakFYiHg6pExg5iEkej/sXugBUFeQ4QizUnew==} + dependencies: + '@near-js/crypto': 0.0.3 + '@near-js/types': 0.0.3 + dev: false + + /@near-js/keystores@0.0.4: + resolution: {integrity: sha512-+vKafmDpQGrz5py1liot2hYSjPGXwihveeN+BL11aJlLqZnWBgYJUWCXG+uyGjGXZORuy2hzkKK6Hi+lbKOfVA==} + dependencies: + '@near-js/crypto': 0.0.4 + '@near-js/types': 0.0.4 + dev: false + + /@near-js/providers@0.0.4: + resolution: {integrity: sha512-g/2pJTYmsIlTW4mGqeRlqDN9pZeN+1E2/wfoMIf3p++boBVxVlaSebtQgawXAf2lkfhb9RqXz5pHqewXIkTBSw==} + dependencies: + '@near-js/transactions': 0.1.0 + '@near-js/types': 0.0.3 + '@near-js/utils': 0.0.3 + bn.js: 5.2.1 + borsh: 0.7.0 + http-errors: 1.8.1 + optionalDependencies: + node-fetch: 2.6.9 + transitivePeerDependencies: + - encoding + dev: false + + /@near-js/signers@0.0.3: + resolution: {integrity: sha512-u1R+DDIua5PY1PDFnpVYqdMgQ7c4dyeZsfqMjE7CtgzdqupgTYCXzJjBubqMlAyAx843PoXmLt6CSSKcMm0WUA==} + dependencies: + '@near-js/crypto': 0.0.3 + '@near-js/keystores': 0.0.3 + js-sha256: 0.9.0 + dev: false + + /@near-js/signers@0.0.4: + resolution: {integrity: sha512-xCglo3U/WIGsz/izPGFMegS5Q3PxOHYB8a1E7RtVhNm5QdqTlQldLCm/BuMg2G/u1l1ZZ0wdvkqRTG9joauf3Q==} + dependencies: + '@near-js/crypto': 0.0.4 + '@near-js/keystores': 0.0.4 + js-sha256: 0.9.0 + dev: false + + /@near-js/transactions@0.1.0: + resolution: {integrity: sha512-OrrDFqhX0rtH+6MV3U3iS+zmzcPQI+L4GJi9na4Uf8FgpaVPF0mtSmVrpUrS5CC3LwWCzcYF833xGYbXOV4Kfg==} + dependencies: + '@near-js/crypto': 0.0.3 + '@near-js/signers': 0.0.3 + '@near-js/types': 0.0.3 + '@near-js/utils': 0.0.3 + bn.js: 5.2.1 + borsh: 0.7.0 + js-sha256: 0.9.0 + dev: false + + /@near-js/transactions@0.1.1: + resolution: {integrity: sha512-Fk83oLLFK7nz4thawpdv9bGyMVQ2i48iUtZEVYhuuuqevl17tSXMlhle9Me1ZbNyguJG/cWPdNybe1UMKpyGxA==} + dependencies: + '@near-js/crypto': 0.0.4 + '@near-js/signers': 0.0.4 + '@near-js/types': 0.0.4 + '@near-js/utils': 0.0.4 + bn.js: 5.2.1 + borsh: 0.7.0 + js-sha256: 0.9.0 + dev: false + + /@near-js/types@0.0.3: + resolution: {integrity: sha512-gC3iGUT+r2JjVsE31YharT+voat79ToMUMLCGozHjp/R/UW1M2z4hdpqTUoeWUBGBJuVc810gNTneHGx0jvzwQ==} + dependencies: + bn.js: 5.2.1 + dev: false + + /@near-js/types@0.0.4: + resolution: {integrity: sha512-8TTMbLMnmyG06R5YKWuS/qFG1tOA3/9lX4NgBqQPsvaWmDsa+D+QwOkrEHDegped0ZHQwcjAXjKML1S1TyGYKg==} + dependencies: + bn.js: 5.2.1 + dev: false + + /@near-js/utils@0.0.3: + resolution: {integrity: sha512-J72n/EL0VfLRRb4xNUF4rmVrdzMkcmkwJOhBZSTWz3PAZ8LqNeU9ZConPfMvEr6lwdaD33ZuVv70DN6IIjPr1A==} + dependencies: + '@near-js/types': 0.0.3 + bn.js: 5.2.1 + depd: 2.0.0 + mustache: 4.2.0 + dev: false + + /@near-js/utils@0.0.4: + resolution: {integrity: sha512-mPUEPJbTCMicGitjEGvQqOe8AS7O4KkRCxqd0xuE/X6gXF1jz1pYMZn4lNUeUz2C84YnVSGLAM0o9zcN6Y4hiA==} + dependencies: + '@near-js/types': 0.0.4 + bn.js: 5.2.1 + depd: 2.0.0 + mustache: 4.2.0 + dev: false + /@nftstorage/metaplex-auth@1.2.0(node-fetch@2.6.9)(typescript@4.9.5): resolution: {integrity: sha512-ffT/cZv1GWXDVrwzNUGGxApDwQJSxUZJAqnPpTk5VBc55T2RtUm2yZ11p74h2fyam1erJH38zg7S9IoaTxSZ8w==} dependencies: @@ -4026,6 +4256,10 @@ packages: /@noble/ed25519@1.7.1: resolution: {integrity: sha512-Rk4SkJFaXZiznFyC/t77Q0NKS4FL7TLJJsVG2V2oiEq3kJVeTdxysEe/yRWSpnWMe808XRDJ+VFh5pt/FN5plw==} + /@noble/hashes@1.1.3: + resolution: {integrity: sha512-CE0FCR57H2acVI5UOzIGSSIYxZ6v/HOhDR0Ro9VLyhnzLwx0o8W1mmgaqlEUx4049qJDlIBRztv5k+MM8vbO3A==} + dev: false + /@noble/hashes@1.2.0: resolution: {integrity: sha512-FZfhjEDbT5GRswV3C6uvLPHMiVD6lQBmpoX5+eSiPaMTXte/IKqI5dykDxzZB/WBeK/CDuQRBWarPdi3FNY2zQ==} @@ -4125,10 +4359,12 @@ packages: /@randlabs/communication-bridge@1.0.1: resolution: {integrity: sha512-CzS0U8IFfXNK7QaJFE4pjbxDGfPjbXBEsEaCn9FN15F+ouSAEUQkva3Gl66hrkBZOGexKFEWMwUHIDKpZ2hfVg==} + requiresBuild: true dev: false /@randlabs/myalgo-connect@1.4.2: resolution: {integrity: sha512-K9hEyUi7G8tqOp7kWIALJLVbGCByhilcy6123WfcorxWwiE1sbQupPyIU5f3YdQK6wMjBsyTWiLW52ZBMp7sXA==} + requiresBuild: true dependencies: '@randlabs/communication-bridge': 1.0.1 dev: false @@ -4349,6 +4585,17 @@ packages: picomatch: 2.3.1 dev: true + /@scure/base@1.1.3: + resolution: {integrity: sha512-/+SgoRjLq7Xlf0CWuLHq2LUZeL/w65kfzAPG5NH9pcmBhs+nunQTn4gvdwgMTIXnt9b2C/1SeL2XiysZEyIC9Q==} + dev: false + + /@scure/bip39@1.1.0: + resolution: {integrity: sha512-pwrPOS16VeTKg98dYXQyIjJEcWfz7/1YJIwxUEPFfQPtc86Ym/1sVgQ2RLoD43AazMk2l/unK4ITySSpW2+82w==} + dependencies: + '@noble/hashes': 1.1.3 + '@scure/base': 1.1.3 + dev: false + /@sideway/address@4.1.4: resolution: {integrity: sha512-7vwq+rOHVWjyXxVlR76Agnvhy8I9rpzjosTESvmhNeXOXdZZB15Fl+TI9x1SiHZH5Jv2wTGduSxFDIaq0m3DUw==} dependencies: @@ -4451,16 +4698,27 @@ packages: - utf-8-validate dev: true - /@solana/wallet-adapter-base@0.9.20(@solana/web3.js@1.72.0): - resolution: {integrity: sha512-ZvnhJ4EJk61oyuBH/a9tMpUfeWQ3g3Cc0Nzl1NzE4SdqEhiNoEW8HXDig9HMemZ9bIEUxIpPWxp+SwjVl0u+rg==} + /@solana/wallet-adapter-base@0.9.23(@solana/web3.js@1.72.0): + resolution: {integrity: sha512-apqMuYwFp1jFi55NxDfvXUX2x1T0Zh07MxhZ/nCCTGys5raSfYUh82zen2BLv8BSDj/JxZ2P/s7jrQZGrX8uAw==} engines: {node: '>=16'} peerDependencies: - '@solana/web3.js': ^1.58.0 + '@solana/web3.js': ^1.77.3 dependencies: + '@solana/wallet-standard-features': 1.1.0 '@solana/web3.js': 1.72.0 + '@wallet-standard/base': 1.0.1 + '@wallet-standard/features': 1.0.3 eventemitter3: 4.0.7 dev: false + /@solana/wallet-standard-features@1.1.0: + resolution: {integrity: sha512-oVyygxfYkkF5INYL0GuD8GFmNO/wd45zNesIqGCFE6X66BYxmI6HmyzQJCcZTZ0BNsezlVg4t+3MCL5AhfFoGA==} + engines: {node: '>=16'} + dependencies: + '@wallet-standard/base': 1.0.1 + '@wallet-standard/features': 1.0.3 + dev: false + /@solana/web3.js@1.72.0: resolution: {integrity: sha512-xMoCk0y/GpiQhHbRjMcrd5NpmkwhAA0c01id7lrr6nhNdz6Uc/CywPdBeZw3Qz6BVZ/qlUoerpKPWeiXqMUjwA==} engines: {node: '>=12.20.0'} @@ -4487,8 +4745,13 @@ packages: - supports-color - utf-8-validate - /@supercharge/promise-pool@2.3.2: - resolution: {integrity: sha512-f5+C7zv+QQivcUO1FH5lXi7GcuJ3CFuJF3Eg06iArhUs5ma0szCLEQwIY4+VQyh7m/RLVZdzvr4E4ZDnLe9MNg==} + /@supercharge/promise-pool@2.4.0: + resolution: {integrity: sha512-O9CMipBlq5OObdt1uKJGIzm9cdjpPWfj+a+Zw9EgWKxaMNHKC7EU7X9taj3H0EGQNLOSq2jAcOa3EzxlfHsD6w==} + engines: {node: '>=8'} + dev: false + + /@supercharge/promise-pool@3.1.0: + resolution: {integrity: sha512-gB3NukbIcYzRtPoE6dx9svQYPodxvnfQlaaQd8N/z87E6WaMfRE7o5HwB+LZ+KeM0nsNAq1n4TmBtfz1VCUR+Q==} engines: {node: '>=8'} dev: false @@ -5112,6 +5375,18 @@ packages: resolution: {integrity: sha512-Ewzq5Yhimg7pSztDV+RH1UDKBzmtqieXQlpTVm2AwraoRL/Rks96mvd8Vgi7Lj+h+TH8dv7mXD3FRZR3TUvbSg==} dev: true + /@wallet-standard/base@1.0.1: + resolution: {integrity: sha512-1To3ekMfzhYxe0Yhkpri+Fedq0SYcfrOfJi3vbLjMwF2qiKPjTGLwZkf2C9ftdQmxES+hmxhBzTwF4KgcOwf8w==} + engines: {node: '>=16'} + dev: false + + /@wallet-standard/features@1.0.3: + resolution: {integrity: sha512-m8475I6W5LTatTZuUz5JJNK42wFRgkJTB0I9tkruMwfqBF2UN2eomkYNVf9RbrsROelCRzSFmugqjKZBFaubsA==} + engines: {node: '>=16'} + dependencies: + '@wallet-standard/base': 1.0.1 + dev: false + /@web-std/blob@2.1.3: resolution: {integrity: sha512-K94rkZpa8yDEylkniNmK0aCYpkZe7wWn8GHNpyM+ckBQuRqhRmX0NG9d1b1f4pX3FKdLcfp7vTj6FjfdcjO3rQ==} dependencies: @@ -5388,16 +5663,58 @@ packages: resolution: {integrity: sha512-lYe4Gx7QT+MKGbDsA+Z+he/Wtef0BiwDOlK/XkBrdfsh9J/jPPXbX0tE9x9cl27Tmu5gg3QUbUrQYa/y+KOHPQ==} dev: true - /arbundles@0.6.22(@solana/web3.js@1.72.0): - resolution: {integrity: sha512-QlSavBHk59mNqgQ6ScxlqaBJlDbSmSrK/uTcF3HojLAZ/4aufTkVTBjl1hSfZ/ZN45oIPgJC05R8SmVARF+8VA==} + /aptos@1.8.5: + resolution: {integrity: sha512-iQxliWesNHjGQ5YYXCyss9eg4+bDGQWqAZa73vprqGQ9tungK0cRjUI2fmnp63Ed6UG6rurHrL+b0ckbZAOZZQ==} + engines: {node: '>=11.0.0'} dependencies: + '@noble/hashes': 1.1.3 + '@scure/bip39': 1.1.0 + axios: 0.27.2 + form-data: 4.0.0 + tweetnacl: 1.0.3 + transitivePeerDependencies: + - debug + dev: false + + /arbundles@0.10.0(arweave@1.12.4): + resolution: {integrity: sha512-Prbkjb0RSR6ToXPaBFhsBiMYSq78vHWbG/Zzy1tALRGvnKYlNLq93cqtmCNHqaYP6YCBZZV05ZpbO5C6269saw==} + dependencies: + '@ethersproject/bytes': 5.7.0 + '@ethersproject/hash': 5.7.0 + '@ethersproject/providers': 5.7.2 + '@ethersproject/signing-key': 5.7.0 + '@ethersproject/transactions': 5.7.0 + '@ethersproject/wallet': 5.7.0 + '@irys/arweave': 0.0.2 '@noble/ed25519': 1.7.1 + base64url: 3.0.1 + bs58: 4.0.1 + keccak: 3.0.3 + secp256k1: 5.0.0 + optionalDependencies: '@randlabs/myalgo-connect': 1.4.2 - '@solana/wallet-adapter-base': 0.9.20(@solana/web3.js@1.72.0) + algosdk: 1.24.1 + arweave-stream-tx: 1.2.2(arweave@1.12.4) + multistream: 4.1.0 + tmp-promise: 3.0.3 + transitivePeerDependencies: + - arweave + - bufferutil + - debug + - encoding + - utf-8-validate + dev: false + + /arbundles@0.6.23(@solana/web3.js@1.72.0): + resolution: {integrity: sha512-+gr93F3fivN+6dhiImT6BQNaXz4oECPn2GYjCZjS2yEoq7hM78FRvVp6kQyjEdhnuBFQr/q4oS/nkjnQlHdj9Q==} + dependencies: + '@noble/ed25519': 1.7.1 + '@randlabs/myalgo-connect': 1.4.2 + '@solana/wallet-adapter-base': 0.9.23(@solana/web3.js@1.72.0) algosdk: 1.24.1 arweave: 1.12.4 arweave-stream-tx: 1.2.2(arweave@1.12.4) - avsc: github.com/Bundlr-Network/avsc/a730cc8018b79e114b6a3381bbb57760a24c6cef + avsc: github.com/Irys-xyz/avsc/a730cc8018b79e114b6a3381bbb57760a24c6cef axios: 0.21.4(debug@4.3.4) base64url: 3.0.1 bs58: 4.0.1 @@ -5540,6 +5857,7 @@ packages: /arweave-stream-tx@1.2.2(arweave@1.12.4): resolution: {integrity: sha512-bNt9rj0hbAEzoUZEF2s6WJbIz8nasZlZpxIw03Xm8fzb9gRiiZlZGW3lxQLjfc9Z0VRUWDzwtqoYeEoB/JDToQ==} + requiresBuild: true peerDependencies: arweave: ^1.10.0 dependencies: @@ -5603,7 +5921,6 @@ packages: /asynckit@0.4.0: resolution: {integrity: sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==} - dev: true /ava@5.1.0(@ava/typescript@3.0.1): resolution: {integrity: sha512-e5VFrSQ0WBPyZJWRXVrO7RFOizFeNM0t2PORwrPvWtApgkORI6cvGnY3GX1G+lzpd0HjqNx5Jus22AhxVnUMNA==} @@ -5684,6 +6001,25 @@ packages: transitivePeerDependencies: - debug + /axios@0.27.2: + resolution: {integrity: sha512-t+yRIyySRTp/wua5xEr+z1q60QmLq8ABsS5O9Me1AsE5dfKqgnCFzwiCZZ/cGNd1lq4/7akDWMxdhVlucjmnOQ==} + dependencies: + follow-redirects: 1.15.2(debug@4.3.4) + form-data: 4.0.0 + transitivePeerDependencies: + - debug + dev: false + + /axios@1.5.1: + resolution: {integrity: sha512-Q28iYCWzNHjAm+yEAot5QaAMxhMghWLFVf7rRdwhUI+c2jix2DUXjAHXVi+s1ibs3mjPO/cCgbA++3BjD0vP/A==} + dependencies: + follow-redirects: 1.15.2(debug@4.3.4) + form-data: 4.0.0 + proxy-from-env: 1.1.0 + transitivePeerDependencies: + - debug + dev: false + /babel-plugin-polyfill-corejs2@0.3.3(@babel/core@7.20.5): resolution: {integrity: sha512-8hOdmFYFSZhqg2C/JgLUQ+t52o5nirNwaWM2B9LWteozwIvM14VSwdsCAUET10qT+kmySAlseadmfeeSWFCy+Q==} peerDependencies: @@ -5732,6 +6068,10 @@ packages: dependencies: safe-buffer: 5.2.1 + /base-x@4.0.0: + resolution: {integrity: sha512-FuwxlW4H5kh37X/oW59pwTzzTKRzfrrQwhmyspRM7swOEZcHtDZSCt45U6oKgtuFE+WYPblePMVIPR4RZrh/hw==} + dev: false + /base64-js@1.5.1: resolution: {integrity: sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==} @@ -5950,6 +6290,12 @@ packages: dependencies: base-x: 3.0.9 + /bs58@5.0.0: + resolution: {integrity: sha512-r+ihvQJvahgYT50JD05dyJNKlmmSlMoOGwn1lCcEzanPglg7TxYjioQUYehQ9mAR/+hOSd2jRc/Z2y5UxBymvQ==} + dependencies: + base-x: 4.0.0 + dev: false + /buffer-from@1.1.2: resolution: {integrity: sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==} dev: true @@ -6304,7 +6650,6 @@ packages: engines: {node: '>= 0.8'} dependencies: delayed-stream: 1.0.0 - dev: true /comma-separated-tokens@2.0.3: resolution: {integrity: sha512-Fu4hJdvzeylCfQPp9SGWidpzrMs7tTrlu6Vb8XGaRGck8QSNZJJp538Wrb60Lax4fPwR64ViY468OIUTbRlGZg==} @@ -6539,26 +6884,23 @@ packages: /csv-generate@3.4.3: resolution: {integrity: sha512-w/T+rqR0vwvHqWs/1ZyMDWtHHSJaN06klRqJXBEpDJaM/+dZkso0OKh1VcuuYvK3XM53KysVNq8Ko/epCK8wOw==} - dev: true - /csv-generate@4.2.1: - resolution: {integrity: sha512-w6GFHjvApv6bcJ2xdi9JGsH6ZvUBfC+vUdfefnEzurXG6hMRwzkBLnhztU2H7v7+zfCk1I/knnQ+tGbgpxWrBw==} + /csv-generate@4.3.0: + resolution: {integrity: sha512-7KdVId/2RgwPIKfWHaHtjBq7I9mgdi8ICzsUyIhP8is6UwpwVGGSC/aPnrZ8/SkgBcCP20lXrdPuP64Irs1VBg==} dev: false /csv-parse@4.16.3: resolution: {integrity: sha512-cO1I/zmz4w2dcKHVvpCr7JVRu8/FymG5OEpmvsZYlccYolPBLoVGKUHgNoc4ZGkFeFlWGEDmMyBM+TTqRdW/wg==} - dev: true - /csv-parse@5.3.4: - resolution: {integrity: sha512-f2E4NzkIX4bVIx5Ff2gKT1BlVwyFQ+2iFy+QrqgUXaFLUo7vSzN6XQ8LV5V/T/p/9g7mJdtYHKLkwG5PiG82fg==} + /csv-parse@5.5.2: + resolution: {integrity: sha512-YRVtvdtUNXZCMyK5zd5Wty1W6dNTpGKdqQd4EQ8tl/c6KW1aMBB1Kg1ppky5FONKmEqGJ/8WjLlTNLPne4ioVA==} dev: false /csv-stringify@5.6.5: resolution: {integrity: sha512-PjiQ659aQ+fUTQqSrd1XEDnOr52jh30RBurfzkscaE2tPaFsDH5wOAHJiw8XAHphRknCwMUE9KRayc4K/NbO8A==} - dev: true - /csv-stringify@6.2.3: - resolution: {integrity: sha512-4qGjUMwnlaRc00gc2jrIYh2w/h1fo25B0mTuY9K8fBiIgtmCX3LcgUbrEGViL98Ci4Se/F5LFEtu8k+dItJVZQ==} + /csv-stringify@6.4.4: + resolution: {integrity: sha512-NDshLupGa7gp4UG4sSNIqwYJqgSwvds0SvENntxoVoVvTzXcrHvd5gG2MWpbRpSNvk59dlmIe1IwNvSxN4IVmg==} dev: false /csv@5.5.3: @@ -6569,16 +6911,15 @@ packages: csv-parse: 4.16.3 csv-stringify: 5.6.5 stream-transform: 2.1.3 - dev: true - /csv@6.2.6: - resolution: {integrity: sha512-0grPtZ92uscXTGw52f/wARz66f5TrDy6nD5lG77idnH94sgOVmDiimHeLQTj7x9bkK0nmbWuHXywWluwG04xtA==} + /csv@6.3.5: + resolution: {integrity: sha512-Y+KTCAUljtq2JaGP42ZL1bymqlU5BkfnFpZhxRczGFDZox2VXhlRHnG5DRshyUrwQzmCdEiLjSqNldCfm1OVCA==} engines: {node: '>= 0.1.90'} dependencies: - csv-generate: 4.2.1 - csv-parse: 5.3.4 - csv-stringify: 6.2.3 - stream-transform: 3.2.1 + csv-generate: 4.3.0 + csv-parse: 5.5.2 + csv-stringify: 6.4.4 + stream-transform: 3.2.10 dev: false /currently-unhandled@0.4.1: @@ -6757,7 +7098,6 @@ packages: /delayed-stream@1.0.0: resolution: {integrity: sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==} engines: {node: '>=0.4.0'} - dev: true /delegates@1.0.0: resolution: {integrity: sha512-bd2L678uiWATM6m5Z1VzNCErI3jiGzt6HGY8OVICs40JQq/HALfbyNJmp0UDakEY4pMMaN0Ly5om/B1VI/+xfQ==} @@ -7786,6 +8126,7 @@ packages: /exponential-backoff@3.1.0: resolution: {integrity: sha512-oBuz5SYz5zzyuHINoe9ooePwSu0xApKWgeNzok4hZ5YKXFh9zrQBEM15CXqoZkJJPuI2ArvqjPQd8UKJA753XA==} + requiresBuild: true dev: false /express-urlrewrite@1.4.0: @@ -8077,6 +8418,15 @@ packages: mime-types: 2.1.35 dev: true + /form-data@4.0.0: + resolution: {integrity: sha512-ETEklSGi5t0QMZuiXoA/Q6vcnxcLQP5vdugSpuAyi6SVGi2clPPp+xgEhuMaHC+zGgn31Kd235W35f7Hykkaww==} + engines: {node: '>= 6'} + dependencies: + asynckit: 0.4.0 + combined-stream: 1.0.8 + mime-types: 2.1.35 + dev: false + /format@0.2.2: resolution: {integrity: sha512-wzsgA6WOq+09wrU1tsJ09udeR/YZRaeArL9e1wPbFg3GG2yDnC2ldKpxs4xunpFF9DgqCqOIra3bc1HWrJ37Ww==} engines: {node: '>=0.4.x'} @@ -10388,7 +10738,6 @@ packages: /mixme@0.5.4: resolution: {integrity: sha512-3KYa4m4Vlqx98GPdOHghxSdNtTvcP8E0kkaJ5Dlh+h2DRzF7zpuVVcA8B0QpKd11YJeP9QQ7ASkKzOeu195Wzw==} engines: {node: '>= 8.0.0'} - dev: true /mkdirp-classic@0.5.3: resolution: {integrity: sha512-gKLcREMhtuZRwRAfqP3RFW+TK4JqApVBtOIftVgjuABpAtpxhPGaDcfvbhNvD0B8iD1oUr/txX35NjcaY6Ns/A==} @@ -10486,6 +10835,7 @@ packages: /multistream@4.1.0: resolution: {integrity: sha512-J1XDiAmmNpRCBfIWJv+n0ymC4ABcf/Pl+5YvC5B/D2f/2+8PtHvCNxMPKiQcZyi922Hq69J2YOpb1pTywfifyw==} + requiresBuild: true dependencies: once: 1.4.0 readable-stream: 3.6.0 @@ -10637,6 +10987,7 @@ packages: /node-addon-api@1.7.2: resolution: {integrity: sha512-ibPK3iA+vaY1eEjESkQkM0BbCqFOaZMiXRTtdB0u7b4djtY6JnsjvPdUHVMg6xQt3B8fpTTWHI9A+ADjM9frzg==} + requiresBuild: true dev: true optional: true @@ -10644,6 +10995,10 @@ packages: resolution: {integrity: sha512-Ntyt4AIXyaLIuMHF6IOoTakB3K+RWxwtsHNRxllEoA6vPwP9o4866g6YWDLUdnucilZhmkxiHwHr11gAENw+QA==} dev: false + /node-addon-api@5.1.0: + resolution: {integrity: sha512-eh0GgfEkpnoWDq+VY8OyvYhFEzBk6jIYbRKdIlyTiAXIVJ8PyBaKb0rp7oDtoddbdoHWhq8wwr+XZ81F1rpNdA==} + dev: false + /node-fetch@2.6.1: resolution: {integrity: sha512-V4aYg89jEoVRxRb2fJdAg8FHvI7cEyYdVAh94HH0UIK8oJxUfkjlDQN9RbMx+bEjP7+ggMiFRprSti032Oipxw==} engines: {node: 4.x || >=6.0.0} @@ -11448,7 +11803,6 @@ packages: /proxy-from-env@1.1.0: resolution: {integrity: sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==} - dev: true /ps-tree@1.2.0: resolution: {integrity: sha512-0VnamPPYHl4uaU/nSFeZZpR21QAWRz+sRv4iW9+v/GS/J5U5iZB5BNN6J0RMoOvdx2gWM2+ZFMIm58q24e4UYA==} @@ -11957,6 +12311,16 @@ packages: node-gyp-build: 4.5.0 dev: false + /secp256k1@5.0.0: + resolution: {integrity: sha512-TKWX8xvoGHrxVdqbYeZM9w+izTF4b9z3NhSaDkdn81btvuh+ivbIMGT/zQvDtTFWhRlThpoz6LEYTr7n8A5GcA==} + engines: {node: '>=14.0.0'} + requiresBuild: true + dependencies: + elliptic: 6.5.4 + node-addon-api: 5.1.0 + node-gyp-build: 4.5.0 + dev: false + /selective-whitespace@1.0.4: resolution: {integrity: sha512-DyL/pLbb9poQNQOVndVohclAO8lq+6gEBW8q3H9c2fX+ODkugQMvjBilPjw09lrIuVRFRQ/nwhLdzn60sFh9lQ==} dependencies: @@ -12367,10 +12731,9 @@ packages: resolution: {integrity: sha512-9GHUiM5hMiCi6Y03jD2ARC1ettBXkQBoQAe7nJsPknnI0ow10aXjTnew8QtYQmLjzn974BnmWEAJgCY6ZP1DeQ==} dependencies: mixme: 0.5.4 - dev: true - /stream-transform@3.2.1: - resolution: {integrity: sha512-ApK+WTJ5bCOf0A2tlec1qhvr8bGEBM/sgXXB7mysdCYgZJO5DZeaV3h3G+g0HnAQ372P5IhiGqnW29zoLOfTzQ==} + /stream-transform@3.2.10: + resolution: {integrity: sha512-Yu+x7zcWbWdyB0Td8dFzHt2JEyD6694CNq2lqh1rbuEBVxPtjb/GZ7xDnZcdYiU5E/RtufM54ClSEOzZDeWguA==} dev: false /streaming-iterables@6.2.0: @@ -12630,6 +12993,7 @@ packages: /tmp-promise@3.0.3: resolution: {integrity: sha512-RwM7MoPojPxsOBYnyd2hy0bxtIlVrihNs9pj5SUvY8Zz1sQcQG2tG1hSr8PDxfgEB8RNKDhqbIlroIarSNDNsQ==} + requiresBuild: true dependencies: tmp: 0.2.1 dev: false @@ -12643,6 +13007,7 @@ packages: /tmp@0.2.1: resolution: {integrity: sha512-76SUhtfqR2Ijn+xllcI5P1oyannHNHByD80W1q447gU3mp9G9PSpGdWmjUOHRDPiHYacIk66W7ubDTuPF3BEtQ==} engines: {node: '>=8.17.0'} + requiresBuild: true dependencies: rimraf: 3.0.2 dev: false @@ -13621,8 +13986,8 @@ packages: resolution: {integrity: sha512-bXE4cR/kVZhKZX/RjPEflHaKVhUVl85noU3v6b8apfQEc1x4A+zBxjZ4lN8LqGd6WZ3dl98pY4o717VFmoPp+A==} dev: true - github.com/Bundlr-Network/avsc/a730cc8018b79e114b6a3381bbb57760a24c6cef: - resolution: {tarball: https://codeload.github.com/Bundlr-Network/avsc/tar.gz/a730cc8018b79e114b6a3381bbb57760a24c6cef} + github.com/Irys-xyz/avsc/a730cc8018b79e114b6a3381bbb57760a24c6cef: + resolution: {tarball: https://codeload.github.com/Irys-xyz/avsc/tar.gz/a730cc8018b79e114b6a3381bbb57760a24c6cef} name: avsc version: 5.4.7 engines: {node: '>=0.11'}