Skip to content

Commit

Permalink
fix!: Switch to a network and client param solution
Browse files Browse the repository at this point in the history
  • Loading branch information
janniks committed Oct 21, 2024
1 parent b2acdca commit ea9fad5
Show file tree
Hide file tree
Showing 20 changed files with 263 additions and 300 deletions.
11 changes: 5 additions & 6 deletions packages/api/src/api.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import { FetchFn, Hex, createFetchFn } from '@stacks/common';
import {
NetworkParam,
STACKS_MAINNET,
StacksNetwork,
StacksNetworkName,
Expand Down Expand Up @@ -46,11 +47,9 @@ export class StacksNodeApi {
}: {
/** The base API/node URL for the network fetch calls */
baseUrl?: string;
/** Stacks network object (defaults to {@link STACKS_MAINNET}) */
network?: StacksNetworkName | StacksNetwork;
/** An optional custom fetch function to override default behaviors */
fetch?: FetchFn;
} = {}) {
} & NetworkParam = {}) {
this.baseUrl = baseUrl ?? defaultUrlFromNetwork(network);
this.fetch = fetch ?? createFetchFn();
this.network = networkFrom(network);
Expand All @@ -67,10 +66,10 @@ export class StacksNodeApi {
*/
broadcastTransaction = async (
transaction: StacksTransaction,
attachment?: Uint8Array | string
attachment?: Uint8Array | string,
network?: StacksNetworkName | StacksNetwork
): Promise<TxBroadcastResult> => {
// todo: should we use a opts object instead of positional args here?
return broadcastTransaction({ transaction, attachment, client: this });
return broadcastTransaction({ transaction, attachment, network });
};

/**
Expand Down
20 changes: 11 additions & 9 deletions packages/auth/src/profile.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,9 @@
import { ClientOpts, ClientParam, defaultClientOpts } from '@stacks/common';
import { NetworkClientParam, NetworkParam, clientFromNetwork, networkFrom } from '@stacks/network';
import { resolveZoneFileToProfile } from '@stacks/profile';

export interface ProfileLookupOptions {
username: string;
zoneFileLookupURL?: string;
client?: ClientOpts;
}

/**
Expand All @@ -16,19 +15,22 @@ export interface ProfileLookupOptions {
* blockstack.js [[getNameInfo]] function.
* @returns {Promise} that resolves to a profile object
*/
export function lookupProfile(options: ProfileLookupOptions): Promise<Record<string, any>> {
export function lookupProfile(
options: ProfileLookupOptions & NetworkClientParam
): Promise<Record<string, any>> {
if (!options.username) {
return Promise.reject(new Error('No username provided'));
}

const client = defaultClientOpts(options.client);
const network = networkFrom(options.network ?? 'mainnet');
const client = Object.assign({}, clientFromNetwork(network), options.client);

let lookupPromise;
if (options.zoneFileLookupURL) {
const url = `${options.zoneFileLookupURL.replace(/\/$/, '')}/${options.username}`;
lookupPromise = client.fetch(url).then(response => response.json());
} else {
lookupPromise = getNameInfo({ name: options.username, client: client });
lookupPromise = getNameInfo({ name: options.username });
}
return lookupPromise.then((responseJSON: any) => {
if (responseJSON.hasOwnProperty('zonefile') && responseJSON.hasOwnProperty('address')) {
Expand All @@ -49,12 +51,12 @@ export function getNameInfo(
opts: {
/** Fully qualified name */
name: string;
} & ClientParam
} & NetworkParam
) {
const api = defaultClientOpts(opts.client);
const client = clientFromNetwork(networkFrom(opts.network ?? 'mainnet'));

const nameLookupURL = `${api.baseUrl}/v1/names/${opts.name}`;
return api
const nameLookupURL = `${client.baseUrl}/v1/names/${opts.name}`;
return client
.fetch(nameLookupURL)
.then((resp: any) => {
if (resp.status === 404) {
Expand Down
11 changes: 4 additions & 7 deletions packages/bns/src/index.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { ClientParam, IntegerType, PublicKey, intToBigInt, utf8ToBytes } from '@stacks/common';
import { StacksNetwork } from '@stacks/network';
import { IntegerType, PublicKey, intToBigInt, utf8ToBytes } from '@stacks/common';
import { NetworkClientParam, StacksNetwork } from '@stacks/network';
import {
ClarityType,
ClarityValue,
Expand Down Expand Up @@ -83,15 +83,12 @@ export interface BnsReadOnlyOptions {
}

async function callReadOnlyBnsFunction(
options: BnsReadOnlyOptions & ClientParam
options: BnsReadOnlyOptions & NetworkClientParam
): Promise<ClarityValue> {
return fetchCallReadOnlyFunction({
...options,
contractAddress: options.network.bootAddress,
contractName: BNS_CONTRACT_NAME,
functionName: options.functionName,
senderAddress: options.senderAddress,
functionArgs: options.functionArgs,
client: options.client,
});
}

Expand Down
14 changes: 7 additions & 7 deletions packages/bns/tests/bns.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,7 @@ test('canRegisterName true', async () => {
bufferCV(utf8ToBytes(fullyQualifiedName.split('.')[0])),
],
senderAddress: notRandomAddress,
client: undefined,
network: STACKS_TESTNET,
};

expect(result).toEqual(true);
Expand Down Expand Up @@ -96,7 +96,7 @@ test('canRegisterName false', async () => {
bufferCV(utf8ToBytes(fullyQualifiedName.split('.')[0])),
],
senderAddress: notRandomAddress,
client: undefined,
network: STACKS_TESTNET,
};

expect(result).toEqual(false);
Expand Down Expand Up @@ -135,7 +135,7 @@ test('canRegisterName error', async () => {
bufferCV(utf8ToBytes(fullyQualifiedName.split('.')[0])),
],
senderAddress: notRandomAddress,
client: undefined,
network: STACKS_TESTNET,
};

expect(result).toEqual(false);
Expand Down Expand Up @@ -171,7 +171,7 @@ test('getNamespacePrice', async () => {
functionName: bnsFunctionName,
senderAddress: address,
functionArgs: [bufferCVFromString(namespace)],
client: undefined,
network: STACKS_TESTNET,
};

expect(result.toString()).toEqual('10');
Expand Down Expand Up @@ -206,7 +206,7 @@ test('getNamespacePrice error', async () => {
functionName: bnsFunctionName,
senderAddress: address,
functionArgs: [bufferCVFromString(namespace)],
client: undefined,
network: STACKS_TESTNET,
};

await expect(getNamespacePrice({ namespace, network })).rejects.toEqual(new Error('u1001'));
Expand Down Expand Up @@ -244,7 +244,7 @@ test('getNamePrice', async () => {
functionName: bnsFunctionName,
senderAddress: address,
functionArgs: [bufferCVFromString(namespace), bufferCVFromString(name)],
client: undefined,
network: STACKS_TESTNET,
};

expect(result.toString()).toEqual('10');
Expand Down Expand Up @@ -281,7 +281,7 @@ test('getNamePrice error', async () => {
functionName: bnsFunctionName,
senderAddress: address,
functionArgs: [bufferCVFromString(namespace), bufferCVFromString(name)],
client: undefined,
network: STACKS_TESTNET,
};

await expect(getNamePrice({ fullyQualifiedName, network })).rejects.toEqual(new Error('u2001'));
Expand Down
40 changes: 13 additions & 27 deletions packages/cli/src/cli.ts
Original file line number Diff line number Diff line change
Expand Up @@ -90,12 +90,7 @@ import { CLI_NETWORK_OPTS, CLINetworkAdapter, getNetwork, NameInfoType } from '.

import { gaiaAuth, gaiaConnect, gaiaUploadProfileAll, getGaiaAddressFromProfile } from './data';

import {
defaultClientOptsFromNetwork,
defaultUrlFromNetwork,
STACKS_MAINNET,
STACKS_TESTNET,
} from '@stacks/network';
import { defaultUrlFromNetwork, STACKS_MAINNET, STACKS_TESTNET } from '@stacks/network';
import {
generateNewAccount,
generateWallet,
Expand Down Expand Up @@ -698,7 +693,6 @@ async function sendTokens(_network: CLINetworkAdapter, args: string[]): Promise<
}

const network = _network.isMainnet() ? STACKS_MAINNET : STACKS_TESTNET;
const client = defaultClientOptsFromNetwork(network);

const options: SignedTokenTransferOptions = {
recipient: recipientAddress,
Expand All @@ -713,7 +707,7 @@ async function sendTokens(_network: CLINetworkAdapter, args: string[]): Promise<
const tx: StacksTransaction = await makeSTXTokenTransfer(options);

if (estimateOnly) {
return fetchFeeEstimateTransfer({ transaction: tx, client }).then(cost => {
return fetchFeeEstimateTransfer({ transaction: tx, network }).then(cost => {
return cost.toString(10);
});
}
Expand All @@ -722,7 +716,7 @@ async function sendTokens(_network: CLINetworkAdapter, args: string[]): Promise<
return Promise.resolve(tx.serialize());
}

return broadcastTransaction({ transaction: tx, client })
return broadcastTransaction({ transaction: tx, network })
.then((response: TxBroadcastResult) => {
if (response.hasOwnProperty('error')) {
return response;
Expand Down Expand Up @@ -815,13 +809,12 @@ async function contractFunctionCall(_network: CLINetworkAdapter, args: string[])

// temporary hack to use network config from stacks-transactions lib
const network = _network.isMainnet() ? STACKS_MAINNET : STACKS_TESTNET;
const client = defaultClientOptsFromNetwork(network);

let abi: ClarityAbi;
let abiArgs: ClarityFunctionArg[];
let functionArgs: ClarityValue[] = [];

return fetchAbi({ contractAddress, contractName, client })
return fetchAbi({ contractAddress, contractName, network })
.then(responseAbi => {
abi = responseAbi;
const filtered = abi.functions.filter(fn => fn.name === functionName);
Expand All @@ -846,7 +839,6 @@ async function contractFunctionCall(_network: CLINetworkAdapter, args: string[])
nonce,
network,
postConditionMode: PostConditionMode.Allow,
client,
};

return makeContractCall(options);
Expand All @@ -867,7 +859,7 @@ async function contractFunctionCall(_network: CLINetworkAdapter, args: string[])
return Promise.resolve(tx.serialize());
}

return broadcastTransaction({ transaction: tx, client })
return broadcastTransaction({ transaction: tx, network })
.then(response => {
if (response.hasOwnProperty('error')) {
return response;
Expand Down Expand Up @@ -901,13 +893,12 @@ async function readOnlyContractFunctionCall(
const senderAddress = args[3];

const network = _network.isMainnet() ? STACKS_MAINNET : STACKS_TESTNET;
const client = defaultClientOptsFromNetwork(network);

let abi: ClarityAbi;
let abiArgs: ClarityFunctionArg[];
let functionArgs: ClarityValue[] = [];

return fetchAbi({ contractAddress, contractName, client })
return fetchAbi({ contractAddress, contractName, network })
.then(responseAbi => {
abi = responseAbi;
const filtered = abi.functions.filter(fn => fn.name === functionName);
Expand Down Expand Up @@ -1634,8 +1625,7 @@ async function stackingStatus(_network: CLINetworkAdapter, args: string[]): Prom
const address = args[0];

const network = _network.isMainnet() ? STACKS_MAINNET : STACKS_TESTNET;
const client = defaultClientOptsFromNetwork(network);
const stacker = new StackingClient({ address, network, client });
const stacker = new StackingClient({ address, network });

return stacker
.getStatus()
Expand Down Expand Up @@ -1667,11 +1657,10 @@ async function canStack(_network: CLINetworkAdapter, args: string[]): Promise<st
const stxAddress = args[3];

const network = _network.isMainnet() ? STACKS_MAINNET : STACKS_TESTNET;
const client = defaultClientOptsFromNetwork(network);
const stacker = new StackingClient({ address: stxAddress, network, client });
const stacker = new StackingClient({ address: stxAddress, network });

const apiConfig = new Configuration({
basePath: client.baseUrl,
basePath: network.client.baseUrl,
});
const accounts = new AccountsApi(apiConfig);

Expand Down Expand Up @@ -1729,10 +1718,9 @@ async function stack(_network: CLINetworkAdapter, args: string[]): Promise<strin
// }

const network = _network.isMainnet() ? STACKS_MAINNET : STACKS_TESTNET;
const client = defaultClientOptsFromNetwork(network);

const apiConfig = new Configuration({
basePath: client.baseUrl,
basePath: network.client.baseUrl,
});
const accounts = new AccountsApi(apiConfig);

Expand All @@ -1742,7 +1730,7 @@ async function stack(_network: CLINetworkAdapter, args: string[]): Promise<strin
principal: stxAddress,
});

const stacker = new StackingClient({ address: stxAddress, network, client });
const stacker = new StackingClient({ address: stxAddress, network });

const poxInfoPromise = stacker.getPoxInfo();

Expand Down Expand Up @@ -1803,7 +1791,6 @@ async function register(_network: CLINetworkAdapter, args: string[]): Promise<st
const publicKey = privateKeyToPublic(privateKey);

const network = _network.isMainnet() ? STACKS_MAINNET : STACKS_TESTNET;
const client = defaultClientOptsFromNetwork(network);

const unsignedTransaction = await buildRegisterNameTx({
fullyQualifiedName,
Expand All @@ -1816,7 +1803,7 @@ async function register(_network: CLINetworkAdapter, args: string[]): Promise<st
const signer = new TransactionSigner(unsignedTransaction);
signer.signOrigin(privateKey);

return broadcastTransaction({ transaction: signer.transaction, client })
return broadcastTransaction({ transaction: signer.transaction, network })
.then((response: TxBroadcastResult) => {
if (response.hasOwnProperty('error')) {
return response;
Expand All @@ -1839,7 +1826,6 @@ async function preorder(_network: CLINetworkAdapter, args: string[]): Promise<st
const publicKey = privateKeyToPublic(privateKey);

const network = _network.isMainnet() ? STACKS_MAINNET : STACKS_TESTNET;
const client = defaultClientOptsFromNetwork(network);

const unsignedTransaction = await buildPreorderNameTx({
fullyQualifiedName,
Expand All @@ -1852,7 +1838,7 @@ async function preorder(_network: CLINetworkAdapter, args: string[]): Promise<st
const signer = new TransactionSigner(unsignedTransaction);
signer.signOrigin(privateKey);

return broadcastTransaction({ transaction: signer.transaction, client })
return broadcastTransaction({ transaction: signer.transaction, network })
.then((response: TxBroadcastResult) => {
if (response.hasOwnProperty('error')) {
return response;
Expand Down
30 changes: 13 additions & 17 deletions packages/common/src/fetch.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,4 @@
// Define a default request options and allow modification using getters, setters

import { HIRO_MAINNET_URL } from './constants';

// Define default request options and allow modification using getters, setters
// Reference: https://developer.mozilla.org/en-US/docs/Web/API/Request/Request
const defaultFetchOpts: RequestInit = {
// By default referrer value will be client:origin: above reference link
Expand Down Expand Up @@ -55,16 +52,16 @@ export type FetchFn = (url: string, init?: RequestInit) => Promise<Response>;
* @ignore Internally used for letting networking functions specify "API" options.
* Should be compatible with the `client`s created by the API and RPC packages.
*/
export type ClientOpts = {
export interface ClientOpts {
baseUrl?: string;
fetch?: FetchFn;
};
}

/** @ignore Internally used for letting networking functions specify "API" options */
export type ClientParam = {
/** Optional API object (for `.url` and `.fetch`) used for API/Node, defaults to use mainnet */
export interface ClientParam {
/** Optional API object (for `.baseUrl` and `.fetch`) used for API/Node, defaults to use mainnet */
client?: ClientOpts;
};
}

export interface RequestContext {
fetch: FetchFn;
Expand Down Expand Up @@ -195,11 +192,10 @@ export function createFetchFn(...args: any[]): FetchFn {
return fetchFn;
}

/** @ignore Creates a client-like object, which can be used without circular dependencies */
export function defaultClientOpts(opts?: { baseUrl?: string; fetch?: FetchFn }) {
return {
// todo: do we want network here as well?
baseUrl: opts?.baseUrl ?? HIRO_MAINNET_URL,
fetch: opts?.fetch ?? createFetchFn(),
};
}
// /** @ignore Creates a client-like object, which can be used without circular dependencies */
// export function defaultClientOpts(opts?: { baseUrl?: string; fetch?: FetchFn }) {
// return {
// baseUrl: opts?.baseUrl ?? HIRO_MAINNET_URL,
// fetch: opts?.fetch ?? createFetchFn(),
// };
// }
Loading

0 comments on commit ea9fad5

Please sign in to comment.