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

Add asset transfer function #1332

Merged
merged 4 commits into from
Dec 22, 2023
Merged
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
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "opensea-js",
"version": "7.0.5",
"version": "7.0.6",
"description": "TypeScript SDK for the OpenSea marketplace helps developers build new experiences using NFTs and our marketplace data",
"license": "MIT",
"author": "OpenSea Developers",
Expand Down
113 changes: 105 additions & 8 deletions src/sdk.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ import {
ethers,
parseEther,
JsonRpcProvider,
ContractTransactionResponse,
} from "ethers";
import { OpenSeaAPI } from "./api/api";
import { CollectionOffer, Listing, NFT, Order } from "./api/types";
Expand Down Expand Up @@ -189,7 +190,6 @@ export class OpenSeaSDK {
this._signerOrProvider,
);

wethContract.connect(this.provider);
try {
const transaction = await wethContract.deposit({ value });
await this._confirmTransaction(
Expand Down Expand Up @@ -229,7 +229,6 @@ export class OpenSeaSDK {
this._signerOrProvider,
);

wethContract.connect(this.provider);
try {
const transaction = await wethContract.withdraw(amount);
await this._confirmTransaction(
Expand Down Expand Up @@ -897,17 +896,18 @@ export class OpenSeaSDK {
}): Promise<bigint> {
switch (asset.tokenStandard) {
case TokenStandard.ERC20: {
const contract = new ethers.Contract(
const contract = ERC20__factory.connect(
asset.tokenAddress,
ERC20__factory.createInterface(),
this.provider,
);
return await contract.balanceOf.staticCall(accountAddress);
}
case TokenStandard.ERC1155: {
const contract = new ethers.Contract(
if (asset.tokenId === undefined || asset.tokenId === null) {
throw new Error("Missing ERC1155 tokenId for getBalance");
}
const contract = ERC1155__factory.connect(
asset.tokenAddress,
ERC1155__factory.createInterface(),
this.provider,
);
return await contract.balanceOf.staticCall(
Expand All @@ -916,9 +916,11 @@ export class OpenSeaSDK {
);
}
case TokenStandard.ERC721: {
const contract = new ethers.Contract(
if (asset.tokenId === undefined || asset.tokenId === null) {
throw new Error("Missing ERC721 tokenId for getBalance");
}
const contract = ERC721__factory.connect(
asset.tokenAddress,
ERC721__factory.createInterface(),
this.provider,
);
try {
Expand All @@ -937,6 +939,101 @@ export class OpenSeaSDK {
}
}

/**
* Transfer an asset. This asset can be an ERC20, ERC1155, or ERC721.
* @param options
* @param options.asset The Asset to transfer. tokenStandard must be set.
* @param options.amount Amount of asset to transfer. Not used for ERC721.
* @param options.fromAddress The address to transfer from
* @param options.toAddress The address to transfer to
* @param options.overrides Transaction overrides, ignored if not set.
*/
public async transfer({
asset,
amount,
fromAddress,
toAddress,
overrides,
}: {
asset: AssetWithTokenStandard;
amount?: BigNumberish;
fromAddress: string;
toAddress: string;
overrides?: Overrides;
}): Promise<void> {
await this._requireAccountIsAvailable(fromAddress);
overrides = { ...overrides, from: fromAddress };
let transaction: Promise<ContractTransactionResponse>;

switch (asset.tokenStandard) {
case TokenStandard.ERC20: {
if (!amount) {
throw new Error("Missing ERC20 amount for transfer");
}
const contract = ERC20__factory.connect(
asset.tokenAddress,
this._signerOrProvider,
);
transaction = contract.transfer(toAddress, amount, overrides);
break;
}
case TokenStandard.ERC1155: {
if (asset.tokenId === undefined || asset.tokenId === null) {
throw new Error("Missing ERC1155 tokenId for transfer");
}
if (!amount) {
ryanio marked this conversation as resolved.
Show resolved Hide resolved
throw new Error("Missing ERC1155 amount for transfer");
}
const contract = ERC1155__factory.connect(
asset.tokenAddress,
this._signerOrProvider,
);
transaction = contract.safeTransferFrom(
fromAddress,
toAddress,
asset.tokenId,
amount,
"",
overrides,
);
break;
}
case TokenStandard.ERC721: {
if (asset.tokenId === undefined || asset.tokenId === null) {
throw new Error("Missing ERC721 tokenId for transfer");
}
const contract = ERC721__factory.connect(
asset.tokenAddress,
this._signerOrProvider,
);
transaction = contract.transferFrom(
fromAddress,
toAddress,
asset.tokenId,
overrides,
);
break;
}
default:
throw new Error("Unsupported token standard for transfer");
}

try {
const transactionResponse = await transaction;
await this._confirmTransaction(
transactionResponse.hash,
EventType.Transfer,
"Transferring asset",
);
} catch (error) {
console.error(error);
this._dispatch(EventType.TransactionDenied, {
error,
accountAddress: fromAddress,
});
}
}

/**
* Instead of signing an off-chain order, this methods allows you to approve an order
* with on on-chain transaction.
Expand Down
4 changes: 4 additions & 0 deletions src/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,10 @@ export enum EventType {
* Emitted when the {@link OpenSeaSDK.approveOrder} method is called.
*/
ApproveOrder = "ApproveOrder",
/**
* Emitted when the {@link OpenSeaSDK.transfer} method is called.
*/
Transfer = "Transfer",
}

/**
Expand Down
Loading