Skip to content

Commit

Permalink
Support for fund and quote_fund for wallet funding (#322)
Browse files Browse the repository at this point in the history
  • Loading branch information
rohan-agarwal-coinbase authored Nov 27, 2024
1 parent a6dc206 commit 16508a7
Show file tree
Hide file tree
Showing 24 changed files with 1,731 additions and 53 deletions.
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,10 @@

## Unreleased

## Added

- Add `FundOperation` and `FundQuote` classes to support wallet funding

### Fixed
- Fixed a bug where the asset ID was not being set correctly for Gwei and Wei

Expand Down
1 change: 1 addition & 0 deletions src/client/api.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6529,6 +6529,7 @@ export interface FundApiInterface {
* @memberof FundApiInterface
*/
listFundOperations(walletId: string, addressId: string, limit?: number, page?: string, options?: RawAxiosRequestConfig): AxiosPromise<FundOperationList>;

}

/**
Expand Down
40 changes: 40 additions & 0 deletions src/coinbase/address/wallet_address.ts
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,8 @@ import { Wallet as WalletClass } from "../wallet";
import { StakingOperation } from "../staking_operation";
import { PayloadSignature } from "../payload_signature";
import { SmartContract } from "../smart_contract";
import { FundOperation } from "../fund_operation";
import { FundQuote } from "../fund_quote";

/**
* A representation of a blockchain address, which is a wallet-controlled account on a network.
Expand Down Expand Up @@ -747,6 +749,44 @@ export class WalletAddress extends Address {
};
}

/**
* Fund the address from your account on the Coinbase Platform.
*
* @param amount - The amount of the Asset to fund the wallet with
* @param assetId - The ID of the Asset to fund with. For Ether, eth, gwei, and wei are supported.
* @returns The created fund operation object
*/
public async fund(amount: Amount, assetId: string): Promise<FundOperation> {
const normalizedAmount = new Decimal(amount.toString());

return FundOperation.create(
this.getWalletId(),
this.getId(),
normalizedAmount,
assetId,
this.getNetworkId(),
);
}

/**
* Get a quote for funding the address from your Coinbase platform account.
*
* @param amount - The amount to fund
* @param assetId - The ID of the Asset to fund with. For Ether, eth, gwei, and wei are supported.
* @returns The fund quote object
*/
public async quoteFund(amount: Amount, assetId: string): Promise<FundQuote> {
const normalizedAmount = new Decimal(amount.toString());

return FundQuote.create(
this.getWalletId(),
this.getId(),
normalizedAmount,
assetId,
this.getNetworkId(),
);
}

/**
* Returns the address and network ID of the given destination.
*
Expand Down
2 changes: 2 additions & 0 deletions src/coinbase/coinbase.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ import {
SmartContractsApiFactory,
TransactionHistoryApiFactory,
MPCWalletStakeApiFactory,
FundApiFactory,
} from "../client";
import { BASE_PATH } from "./../client/base";
import { Configuration } from "./../client/configuration";
Expand Down Expand Up @@ -154,6 +155,7 @@ export class Coinbase {
Coinbase.apiClients.balanceHistory = BalanceHistoryApiFactory(config, basePath, axiosInstance);
Coinbase.apiClients.contractEvent = ContractEventsApiFactory(config, basePath, axiosInstance);
Coinbase.apiClients.smartContract = SmartContractsApiFactory(config, basePath, axiosInstance);
Coinbase.apiClients.fund = FundApiFactory(config, basePath, axiosInstance);
Coinbase.apiClients.transactionHistory = TransactionHistoryApiFactory(
config,
basePath,
Expand Down
99 changes: 99 additions & 0 deletions src/coinbase/crypto_amount.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
import Decimal from "decimal.js";
import { CryptoAmount as CryptoAmountModel } from "../client/api";
import { Asset } from "./asset";

/**
* A representation of a CryptoAmount that includes the amount and asset.
*/
export class CryptoAmount {
private amount: Decimal;
private assetObj: Asset;
private assetId: string;

/**
* Creates a new CryptoAmount instance.
*
* @param amount - The amount of the Asset
* @param asset - The Asset
* @param assetId - Optional Asset ID override
*/
constructor(amount: Decimal, asset: Asset, assetId?: string) {
this.amount = amount;
this.assetObj = asset;
this.assetId = assetId || asset.getAssetId();
}

/**
* Converts a CryptoAmount model to a CryptoAmount.
*
* @param amountModel - The crypto amount from the API
* @returns The converted CryptoAmount object
*/
public static fromModel(amountModel: CryptoAmountModel): CryptoAmount {
const asset = Asset.fromModel(amountModel.asset);
return new CryptoAmount(asset.fromAtomicAmount(new Decimal(amountModel.amount)), asset);
}

/**
* Converts a CryptoAmount model and asset ID to a CryptoAmount.
* This can be used to specify a non-primary denomination that we want the amount
* to be converted to.
*
* @param amountModel - The crypto amount from the API
* @param assetId - The Asset ID of the denomination we want returned
* @returns The converted CryptoAmount object
*/
public static fromModelAndAssetId(amountModel: CryptoAmountModel, assetId: string): CryptoAmount {
const asset = Asset.fromModel(amountModel.asset, assetId);
return new CryptoAmount(
asset.fromAtomicAmount(new Decimal(amountModel.amount)),
asset,
assetId,
);
}

/**
* Gets the amount of the Asset.
*
* @returns The amount of the Asset
*/
public getAmount(): Decimal {
return this.amount;
}

/**
* Gets the Asset.
*
* @returns The Asset
*/
public getAsset(): Asset {
return this.assetObj;
}

/**
* Gets the Asset ID.
*
* @returns The Asset ID
*/
public getAssetId(): string {
return this.assetId;
}

/**
* Converts the amount to atomic units.
*
* @returns The amount in atomic units
*/
public toAtomicAmount(): bigint {
return this.assetObj.toAtomicAmount(this.amount);
}

/**
* Returns a string representation of the CryptoAmount.
*
* @returns A string representation of the CryptoAmount
*/
public toString(): string {
return `CryptoAmount{amount: '${this.amount}', assetId: '${this.assetId}'}`;
}
}
57 changes: 57 additions & 0 deletions src/coinbase/fiat_amount.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
import { FiatAmount as FiatAmountModel } from "../client/api";

/**
* A representation of a FiatAmount that includes the amount and currency.
*/
export class FiatAmount {
private amount: string;
private currency: string;

/**
* Initialize a new FiatAmount. Do not use this directly, use the fromModel method instead.
*
* @param amount - The amount in the fiat currency
* @param currency - The currency code (e.g. 'USD')
*/
constructor(amount: string, currency: string) {
this.amount = amount;
this.currency = currency;
}

/**
* Convert a FiatAmount model to a FiatAmount.
*
* @param fiatAmountModel - The fiat amount from the API.
* @returns The converted FiatAmount object.
*/
public static fromModel(fiatAmountModel: FiatAmountModel): FiatAmount {
return new FiatAmount(fiatAmountModel.amount, fiatAmountModel.currency);
}

/**
* Get the amount in the fiat currency.
*
* @returns The amount in the fiat currency.
*/
public getAmount(): string {
return this.amount;
}

/**
* Get the currency code.
*
* @returns The currency code.
*/
public getCurrency(): string {
return this.currency;
}

/**
* Get a string representation of the FiatAmount.
*
* @returns A string representation of the FiatAmount.
*/
public toString(): string {
return `FiatAmount(amount: '${this.amount}', currency: '${this.currency}')`;
}
}
Loading

0 comments on commit 16508a7

Please sign in to comment.