Skip to content

Commit

Permalink
feat(PE-6910): support primary name APIs
Browse files Browse the repository at this point in the history
  • Loading branch information
dtfiedler authored and dtfiedler committed Nov 18, 2024
1 parent da9740d commit 82a5b44
Show file tree
Hide file tree
Showing 6 changed files with 236 additions and 449 deletions.
192 changes: 112 additions & 80 deletions src/common/io.ts
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,8 @@ import {
AoGatewayWithAddress,
AoJoinNetworkParams,
AoMessageResult,
AoPrimaryName,
AoPrimaryNameRequest,
AoTokenSupplyData,
AoUpdateGatewaySettingsParams,
AoWeightedObserver,
Expand Down Expand Up @@ -58,7 +60,11 @@ import {
} from '../types/io.js';
import { AoSigner, mIOToken } from '../types/token.js';
import { createAoSigner } from '../utils/ao.js';
import { getCurrentBlockUnixTimestampMs, pruneTags } from '../utils/arweave.js';
import {
getCurrentBlockUnixTimestampMs,
paginationParamsToTags,
pruneTags,
} from '../utils/arweave.js';
import { defaultArweave } from './arweave.js';
import { AOProcess } from './contracts/ao-process.js';
import { InvalidContractConfigurationError } from './error.js';
Expand Down Expand Up @@ -200,16 +206,11 @@ export class IOReadable implements AoIORead {
async getArNSRecords(
params?: PaginationParams<AoArNSNameDataWithName>,
): Promise<PaginationResult<AoArNSNameDataWithName>> {
const allTags = [
{ name: 'Action', value: 'Paginated-Records' },
{ name: 'Cursor', value: params?.cursor?.toString() },
{ name: 'Limit', value: params?.limit?.toString() },
{ name: 'Sort-By', value: params?.sortBy },
{ name: 'Sort-Order', value: params?.sortOrder },
];

return this.process.read<PaginationResult<AoArNSNameDataWithName>>({
tags: pruneTags(allTags),
tags: [
{ name: 'Action', value: 'Paginated-Records' },
...paginationParamsToTags<AoArNSNameDataWithName>(params),
],
});
}

Expand Down Expand Up @@ -246,16 +247,11 @@ export class IOReadable implements AoIORead {
async getBalances(
params?: PaginationParams<AoBalanceWithAddress>,
): Promise<PaginationResult<AoBalanceWithAddress>> {
const allTags = [
{ name: 'Action', value: 'Paginated-Balances' },
{ name: 'Cursor', value: params?.cursor?.toString() },
{ name: 'Limit', value: params?.limit?.toString() },
{ name: 'Sort-By', value: params?.sortBy },
{ name: 'Sort-Order', value: params?.sortOrder },
];

return this.process.read<PaginationResult<AoBalanceWithAddress>>({
tags: pruneTags(allTags),
tags: [
{ name: 'Action', value: 'Paginated-Balances' },
...paginationParamsToTags<AoBalanceWithAddress>(params),
],
});
}

Expand All @@ -278,16 +274,11 @@ export class IOReadable implements AoIORead {
async getVaults(
params?: PaginationParams<AoWalletVault>,
): Promise<PaginationResult<AoWalletVault>> {
const allTags = [
{ name: 'Action', value: 'Paginated-Vaults' },
{ name: 'Cursor', value: params?.cursor?.toString() },
{ name: 'Limit', value: params?.limit?.toString() },
{ name: 'Sort-By', value: params?.sortBy },
{ name: 'Sort-Order', value: params?.sortOrder },
];

return this.process.read<PaginationResult<AoWalletVault>>({
tags: pruneTags(allTags),
tags: [
{ name: 'Action', value: 'Paginated-Vaults' },
...paginationParamsToTags<AoWalletVault>(params),
],
});
}

Expand All @@ -308,17 +299,12 @@ export class IOReadable implements AoIORead {
address,
...pageParams
}): Promise<PaginationResult<AoGatewayDelegateWithAddress>> {
const allTags = [
{ name: 'Action', value: 'Paginated-Delegates' },
{ name: 'Address', value: address },
{ name: 'Cursor', value: pageParams?.cursor?.toString() },
{ name: 'Limit', value: pageParams?.limit?.toString() },
{ name: 'Sort-By', value: pageParams?.sortBy },
{ name: 'Sort-Order', value: pageParams?.sortOrder },
];

return this.process.read<PaginationResult<AoGatewayDelegateWithAddress>>({
tags: pruneTags(allTags),
tags: [
{ name: 'Action', value: 'Paginated-Delegates' },
{ name: 'Address', value: address },
...paginationParamsToTags<AoGatewayDelegateWithAddress>(pageParams),
],
});
}

Expand All @@ -330,33 +316,23 @@ export class IOReadable implements AoIORead {
} & PaginationParams<WalletAddress>): Promise<
PaginationResult<WalletAddress>
> {
const allTags = [
{ name: 'Action', value: 'Paginated-Allowed-Delegates' },
{ name: 'Address', value: address },
{ name: 'Cursor', value: pageParams?.cursor?.toString() },
{ name: 'Limit', value: pageParams?.limit?.toString() },
{ name: 'Sort-Order', value: pageParams?.sortOrder },
// note: sortBy is omitted because it's not supported for this action as table is an of addresses
];

return this.process.read<PaginationResult<WalletAddress>>({
tags: pruneTags(allTags),
tags: [
{ name: 'Action', value: 'Paginated-Allowed-Delegates' },
{ name: 'Address', value: address },
...paginationParamsToTags<WalletAddress>(pageParams),
],
});
}

async getGateways(
pageParams?: PaginationParams<AoGatewayWithAddress>,
): Promise<PaginationResult<AoGatewayWithAddress>> {
const allTags = [
{ name: 'Action', value: 'Paginated-Gateways' },
{ name: 'Cursor', value: pageParams?.cursor?.toString() },
{ name: 'Limit', value: pageParams?.limit?.toString() },
{ name: 'Sort-By', value: pageParams?.sortBy },
{ name: 'Sort-Order', value: pageParams?.sortOrder },
];

return this.process.read<PaginationResult<AoGatewayWithAddress>>({
tags: pruneTags(allTags),
tags: [
{ name: 'Action', value: 'Paginated-Gateways' },
...paginationParamsToTags<AoGatewayWithAddress>(pageParams),
],
});
}

Expand Down Expand Up @@ -430,16 +406,7 @@ export class IOReadable implements AoIORead {
name: 'Timestamp',
value:
(epoch as { timestamp?: number })?.timestamp?.toString() ??
(
await this.arweave.blocks
.getCurrent()
.then((block) => {
return { timestamp: block.timestamp * 1000 };
})
.catch(() => {
return { timestamp: `${Date.now()}` }; // fallback to current time
})
).timestamp.toString(),
(await getCurrentBlockUnixTimestampMs(this.arweave)).toString(),
},
{
name: 'Epoch-Index',
Expand Down Expand Up @@ -559,16 +526,11 @@ export class IOReadable implements AoIORead {
async getArNSAuctions(
params?: PaginationParams<AoAuction>,
): Promise<PaginationResult<AoAuction>> {
const allTags = [
{ name: 'Action', value: 'Auctions' },
{ name: 'Cursor', value: params?.cursor?.toString() },
{ name: 'Limit', value: params?.limit?.toString() },
{ name: 'Sort-By', value: params?.sortBy },
{ name: 'Sort-Order', value: params?.sortOrder },
];

return this.process.read<PaginationResult<AoAuction>>({
tags: pruneTags(allTags),
tags: [
{ name: 'Action', value: 'Auctions' },
...paginationParamsToTags<AoAuction>(params),
],
});
}

Expand Down Expand Up @@ -644,16 +606,76 @@ export class IOReadable implements AoIORead {
): Promise<PaginationResult<AoDelegation>> {
const allTags = [
{ name: 'Action', value: 'Paginated-Delegations' },
{ name: 'Cursor', value: params.cursor?.toString() },
{ name: 'Limit', value: params.limit?.toString() },
{ name: 'Sort-By', value: params.sortBy },
{ name: 'Sort-Order', value: params.sortOrder },
{ name: 'Address', value: params.address },
...paginationParamsToTags(params),
];

return this.process.read<PaginationResult<AoDelegation>>({
tags: pruneTags(allTags),
});
}

async getPrimaryNameRequest(
params:
| {
initiator: WalletAddress;
}
| {
name: string;
},
): Promise<AoMessageResult> {
const allTags = [
{ name: 'Action', value: 'Primary-Name-Request' },
{ name: 'Name', value: (params as { name: string }).name },
{
name: 'Initiator',
value: (params as { initiator: WalletAddress }).initiator,
},
];

return this.process.read<AoMessageResult>({
tags: allTags,
});
}

async getPrimaryNameRequests(
params: PaginationParams<AoPrimaryNameRequest>,
): Promise<PaginationResult<AoPrimaryNameRequest>> {
return this.process.read<PaginationResult<AoPrimaryNameRequest>>({
tags: [
{ name: 'Action', value: 'Primary-Name-Requests' },
...paginationParamsToTags(params),
],
});
}

async getPrimaryName(
params: { address: WalletAddress } | { name: string },
): Promise<AoPrimaryName> {
const allTags = [
{ name: 'Action', value: 'Primary-Name' },
{
name: 'Address',
value: (params as { address: WalletAddress })?.address,
},
{ name: 'Name', value: (params as { name: string })?.name },
];

return this.process.read<AoPrimaryName>({
tags: pruneTags(allTags),
});
}

async getPrimaryNames(
params: PaginationParams<AoPrimaryName>,
): Promise<PaginationResult<AoPrimaryName>> {
return this.process.read<PaginationResult<AoPrimaryName>>({
tags: [
{ name: 'Action', value: 'Primary-Names' },
...paginationParamsToTags(params),
],
});
}
}

export class IOWriteable extends IOReadable implements AoIOWrite {
Expand Down Expand Up @@ -1142,4 +1164,14 @@ export class IOWriteable extends IOReadable implements AoIOWrite {
tags: pruneTags(allTags),
});
}

async requestPrimaryName(params: { name: string }): Promise<AoMessageResult> {
return this.process.send({
signer: this.signer,
tags: [
{ name: 'Action', value: 'Primary-Name-Request' },
{ name: 'Name', value: params.name },
],
});
}
}
12 changes: 12 additions & 0 deletions src/types/common.ts
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,18 @@ export type WriteParameters<Input> = WithSigner<

export type AoMessageResult = { id: string };

export type AoPrimaryNameRequest = {
name: string;
startTimestamp: Timestamp;
endTimestamp: Timestamp;
};

export type AoPrimaryName = {
owner: WalletAddress;
name: string;
startTimestamp: Timestamp;
};

// Utility type to require at least one of the fields
export type AtLeastOne<
T,
Expand Down
17 changes: 17 additions & 0 deletions src/types/io.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,8 @@ import { AOProcess } from '../common/index.js';
import { validateArweaveId } from '../utils/arweave.js';
import {
AoMessageResult,
AoPrimaryName,
AoPrimaryNameRequest,
AtLeastOne,
BlockHeight,
ProcessId,
Expand Down Expand Up @@ -433,6 +435,20 @@ export interface AoIORead {
address: WalletAddress;
vaultId: string;
}): Promise<AoVaultData>;
getPrimaryNameRequest(
params: { initiator: WalletAddress } | { name: string },
): Promise<AoMessageResult>;
getPrimaryNameRequests(
params: PaginationParams<AoPrimaryNameRequest> & {
initiator?: WalletAddress;
},
): Promise<PaginationResult<AoPrimaryNameRequest>>;
getPrimaryName(
params: { address: WalletAddress } | { name: string },
): Promise<AoPrimaryName>;
getPrimaryNames(
params?: PaginationParams<AoPrimaryName>,
): Promise<PaginationResult<AoPrimaryName>>;
}

export interface AoIOWrite extends AoIORead {
Expand Down Expand Up @@ -545,6 +561,7 @@ export interface AoIOWrite extends AoIORead {
},
options?: WriteOptions,
): Promise<AoMessageResult>;
requestPrimaryName(params: { name: string }): Promise<AoMessageResult>;
}

// Typeguard functions
Expand Down
14 changes: 14 additions & 0 deletions src/utils/arweave.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import Arweave from 'arweave';

import { ARWEAVE_TX_REGEX } from '../constants.js';
import { BlockHeight, Timestamp } from '../types/common.js';
import { PaginationParams } from '../types/io.js';

export const validateArweaveId = (id: string): boolean => {
return ARWEAVE_TX_REGEX.test(id);
Expand Down Expand Up @@ -49,3 +50,16 @@ export const getCurrentBlockUnixTimestampMs = async (
return Date.now(); // fallback to current time
});
};

export const paginationParamsToTags = <T>(
params?: PaginationParams<T>,
): { name: string; value: string }[] => {
const tags = [
{ name: 'Cursor', value: params?.cursor?.toString() },
{ name: 'Limit', value: params?.limit?.toString() },
{ name: 'Sort-By', value: params?.sortBy?.toString() },
{ name: 'Sort-Order', value: params?.sortOrder?.toString() },
];

return pruneTags(tags);
};
Loading

0 comments on commit 82a5b44

Please sign in to comment.