Skip to content

Commit 431b3ee

Browse files
committed
feat: add polymarket and native svm endpoints
1 parent 1f8e115 commit 431b3ee

4 files changed

Lines changed: 3117 additions & 1156 deletions

File tree

package.json

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "@pinax/token-api",
3-
"version": "0.2.5",
3+
"version": "0.2.6",
44
"description": "Pinax Token API - Power your apps & AI agents with real-time token data",
55
"main": "dist/index.js",
66
"module": "dist/index.js",
@@ -18,7 +18,7 @@
1818
],
1919
"scripts": {
2020
"prepublishOnly": "bun run build",
21-
"generate": "openapi-typescript https://token-api.service.stage.pinax.network/openapi -o src/openapi.d.ts",
21+
"generate": "openapi-typescript https://token-api.stage.pinax.network/openapi -o src/openapi.d.ts",
2222
"build": "bun run generate && bun build src/index.ts --outdir dist --target node && bun run build:types",
2323
"build:types": "tsc --emitDeclarationOnly --declaration --outDir dist && cp ./src/openapi.d.ts dist/openapi.d.ts",
2424
"typecheck": "tsc --noEmit",

src/index.spec.ts

Lines changed: 157 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,7 @@ describe('TokenAPI', () => {
4343
expect(client.evm).toBeDefined();
4444
expect(client.svm).toBeDefined();
4545
expect(client.tvm).toBeDefined();
46+
expect(client.polymarket).toBeDefined();
4647
});
4748

4849
it('should create a TokenAPI instance with custom options', () => {
@@ -107,10 +108,12 @@ describe('TokenAPI', () => {
107108
it('should expose svm.tokens API', () => {
108109
expect(client.svm.tokens).toBeDefined();
109110
expect(typeof client.svm.tokens.getTransfers).toBe('function');
111+
expect(typeof client.svm.tokens.getNativeTransfers).toBe('function');
110112
expect(typeof client.svm.tokens.getTokenMetadata).toBe('function');
111113
expect(typeof client.svm.tokens.getBalances).toBe('function');
112114
expect(typeof client.svm.tokens.getNativeBalances).toBe('function');
113115
expect(typeof client.svm.tokens.getHolders).toBe('function');
116+
expect(typeof client.svm.tokens.getNativeHolders).toBe('function');
114117
expect(typeof client.svm.tokens.getAccountOwner).toBe('function');
115118
});
116119

@@ -174,6 +177,26 @@ describe('TokenAPI', () => {
174177
expect(typeof client.getNetworks).toBe('function');
175178
});
176179
});
180+
181+
describe('Polymarket API structure', () => {
182+
let client: TokenAPI;
183+
184+
beforeEach(() => {
185+
client = new TokenAPI();
186+
});
187+
188+
it('should expose polymarket API', () => {
189+
expect(client.polymarket).toBeDefined();
190+
expect(typeof client.polymarket.getMarkets).toBe('function');
191+
expect(typeof client.polymarket.getMarketOHLC).toBe('function');
192+
expect(typeof client.polymarket.getMarketOpenInterest).toBe('function');
193+
expect(typeof client.polymarket.getMarketActivity).toBe('function');
194+
expect(typeof client.polymarket.getMarketPositions).toBe('function');
195+
expect(typeof client.polymarket.getPlatform).toBe('function');
196+
expect(typeof client.polymarket.getUsers).toBe('function');
197+
expect(typeof client.polymarket.getUserPositions).toBe('function');
198+
});
199+
});
177200
});
178201

179202
describe('Constants', () => {
@@ -307,6 +330,19 @@ describe('API methods with mocked fetch', () => {
307330
expect(capturedRequest!.url).toContain('network=solana');
308331
});
309332

333+
it('should call the correct endpoint for SVM native transfers', async () => {
334+
const client = new TokenAPI({ apiToken: 'test-token' });
335+
336+
await client.svm.tokens.getNativeTransfers({
337+
network: 'solana',
338+
limit: 10,
339+
});
340+
341+
expect(capturedRequest).not.toBeNull();
342+
expect(capturedRequest!.url).toContain('/v1/svm/transfers/native');
343+
expect(capturedRequest!.url).toContain('network=solana');
344+
});
345+
310346
it('should include amm_pool filter for SVM pools', async () => {
311347
const client = new TokenAPI({ apiToken: 'test-token' });
312348

@@ -792,6 +828,19 @@ describe('API methods with mocked fetch', () => {
792828
expect(capturedRequest!.url).toContain('mint=');
793829
});
794830

831+
it('should call the correct endpoint for SVM native holders', async () => {
832+
const client = new TokenAPI({ apiToken: 'test-token' });
833+
834+
await client.svm.tokens.getNativeHolders({
835+
network: 'solana',
836+
limit: 10,
837+
});
838+
839+
expect(capturedRequest).not.toBeNull();
840+
expect(capturedRequest!.url).toContain('/v1/svm/holders/native');
841+
expect(capturedRequest!.url).toContain('network=solana');
842+
});
843+
795844
it('should call the correct endpoint for SVM account owner', async () => {
796845
const client = new TokenAPI({ apiToken: 'test-token' });
797846

@@ -932,6 +981,114 @@ describe('API methods with mocked fetch', () => {
932981
expect(capturedRequest!.url).toContain('/v1/tvm/pools/ohlc');
933982
expect(capturedRequest!.url).toContain('pool=pool-address');
934983
});
984+
985+
// --- Polymarket: all methods ---
986+
987+
it('should call the correct endpoint for Polymarket markets', async () => {
988+
const client = new TokenAPI({ apiToken: 'test-token' });
989+
990+
await client.polymarket.getMarkets({
991+
market_slug: 'will-btc-hit-100k',
992+
});
993+
994+
expect(capturedRequest).not.toBeNull();
995+
expect(capturedRequest!.url).toContain('/v1/polymarket/markets');
996+
expect(capturedRequest!.url).toContain('market_slug=will-btc-hit-100k');
997+
});
998+
999+
it('should call the correct endpoint for Polymarket market OHLC', async () => {
1000+
const client = new TokenAPI({ apiToken: 'test-token' });
1001+
1002+
await client.polymarket.getMarketOHLC({
1003+
token_id: '123',
1004+
interval: '1d',
1005+
});
1006+
1007+
expect(capturedRequest).not.toBeNull();
1008+
expect(capturedRequest!.url).toContain('/v1/polymarket/markets/ohlc');
1009+
expect(capturedRequest!.url).toContain('token_id=123');
1010+
expect(capturedRequest!.url).toContain('interval=1d');
1011+
});
1012+
1013+
it('should call the correct endpoint for Polymarket open interest', async () => {
1014+
const client = new TokenAPI({ apiToken: 'test-token' });
1015+
1016+
await client.polymarket.getMarketOpenInterest({
1017+
market_slug: 'will-btc-hit-100k',
1018+
interval: '1h',
1019+
});
1020+
1021+
expect(capturedRequest).not.toBeNull();
1022+
expect(capturedRequest!.url).toContain('/v1/polymarket/markets/oi');
1023+
expect(capturedRequest!.url).toContain('market_slug=will-btc-hit-100k');
1024+
});
1025+
1026+
it('should call the correct endpoint for Polymarket activity', async () => {
1027+
const client = new TokenAPI({ apiToken: 'test-token' });
1028+
1029+
await client.polymarket.getMarketActivity({
1030+
user: '0xabc',
1031+
event_type: 'trade',
1032+
});
1033+
1034+
expect(capturedRequest).not.toBeNull();
1035+
expect(capturedRequest!.url).toContain('/v1/polymarket/markets/activity');
1036+
expect(capturedRequest!.url).toContain('user=0xabc');
1037+
expect(capturedRequest!.url).toContain('event_type=trade');
1038+
});
1039+
1040+
it('should call the correct endpoint for Polymarket market positions', async () => {
1041+
const client = new TokenAPI({ apiToken: 'test-token' });
1042+
1043+
await client.polymarket.getMarketPositions({
1044+
token_id: '123',
1045+
closed: false,
1046+
});
1047+
1048+
expect(capturedRequest).not.toBeNull();
1049+
expect(capturedRequest!.url).toContain('/v1/polymarket/markets/positions');
1050+
expect(capturedRequest!.url).toContain('token_id=123');
1051+
});
1052+
1053+
it('should call the correct endpoint for Polymarket platform aggregates', async () => {
1054+
const client = new TokenAPI({ apiToken: 'test-token' });
1055+
1056+
await client.polymarket.getPlatform({
1057+
interval: '1d',
1058+
});
1059+
1060+
expect(capturedRequest).not.toBeNull();
1061+
expect(capturedRequest!.url).toContain('/v1/polymarket/platform');
1062+
expect(capturedRequest!.url).toContain('interval=1d');
1063+
});
1064+
1065+
it('should call the correct endpoint for Polymarket users', async () => {
1066+
const client = new TokenAPI({ apiToken: 'test-token' });
1067+
1068+
await client.polymarket.getUsers({
1069+
interval: '30d',
1070+
sort_by: 'total_volume',
1071+
});
1072+
1073+
expect(capturedRequest).not.toBeNull();
1074+
expect(capturedRequest!.url).toContain('/v1/polymarket/users');
1075+
expect(capturedRequest!.url).toContain('interval=30d');
1076+
expect(capturedRequest!.url).toContain('sort_by=total_volume');
1077+
});
1078+
1079+
it('should call the correct endpoint for Polymarket user positions', async () => {
1080+
const client = new TokenAPI({ apiToken: 'test-token' });
1081+
1082+
await client.polymarket.getUserPositions({
1083+
user: '0xabc',
1084+
market_slug: 'will-btc-hit-100k',
1085+
});
1086+
1087+
expect(capturedRequest).not.toBeNull();
1088+
expect(capturedRequest!.url).toContain('/v1/polymarket/users/positions');
1089+
expect(capturedRequest!.url).toContain('user=0xabc');
1090+
expect(capturedRequest!.url).toContain('market_slug=will-btc-hit-100k');
1091+
});
9351092
});
9361093

9371094
describe('Error handling', () => {

0 commit comments

Comments
 (0)