opentool 0.18.0 → 0.19.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/adapters/polymarket/index.d.ts +223 -11
- package/dist/adapters/polymarket/index.js +543 -44
- package/dist/adapters/polymarket/index.js.map +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +543 -44
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
- package/templates/base/package.json +1 -1
- package/templates/polymarket-simple-trade/README.md +28 -0
- package/templates/polymarket-simple-trade/metadata.ts +12 -0
- package/templates/polymarket-simple-trade/package.json +23 -0
- package/templates/polymarket-simple-trade/tools/place-polymarket-order.ts +172 -0
- package/templates/polymarket-simple-trade/tsconfig.json +14 -0
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { createHmac, randomBytes } from 'crypto';
|
|
2
|
-
import { parseUnits } from 'viem';
|
|
2
|
+
import { parseUnits, encodeFunctionData, maxUint256, erc20Abi, decodeFunctionData } from 'viem';
|
|
3
3
|
|
|
4
4
|
// src/adapters/polymarket/base.ts
|
|
5
5
|
var PolymarketApiError = class extends Error {
|
|
@@ -159,7 +159,7 @@ async function buildL1Headers(args) {
|
|
|
159
159
|
const nonce = args.nonce ?? Date.now();
|
|
160
160
|
const chainId = POLYMARKET_CHAIN_ID[args.environment ?? "mainnet"];
|
|
161
161
|
const address = args.wallet.address;
|
|
162
|
-
const message = args.message ?? "
|
|
162
|
+
const message = args.message ?? "This message attests that I control the given wallet";
|
|
163
163
|
const signature = await args.wallet.walletClient.signTypedData({
|
|
164
164
|
account: args.wallet.account,
|
|
165
165
|
domain: {
|
|
@@ -313,14 +313,32 @@ async function buildSignedOrderPayload(args) {
|
|
|
313
313
|
}
|
|
314
314
|
|
|
315
315
|
// src/adapters/polymarket/exchange.ts
|
|
316
|
+
function requireApiKeyNonce(nonce, message = "Polymarket API key operations require an explicit nonce.") {
|
|
317
|
+
if (!Number.isSafeInteger(nonce) || nonce == null || nonce < 0) {
|
|
318
|
+
throw new PolymarketAuthError(message);
|
|
319
|
+
}
|
|
320
|
+
return nonce;
|
|
321
|
+
}
|
|
316
322
|
async function resolveAuthContext(args) {
|
|
317
323
|
if (args.wallet) {
|
|
318
|
-
const credentials = args.credentials
|
|
324
|
+
const credentials = args.credentials;
|
|
325
|
+
if (credentials) {
|
|
326
|
+
return {
|
|
327
|
+
credentials,
|
|
328
|
+
address: args.wallet.address
|
|
329
|
+
};
|
|
330
|
+
}
|
|
331
|
+
const apiKeyNonce = requireApiKeyNonce(
|
|
332
|
+
args.apiKeyNonce,
|
|
333
|
+
"Polymarket auto-auth requires apiKeyNonce when credentials are not provided."
|
|
334
|
+
);
|
|
335
|
+
const derivedCredentials = await derivePolymarketApiKey({
|
|
319
336
|
wallet: args.wallet,
|
|
320
|
-
...args.environment ? { environment: args.environment } : {}
|
|
337
|
+
...args.environment ? { environment: args.environment } : {},
|
|
338
|
+
nonce: apiKeyNonce
|
|
321
339
|
});
|
|
322
340
|
return {
|
|
323
|
-
credentials,
|
|
341
|
+
credentials: derivedCredentials,
|
|
324
342
|
address: args.wallet.address
|
|
325
343
|
};
|
|
326
344
|
}
|
|
@@ -352,27 +370,9 @@ function resolvePath(url) {
|
|
|
352
370
|
const parsed = new URL(url);
|
|
353
371
|
return `${parsed.pathname}${parsed.search}`;
|
|
354
372
|
}
|
|
355
|
-
|
|
356
|
-
const environment = args.environment ?? "mainnet";
|
|
357
|
-
const baseUrl = resolvePolymarketBaseUrl("clob", environment);
|
|
358
|
-
const url = `${baseUrl}/auth/api-key`;
|
|
359
|
-
const headers = await buildL1Headers({
|
|
360
|
-
wallet: args.wallet,
|
|
361
|
-
environment,
|
|
362
|
-
...args.timestamp !== void 0 ? { timestamp: args.timestamp } : {},
|
|
363
|
-
...args.nonce !== void 0 ? { nonce: args.nonce } : {},
|
|
364
|
-
...args.message !== void 0 ? { message: args.message } : {}
|
|
365
|
-
});
|
|
366
|
-
const data = await requestJson(url, {
|
|
367
|
-
method: "POST",
|
|
368
|
-
headers: {
|
|
369
|
-
"content-type": "application/json",
|
|
370
|
-
...headers
|
|
371
|
-
},
|
|
372
|
-
body: JSON.stringify({})
|
|
373
|
-
});
|
|
373
|
+
function normalizeApiKeyResponse(data) {
|
|
374
374
|
if (!data?.apiKey || !data?.secret || !data?.passphrase) {
|
|
375
|
-
|
|
375
|
+
return null;
|
|
376
376
|
}
|
|
377
377
|
return {
|
|
378
378
|
apiKey: data.apiKey,
|
|
@@ -380,32 +380,69 @@ async function createPolymarketApiKey(args) {
|
|
|
380
380
|
passphrase: data.passphrase
|
|
381
381
|
};
|
|
382
382
|
}
|
|
383
|
-
async function
|
|
383
|
+
async function requestPolymarketApiKey(args) {
|
|
384
384
|
const environment = args.environment ?? "mainnet";
|
|
385
385
|
const baseUrl = resolvePolymarketBaseUrl("clob", environment);
|
|
386
|
-
const url = `${baseUrl}/auth/derive-api-key`;
|
|
386
|
+
const url = args.mode === "create" ? `${baseUrl}/auth/api-key` : `${baseUrl}/auth/derive-api-key`;
|
|
387
|
+
const nonce = requireApiKeyNonce(args.nonce);
|
|
387
388
|
const headers = await buildL1Headers({
|
|
388
389
|
wallet: args.wallet,
|
|
389
390
|
environment,
|
|
390
391
|
...args.timestamp !== void 0 ? { timestamp: args.timestamp } : {},
|
|
391
|
-
|
|
392
|
+
nonce,
|
|
392
393
|
...args.message !== void 0 ? { message: args.message } : {}
|
|
393
394
|
});
|
|
394
|
-
|
|
395
|
-
method: "GET",
|
|
395
|
+
return await requestJson(url, {
|
|
396
|
+
method: args.mode === "create" ? "POST" : "GET",
|
|
396
397
|
headers: {
|
|
397
398
|
"content-type": "application/json",
|
|
398
399
|
...headers
|
|
399
|
-
}
|
|
400
|
+
},
|
|
401
|
+
...args.mode === "create" ? { body: JSON.stringify({}) } : {}
|
|
400
402
|
});
|
|
401
|
-
|
|
403
|
+
}
|
|
404
|
+
async function createPolymarketApiKey(args) {
|
|
405
|
+
const normalized = normalizeApiKeyResponse(
|
|
406
|
+
await requestPolymarketApiKey({ ...args, mode: "create" })
|
|
407
|
+
);
|
|
408
|
+
if (!normalized) {
|
|
409
|
+
throw new PolymarketAuthError("Failed to create Polymarket API key.");
|
|
410
|
+
}
|
|
411
|
+
return normalized;
|
|
412
|
+
}
|
|
413
|
+
async function derivePolymarketApiKey(args) {
|
|
414
|
+
const normalized = normalizeApiKeyResponse(
|
|
415
|
+
await requestPolymarketApiKey({ ...args, mode: "derive" })
|
|
416
|
+
);
|
|
417
|
+
if (!normalized) {
|
|
402
418
|
throw new PolymarketAuthError("Failed to derive Polymarket API key.");
|
|
403
419
|
}
|
|
404
|
-
return
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
|
|
420
|
+
return normalized;
|
|
421
|
+
}
|
|
422
|
+
async function createOrDerivePolymarketApiKey(args) {
|
|
423
|
+
let deriveError;
|
|
424
|
+
try {
|
|
425
|
+
const derived = normalizeApiKeyResponse(
|
|
426
|
+
await requestPolymarketApiKey({ ...args, mode: "derive" })
|
|
427
|
+
);
|
|
428
|
+
if (derived) {
|
|
429
|
+
return derived;
|
|
430
|
+
}
|
|
431
|
+
} catch (error) {
|
|
432
|
+
deriveError = error;
|
|
433
|
+
}
|
|
434
|
+
const created = normalizeApiKeyResponse(
|
|
435
|
+
await requestPolymarketApiKey({ ...args, mode: "create" })
|
|
436
|
+
);
|
|
437
|
+
if (created) {
|
|
438
|
+
return created;
|
|
439
|
+
}
|
|
440
|
+
if (deriveError) {
|
|
441
|
+
throw deriveError;
|
|
442
|
+
}
|
|
443
|
+
throw new PolymarketAuthError(
|
|
444
|
+
"Failed to derive or create Polymarket API key."
|
|
445
|
+
);
|
|
409
446
|
}
|
|
410
447
|
async function placePolymarketOrder(args) {
|
|
411
448
|
const environment = args.environment ?? "mainnet";
|
|
@@ -419,7 +456,8 @@ async function placePolymarketOrder(args) {
|
|
|
419
456
|
const auth = await resolveAuthContext({
|
|
420
457
|
wallet: args.wallet,
|
|
421
458
|
...args.credentials ? { credentials: args.credentials } : {},
|
|
422
|
-
environment
|
|
459
|
+
environment,
|
|
460
|
+
...args.apiKeyNonce !== void 0 ? { apiKeyNonce: args.apiKeyNonce } : {}
|
|
423
461
|
});
|
|
424
462
|
const body = {
|
|
425
463
|
order: signedOrder,
|
|
@@ -451,7 +489,8 @@ async function cancelPolymarketOrder(args) {
|
|
|
451
489
|
...args.wallet ? { wallet: args.wallet } : {},
|
|
452
490
|
...args.walletAddress ? { walletAddress: args.walletAddress } : {},
|
|
453
491
|
...args.credentials ? { credentials: args.credentials } : {},
|
|
454
|
-
environment
|
|
492
|
+
environment,
|
|
493
|
+
...args.apiKeyNonce !== void 0 ? { apiKeyNonce: args.apiKeyNonce } : {}
|
|
455
494
|
});
|
|
456
495
|
const headers = buildL2Headers({
|
|
457
496
|
credentials: auth.credentials,
|
|
@@ -478,7 +517,8 @@ async function cancelPolymarketOrders(args) {
|
|
|
478
517
|
...args.wallet ? { wallet: args.wallet } : {},
|
|
479
518
|
...args.walletAddress ? { walletAddress: args.walletAddress } : {},
|
|
480
519
|
...args.credentials ? { credentials: args.credentials } : {},
|
|
481
|
-
environment
|
|
520
|
+
environment,
|
|
521
|
+
...args.apiKeyNonce !== void 0 ? { apiKeyNonce: args.apiKeyNonce } : {}
|
|
482
522
|
});
|
|
483
523
|
const headers = buildL2Headers({
|
|
484
524
|
credentials: auth.credentials,
|
|
@@ -504,7 +544,8 @@ async function cancelAllPolymarketOrders(args) {
|
|
|
504
544
|
...args.wallet ? { wallet: args.wallet } : {},
|
|
505
545
|
...args.walletAddress ? { walletAddress: args.walletAddress } : {},
|
|
506
546
|
...args.credentials ? { credentials: args.credentials } : {},
|
|
507
|
-
environment
|
|
547
|
+
environment,
|
|
548
|
+
...args.apiKeyNonce !== void 0 ? { apiKeyNonce: args.apiKeyNonce } : {}
|
|
508
549
|
});
|
|
509
550
|
const headers = buildL2Headers({
|
|
510
551
|
credentials: auth.credentials,
|
|
@@ -529,7 +570,8 @@ async function cancelMarketPolymarketOrders(args) {
|
|
|
529
570
|
...args.wallet ? { wallet: args.wallet } : {},
|
|
530
571
|
...args.walletAddress ? { walletAddress: args.walletAddress } : {},
|
|
531
572
|
...args.credentials ? { credentials: args.credentials } : {},
|
|
532
|
-
environment
|
|
573
|
+
environment,
|
|
574
|
+
...args.apiKeyNonce !== void 0 ? { apiKeyNonce: args.apiKeyNonce } : {}
|
|
533
575
|
});
|
|
534
576
|
const headers = buildL2Headers({
|
|
535
577
|
credentials: auth.credentials,
|
|
@@ -551,6 +593,7 @@ var PolymarketExchangeClient = class {
|
|
|
551
593
|
constructor(args) {
|
|
552
594
|
this.wallet = args.wallet;
|
|
553
595
|
this.credentials = args.credentials;
|
|
596
|
+
this.apiKeyNonce = args.apiKeyNonce;
|
|
554
597
|
this.environment = args.environment ?? "mainnet";
|
|
555
598
|
}
|
|
556
599
|
async getCredentials() {
|
|
@@ -558,7 +601,8 @@ var PolymarketExchangeClient = class {
|
|
|
558
601
|
const resolved = await resolveAuthContext({
|
|
559
602
|
wallet: this.wallet,
|
|
560
603
|
...this.credentials ? { credentials: this.credentials } : {},
|
|
561
|
-
environment: this.environment
|
|
604
|
+
environment: this.environment,
|
|
605
|
+
...this.apiKeyNonce !== void 0 ? { apiKeyNonce: this.apiKeyNonce } : {}
|
|
562
606
|
});
|
|
563
607
|
this.cachedCredentials = resolved.credentials;
|
|
564
608
|
return resolved.credentials;
|
|
@@ -634,6 +678,61 @@ function getString(value) {
|
|
|
634
678
|
const str = String(value).trim();
|
|
635
679
|
return str.length ? str : null;
|
|
636
680
|
}
|
|
681
|
+
function getNumber(value) {
|
|
682
|
+
const numeric = Number(value);
|
|
683
|
+
return Number.isFinite(numeric) ? numeric : null;
|
|
684
|
+
}
|
|
685
|
+
function getInteger(value) {
|
|
686
|
+
const numeric = getNumber(value);
|
|
687
|
+
return numeric == null ? null : Math.trunc(numeric);
|
|
688
|
+
}
|
|
689
|
+
function getBoolean(value) {
|
|
690
|
+
if (typeof value === "boolean") return value;
|
|
691
|
+
if (typeof value === "string") {
|
|
692
|
+
const normalized = value.trim().toLowerCase();
|
|
693
|
+
if (normalized === "true") return true;
|
|
694
|
+
if (normalized === "false") return false;
|
|
695
|
+
}
|
|
696
|
+
return null;
|
|
697
|
+
}
|
|
698
|
+
function normalizeCsvStringInput(value) {
|
|
699
|
+
if (Array.isArray(value)) {
|
|
700
|
+
return value.flatMap((entry) => String(entry).split(",")).map((entry) => entry.trim()).filter((entry) => entry.length > 0);
|
|
701
|
+
}
|
|
702
|
+
if (typeof value === "string") {
|
|
703
|
+
return value.split(",").map((entry) => entry.trim()).filter((entry) => entry.length > 0);
|
|
704
|
+
}
|
|
705
|
+
return [];
|
|
706
|
+
}
|
|
707
|
+
function normalizeCsvNumberInput(value) {
|
|
708
|
+
if (Array.isArray(value)) {
|
|
709
|
+
return value.filter((entry) => Number.isFinite(entry));
|
|
710
|
+
}
|
|
711
|
+
if (typeof value === "number" && Number.isFinite(value)) {
|
|
712
|
+
return [value];
|
|
713
|
+
}
|
|
714
|
+
return [];
|
|
715
|
+
}
|
|
716
|
+
function appendCsvParam(url, key, values) {
|
|
717
|
+
if (values.length > 0) {
|
|
718
|
+
url.searchParams.set(key, values.join(","));
|
|
719
|
+
}
|
|
720
|
+
}
|
|
721
|
+
function appendNumberParam(url, key, value) {
|
|
722
|
+
if (typeof value === "number" && Number.isFinite(value)) {
|
|
723
|
+
url.searchParams.set(key, String(value));
|
|
724
|
+
}
|
|
725
|
+
}
|
|
726
|
+
function appendBooleanParam(url, key, value) {
|
|
727
|
+
if (typeof value === "boolean") {
|
|
728
|
+
url.searchParams.set(key, value ? "true" : "false");
|
|
729
|
+
}
|
|
730
|
+
}
|
|
731
|
+
function assertMutuallyExclusiveMarketScope(market, eventIds) {
|
|
732
|
+
if (market.length > 0 && eventIds.length > 0) {
|
|
733
|
+
throw new Error("market and eventId are mutually exclusive.");
|
|
734
|
+
}
|
|
735
|
+
}
|
|
637
736
|
function normalizeOrderbookLevels(raw) {
|
|
638
737
|
if (!Array.isArray(raw)) return [];
|
|
639
738
|
return raw.map((entry) => {
|
|
@@ -697,6 +796,132 @@ function normalizeGammaMarket(market, event) {
|
|
|
697
796
|
}
|
|
698
797
|
return normalized;
|
|
699
798
|
}
|
|
799
|
+
function normalizeUserPosition(raw) {
|
|
800
|
+
const record = raw && typeof raw === "object" ? raw : {};
|
|
801
|
+
const normalized = {
|
|
802
|
+
proxyWallet: getString(record.proxyWallet),
|
|
803
|
+
asset: getString(record.asset),
|
|
804
|
+
conditionId: getString(record.conditionId),
|
|
805
|
+
size: getNumber(record.size),
|
|
806
|
+
avgPrice: getNumber(record.avgPrice),
|
|
807
|
+
initialValue: getNumber(record.initialValue),
|
|
808
|
+
currentValue: getNumber(record.currentValue),
|
|
809
|
+
cashPnl: getNumber(record.cashPnl),
|
|
810
|
+
percentPnl: getNumber(record.percentPnl),
|
|
811
|
+
totalBought: getNumber(record.totalBought),
|
|
812
|
+
realizedPnl: getNumber(record.realizedPnl),
|
|
813
|
+
percentRealizedPnl: getNumber(record.percentRealizedPnl),
|
|
814
|
+
curPrice: getNumber(record.curPrice),
|
|
815
|
+
title: getString(record.title),
|
|
816
|
+
slug: getString(record.slug),
|
|
817
|
+
icon: getString(record.icon),
|
|
818
|
+
eventSlug: getString(record.eventSlug),
|
|
819
|
+
outcome: getString(record.outcome),
|
|
820
|
+
outcomeIndex: getInteger(record.outcomeIndex),
|
|
821
|
+
oppositeOutcome: getString(record.oppositeOutcome),
|
|
822
|
+
oppositeAsset: getString(record.oppositeAsset),
|
|
823
|
+
endDate: parseOptionalDate(record.endDate)
|
|
824
|
+
};
|
|
825
|
+
const redeemable = getBoolean(record.redeemable);
|
|
826
|
+
if (redeemable != null) normalized.redeemable = redeemable;
|
|
827
|
+
const mergeable = getBoolean(record.mergeable);
|
|
828
|
+
if (mergeable != null) normalized.mergeable = mergeable;
|
|
829
|
+
const negativeRisk = getBoolean(record.negativeRisk);
|
|
830
|
+
if (negativeRisk != null) normalized.negativeRisk = negativeRisk;
|
|
831
|
+
return normalized;
|
|
832
|
+
}
|
|
833
|
+
function normalizeClosedPosition(raw) {
|
|
834
|
+
const record = raw && typeof raw === "object" ? raw : {};
|
|
835
|
+
return {
|
|
836
|
+
proxyWallet: getString(record.proxyWallet),
|
|
837
|
+
asset: getString(record.asset),
|
|
838
|
+
conditionId: getString(record.conditionId),
|
|
839
|
+
avgPrice: getNumber(record.avgPrice),
|
|
840
|
+
totalBought: getNumber(record.totalBought),
|
|
841
|
+
realizedPnl: getNumber(record.realizedPnl),
|
|
842
|
+
curPrice: getNumber(record.curPrice),
|
|
843
|
+
timestamp: getInteger(record.timestamp),
|
|
844
|
+
title: getString(record.title),
|
|
845
|
+
slug: getString(record.slug),
|
|
846
|
+
icon: getString(record.icon),
|
|
847
|
+
eventSlug: getString(record.eventSlug),
|
|
848
|
+
outcome: getString(record.outcome),
|
|
849
|
+
outcomeIndex: getInteger(record.outcomeIndex),
|
|
850
|
+
oppositeOutcome: getString(record.oppositeOutcome),
|
|
851
|
+
oppositeAsset: getString(record.oppositeAsset),
|
|
852
|
+
endDate: parseOptionalDate(record.endDate)
|
|
853
|
+
};
|
|
854
|
+
}
|
|
855
|
+
function normalizeUserActivity(raw) {
|
|
856
|
+
const record = raw && typeof raw === "object" ? raw : {};
|
|
857
|
+
return {
|
|
858
|
+
proxyWallet: getString(record.proxyWallet),
|
|
859
|
+
timestamp: getInteger(record.timestamp),
|
|
860
|
+
conditionId: getString(record.conditionId),
|
|
861
|
+
type: getString(record.type),
|
|
862
|
+
size: getNumber(record.size),
|
|
863
|
+
usdcSize: getNumber(record.usdcSize),
|
|
864
|
+
transactionHash: getString(record.transactionHash),
|
|
865
|
+
price: getNumber(record.price),
|
|
866
|
+
asset: getString(record.asset),
|
|
867
|
+
side: getString(record.side),
|
|
868
|
+
outcomeIndex: getInteger(record.outcomeIndex),
|
|
869
|
+
title: getString(record.title),
|
|
870
|
+
slug: getString(record.slug),
|
|
871
|
+
icon: getString(record.icon),
|
|
872
|
+
eventSlug: getString(record.eventSlug),
|
|
873
|
+
outcome: getString(record.outcome),
|
|
874
|
+
name: getString(record.name),
|
|
875
|
+
pseudonym: getString(record.pseudonym),
|
|
876
|
+
bio: getString(record.bio),
|
|
877
|
+
profileImage: getString(record.profileImage),
|
|
878
|
+
profileImageOptimized: getString(record.profileImageOptimized)
|
|
879
|
+
};
|
|
880
|
+
}
|
|
881
|
+
function normalizePositionValue(raw) {
|
|
882
|
+
const record = raw && typeof raw === "object" ? raw : {};
|
|
883
|
+
return {
|
|
884
|
+
user: getString(record.user),
|
|
885
|
+
value: getNumber(record.value)
|
|
886
|
+
};
|
|
887
|
+
}
|
|
888
|
+
function normalizeProfileUsers(raw) {
|
|
889
|
+
if (!Array.isArray(raw)) return null;
|
|
890
|
+
return raw.map((entry) => {
|
|
891
|
+
const record = entry && typeof entry === "object" ? entry : {};
|
|
892
|
+
const normalized = {
|
|
893
|
+
id: getString(record.id)
|
|
894
|
+
};
|
|
895
|
+
const creator = getBoolean(record.creator);
|
|
896
|
+
if (creator != null) normalized.creator = creator;
|
|
897
|
+
const mod = getBoolean(record.mod);
|
|
898
|
+
if (mod != null) normalized.mod = mod;
|
|
899
|
+
return normalized;
|
|
900
|
+
});
|
|
901
|
+
}
|
|
902
|
+
function normalizePublicProfile(raw) {
|
|
903
|
+
if (!raw || typeof raw !== "object") return null;
|
|
904
|
+
const record = raw;
|
|
905
|
+
const normalized = {
|
|
906
|
+
createdAt: parseOptionalDate(record.createdAt),
|
|
907
|
+
proxyWallet: getString(record.proxyWallet),
|
|
908
|
+
profileImage: getString(record.profileImage),
|
|
909
|
+
bio: getString(record.bio),
|
|
910
|
+
pseudonym: getString(record.pseudonym),
|
|
911
|
+
name: getString(record.name),
|
|
912
|
+
users: normalizeProfileUsers(record.users),
|
|
913
|
+
xUsername: getString(record.xUsername)
|
|
914
|
+
};
|
|
915
|
+
const displayUsernamePublic = getBoolean(record.displayUsernamePublic);
|
|
916
|
+
if (displayUsernamePublic != null) {
|
|
917
|
+
normalized.displayUsernamePublic = displayUsernamePublic;
|
|
918
|
+
}
|
|
919
|
+
const verifiedBadge = getBoolean(record.verifiedBadge);
|
|
920
|
+
if (verifiedBadge != null) {
|
|
921
|
+
normalized.verifiedBadge = verifiedBadge;
|
|
922
|
+
}
|
|
923
|
+
return normalized;
|
|
924
|
+
}
|
|
700
925
|
var PolymarketInfoClient = class {
|
|
701
926
|
constructor(environment = "mainnet") {
|
|
702
927
|
this.environment = environment;
|
|
@@ -719,6 +944,21 @@ var PolymarketInfoClient = class {
|
|
|
719
944
|
priceHistory(params) {
|
|
720
945
|
return fetchPolymarketPriceHistory({ ...params, environment: this.environment });
|
|
721
946
|
}
|
|
947
|
+
positions(params) {
|
|
948
|
+
return fetchPolymarketPositions({ ...params, environment: this.environment });
|
|
949
|
+
}
|
|
950
|
+
closedPositions(params) {
|
|
951
|
+
return fetchPolymarketClosedPositions({ ...params, environment: this.environment });
|
|
952
|
+
}
|
|
953
|
+
activity(params) {
|
|
954
|
+
return fetchPolymarketActivity({ ...params, environment: this.environment });
|
|
955
|
+
}
|
|
956
|
+
positionValue(params) {
|
|
957
|
+
return fetchPolymarketPositionValue({ ...params, environment: this.environment });
|
|
958
|
+
}
|
|
959
|
+
publicProfile(address) {
|
|
960
|
+
return fetchPolymarketPublicProfile({ address, environment: this.environment });
|
|
961
|
+
}
|
|
722
962
|
};
|
|
723
963
|
async function fetchPolymarketMarkets(params = {}) {
|
|
724
964
|
if (params.active !== void 0 && params.active !== true) {
|
|
@@ -825,7 +1065,266 @@ async function fetchPolymarketPriceHistory(params) {
|
|
|
825
1065
|
p: Number(point.p)
|
|
826
1066
|
})).filter((point) => Number.isFinite(point.t) && Number.isFinite(point.p));
|
|
827
1067
|
}
|
|
1068
|
+
async function fetchPolymarketPositions(params) {
|
|
1069
|
+
const environment = params.environment ?? "mainnet";
|
|
1070
|
+
const market = normalizeCsvStringInput(params.market);
|
|
1071
|
+
const eventIds = normalizeCsvNumberInput(params.eventId);
|
|
1072
|
+
assertMutuallyExclusiveMarketScope(market, eventIds);
|
|
1073
|
+
const baseUrl = resolvePolymarketBaseUrl("data", environment);
|
|
1074
|
+
const url = new URL("/positions", baseUrl);
|
|
1075
|
+
url.searchParams.set("user", params.user);
|
|
1076
|
+
appendCsvParam(url, "market", market);
|
|
1077
|
+
appendCsvParam(
|
|
1078
|
+
url,
|
|
1079
|
+
"eventId",
|
|
1080
|
+
eventIds.map((entry) => String(entry))
|
|
1081
|
+
);
|
|
1082
|
+
appendNumberParam(url, "sizeThreshold", params.sizeThreshold);
|
|
1083
|
+
appendBooleanParam(url, "redeemable", params.redeemable);
|
|
1084
|
+
appendBooleanParam(url, "mergeable", params.mergeable);
|
|
1085
|
+
appendNumberParam(url, "limit", params.limit);
|
|
1086
|
+
appendNumberParam(url, "offset", params.offset);
|
|
1087
|
+
if (params.sortBy) url.searchParams.set("sortBy", params.sortBy);
|
|
1088
|
+
if (params.sortDirection) url.searchParams.set("sortDirection", params.sortDirection);
|
|
1089
|
+
if (params.title) url.searchParams.set("title", params.title);
|
|
1090
|
+
const data = await requestJson2(url.toString());
|
|
1091
|
+
return Array.isArray(data) ? data.map((entry) => normalizeUserPosition(entry)) : [];
|
|
1092
|
+
}
|
|
1093
|
+
async function fetchPolymarketClosedPositions(params) {
|
|
1094
|
+
const environment = params.environment ?? "mainnet";
|
|
1095
|
+
const market = normalizeCsvStringInput(params.market);
|
|
1096
|
+
const eventIds = normalizeCsvNumberInput(params.eventId);
|
|
1097
|
+
assertMutuallyExclusiveMarketScope(market, eventIds);
|
|
1098
|
+
const baseUrl = resolvePolymarketBaseUrl("data", environment);
|
|
1099
|
+
const url = new URL("/closed-positions", baseUrl);
|
|
1100
|
+
url.searchParams.set("user", params.user);
|
|
1101
|
+
appendCsvParam(url, "market", market);
|
|
1102
|
+
appendCsvParam(
|
|
1103
|
+
url,
|
|
1104
|
+
"eventId",
|
|
1105
|
+
eventIds.map((entry) => String(entry))
|
|
1106
|
+
);
|
|
1107
|
+
appendNumberParam(url, "limit", params.limit);
|
|
1108
|
+
appendNumberParam(url, "offset", params.offset);
|
|
1109
|
+
if (params.sortBy) url.searchParams.set("sortBy", params.sortBy);
|
|
1110
|
+
if (params.sortDirection) url.searchParams.set("sortDirection", params.sortDirection);
|
|
1111
|
+
if (params.title) url.searchParams.set("title", params.title);
|
|
1112
|
+
const data = await requestJson2(url.toString());
|
|
1113
|
+
return Array.isArray(data) ? data.map((entry) => normalizeClosedPosition(entry)) : [];
|
|
1114
|
+
}
|
|
1115
|
+
async function fetchPolymarketActivity(params) {
|
|
1116
|
+
const environment = params.environment ?? "mainnet";
|
|
1117
|
+
const market = normalizeCsvStringInput(params.market);
|
|
1118
|
+
const eventIds = normalizeCsvNumberInput(params.eventId);
|
|
1119
|
+
assertMutuallyExclusiveMarketScope(market, eventIds);
|
|
1120
|
+
const types = Array.isArray(params.type) ? params.type : params.type ? [params.type] : [];
|
|
1121
|
+
const baseUrl = resolvePolymarketBaseUrl("data", environment);
|
|
1122
|
+
const url = new URL("/activity", baseUrl);
|
|
1123
|
+
url.searchParams.set("user", params.user);
|
|
1124
|
+
appendCsvParam(url, "market", market);
|
|
1125
|
+
appendCsvParam(
|
|
1126
|
+
url,
|
|
1127
|
+
"eventId",
|
|
1128
|
+
eventIds.map((entry) => String(entry))
|
|
1129
|
+
);
|
|
1130
|
+
appendCsvParam(url, "type", types);
|
|
1131
|
+
appendNumberParam(url, "start", params.start);
|
|
1132
|
+
appendNumberParam(url, "end", params.end);
|
|
1133
|
+
appendNumberParam(url, "limit", params.limit);
|
|
1134
|
+
appendNumberParam(url, "offset", params.offset);
|
|
1135
|
+
if (params.sortBy) url.searchParams.set("sortBy", params.sortBy);
|
|
1136
|
+
if (params.sortDirection) url.searchParams.set("sortDirection", params.sortDirection);
|
|
1137
|
+
if (params.side) url.searchParams.set("side", params.side);
|
|
1138
|
+
const data = await requestJson2(url.toString());
|
|
1139
|
+
return Array.isArray(data) ? data.map((entry) => normalizeUserActivity(entry)) : [];
|
|
1140
|
+
}
|
|
1141
|
+
async function fetchPolymarketPositionValue(params) {
|
|
1142
|
+
const environment = params.environment ?? "mainnet";
|
|
1143
|
+
const baseUrl = resolvePolymarketBaseUrl("data", environment);
|
|
1144
|
+
const url = new URL("/value", baseUrl);
|
|
1145
|
+
url.searchParams.set("user", params.user);
|
|
1146
|
+
appendCsvParam(url, "market", normalizeCsvStringInput(params.market));
|
|
1147
|
+
const data = await requestJson2(url.toString());
|
|
1148
|
+
return Array.isArray(data) ? data.map((entry) => normalizePositionValue(entry)) : [];
|
|
1149
|
+
}
|
|
1150
|
+
async function fetchPolymarketPublicProfile(params) {
|
|
1151
|
+
const environment = params.environment ?? "mainnet";
|
|
1152
|
+
const baseUrl = resolvePolymarketBaseUrl("gamma", environment);
|
|
1153
|
+
const url = new URL("/public-profile", baseUrl);
|
|
1154
|
+
url.searchParams.set("address", params.address);
|
|
1155
|
+
const data = await requestJson2(url.toString());
|
|
1156
|
+
return normalizePublicProfile(data);
|
|
1157
|
+
}
|
|
1158
|
+
var POLYMARKET_SET_APPROVAL_FOR_ALL_ABI = [
|
|
1159
|
+
{
|
|
1160
|
+
inputs: [
|
|
1161
|
+
{ name: "operator", type: "address" },
|
|
1162
|
+
{ name: "approved", type: "bool" }
|
|
1163
|
+
],
|
|
1164
|
+
name: "setApprovalForAll",
|
|
1165
|
+
outputs: [],
|
|
1166
|
+
stateMutability: "nonpayable",
|
|
1167
|
+
type: "function"
|
|
1168
|
+
},
|
|
1169
|
+
{
|
|
1170
|
+
inputs: [
|
|
1171
|
+
{ name: "account", type: "address" },
|
|
1172
|
+
{ name: "operator", type: "address" }
|
|
1173
|
+
],
|
|
1174
|
+
name: "isApprovedForAll",
|
|
1175
|
+
outputs: [{ name: "", type: "bool" }],
|
|
1176
|
+
stateMutability: "view",
|
|
1177
|
+
type: "function"
|
|
1178
|
+
}
|
|
1179
|
+
];
|
|
1180
|
+
var POLYMARKET_BOOTSTRAP_CONTRACTS_BY_ENV = {
|
|
1181
|
+
mainnet: {
|
|
1182
|
+
usdc: "0x2791Bca1f2de4661ED88A30C99A7a9449Aa84174",
|
|
1183
|
+
ctf: "0x4D97DCd97eC945f40cF65F87097ACe5EA0476045",
|
|
1184
|
+
negRiskAdapter: "0xd91E80cF2E7be2e162c6513ceD06f1dD0dA35296",
|
|
1185
|
+
safeFactory: "0xaacFeEa03eb1561C4e67d661e40682Bd20E3541b",
|
|
1186
|
+
safeMultisend: "0xA238CBeb142c10Ef7Ad8442C6D1f9E89e07e7761",
|
|
1187
|
+
relayerUrl: "https://relayer-v2.polymarket.com",
|
|
1188
|
+
bridgeUrl: "https://bridge.polymarket.com"
|
|
1189
|
+
}
|
|
1190
|
+
};
|
|
1191
|
+
async function requestJson3(url, init) {
|
|
1192
|
+
const response = await fetch(url, init);
|
|
1193
|
+
const text = await response.text().catch(() => "");
|
|
1194
|
+
let data = null;
|
|
1195
|
+
try {
|
|
1196
|
+
data = text ? JSON.parse(text) : null;
|
|
1197
|
+
} catch {
|
|
1198
|
+
data = text;
|
|
1199
|
+
}
|
|
1200
|
+
if (!response.ok) {
|
|
1201
|
+
throw new PolymarketApiError(
|
|
1202
|
+
`Polymarket request failed (${response.status}).`,
|
|
1203
|
+
data ?? { status: response.status }
|
|
1204
|
+
);
|
|
1205
|
+
}
|
|
1206
|
+
return data;
|
|
1207
|
+
}
|
|
1208
|
+
function resolvePolymarketBootstrapContracts(environment) {
|
|
1209
|
+
const contracts = POLYMARKET_BOOTSTRAP_CONTRACTS_BY_ENV[environment];
|
|
1210
|
+
if (!contracts) {
|
|
1211
|
+
throw new Error(
|
|
1212
|
+
`Polymarket bootstrap contracts are not configured for ${environment}.`
|
|
1213
|
+
);
|
|
1214
|
+
}
|
|
1215
|
+
return contracts;
|
|
1216
|
+
}
|
|
1217
|
+
function buildPolymarketUsdcApprovalTransaction(args) {
|
|
1218
|
+
const environment = args?.environment ?? "mainnet";
|
|
1219
|
+
const contracts = resolvePolymarketBootstrapContracts(environment);
|
|
1220
|
+
return {
|
|
1221
|
+
to: contracts.usdc,
|
|
1222
|
+
data: encodeFunctionData({
|
|
1223
|
+
abi: erc20Abi,
|
|
1224
|
+
functionName: "approve",
|
|
1225
|
+
args: [contracts.ctf, args?.amount ?? maxUint256]
|
|
1226
|
+
}),
|
|
1227
|
+
value: "0",
|
|
1228
|
+
description: "Approve USDC.e for CTF"
|
|
1229
|
+
};
|
|
1230
|
+
}
|
|
1231
|
+
function buildPolymarketOutcomeTokenApprovalTransactions(args) {
|
|
1232
|
+
const environment = args?.environment ?? "mainnet";
|
|
1233
|
+
const includeNegRisk = args?.includeNegRisk ?? true;
|
|
1234
|
+
const contracts = resolvePolymarketBootstrapContracts(environment);
|
|
1235
|
+
const transactions = [
|
|
1236
|
+
{
|
|
1237
|
+
to: contracts.ctf,
|
|
1238
|
+
data: encodeFunctionData({
|
|
1239
|
+
abi: POLYMARKET_SET_APPROVAL_FOR_ALL_ABI,
|
|
1240
|
+
functionName: "setApprovalForAll",
|
|
1241
|
+
args: [POLYMARKET_EXCHANGE_ADDRESSES[environment].ctf, true]
|
|
1242
|
+
}),
|
|
1243
|
+
value: "0",
|
|
1244
|
+
description: "Approve outcome tokens for CTF Exchange"
|
|
1245
|
+
}
|
|
1246
|
+
];
|
|
1247
|
+
if (includeNegRisk) {
|
|
1248
|
+
transactions.push({
|
|
1249
|
+
to: contracts.ctf,
|
|
1250
|
+
data: encodeFunctionData({
|
|
1251
|
+
abi: POLYMARKET_SET_APPROVAL_FOR_ALL_ABI,
|
|
1252
|
+
functionName: "setApprovalForAll",
|
|
1253
|
+
args: [POLYMARKET_EXCHANGE_ADDRESSES[environment].negRisk, true]
|
|
1254
|
+
}),
|
|
1255
|
+
value: "0",
|
|
1256
|
+
description: "Approve outcome tokens for Neg Risk Exchange"
|
|
1257
|
+
});
|
|
1258
|
+
}
|
|
1259
|
+
return transactions;
|
|
1260
|
+
}
|
|
1261
|
+
function buildPolymarketApprovalTransactions(args) {
|
|
1262
|
+
return [
|
|
1263
|
+
buildPolymarketUsdcApprovalTransaction(args),
|
|
1264
|
+
...buildPolymarketOutcomeTokenApprovalTransactions(args)
|
|
1265
|
+
];
|
|
1266
|
+
}
|
|
1267
|
+
async function fetchPolymarketApprovalState(args) {
|
|
1268
|
+
const environment = args.environment ?? "mainnet";
|
|
1269
|
+
const includeNegRisk = args.includeNegRisk ?? true;
|
|
1270
|
+
const contracts = resolvePolymarketBootstrapContracts(environment);
|
|
1271
|
+
const ctfExchange = POLYMARKET_EXCHANGE_ADDRESSES[environment].ctf;
|
|
1272
|
+
const negRiskExchange = POLYMARKET_EXCHANGE_ADDRESSES[environment].negRisk;
|
|
1273
|
+
const [allowance, ctfExchangeApproved, negRiskExchangeApproved] = await Promise.all([
|
|
1274
|
+
args.publicClient.readContract({
|
|
1275
|
+
address: contracts.usdc,
|
|
1276
|
+
abi: erc20Abi,
|
|
1277
|
+
functionName: "allowance",
|
|
1278
|
+
args: [args.funder, contracts.ctf]
|
|
1279
|
+
}),
|
|
1280
|
+
args.publicClient.readContract({
|
|
1281
|
+
address: contracts.ctf,
|
|
1282
|
+
abi: POLYMARKET_SET_APPROVAL_FOR_ALL_ABI,
|
|
1283
|
+
functionName: "isApprovedForAll",
|
|
1284
|
+
args: [args.funder, ctfExchange]
|
|
1285
|
+
}),
|
|
1286
|
+
includeNegRisk ? args.publicClient.readContract({
|
|
1287
|
+
address: contracts.ctf,
|
|
1288
|
+
abi: POLYMARKET_SET_APPROVAL_FOR_ALL_ABI,
|
|
1289
|
+
functionName: "isApprovedForAll",
|
|
1290
|
+
args: [args.funder, negRiskExchange]
|
|
1291
|
+
}) : Promise.resolve(true)
|
|
1292
|
+
]);
|
|
1293
|
+
return {
|
|
1294
|
+
funder: args.funder,
|
|
1295
|
+
usdcAllowance: allowance,
|
|
1296
|
+
usdcApproved: allowance > 0n,
|
|
1297
|
+
ctfExchangeApproved,
|
|
1298
|
+
negRiskExchangeApproved,
|
|
1299
|
+
approvalsReady: allowance > 0n && ctfExchangeApproved && negRiskExchangeApproved
|
|
1300
|
+
};
|
|
1301
|
+
}
|
|
1302
|
+
async function fetchPolymarketDepositAddresses(args) {
|
|
1303
|
+
const environment = args.environment ?? "mainnet";
|
|
1304
|
+
const contracts = resolvePolymarketBootstrapContracts(environment);
|
|
1305
|
+
return await requestJson3(`${contracts.bridgeUrl}/deposit`, {
|
|
1306
|
+
method: "POST",
|
|
1307
|
+
headers: {
|
|
1308
|
+
"content-type": "application/json"
|
|
1309
|
+
},
|
|
1310
|
+
body: JSON.stringify({
|
|
1311
|
+
address: args.address
|
|
1312
|
+
})
|
|
1313
|
+
});
|
|
1314
|
+
}
|
|
1315
|
+
function decodePolymarketBootstrapTransaction(transaction) {
|
|
1316
|
+
const abi = transaction.to.toLowerCase() === resolvePolymarketBootstrapContracts("mainnet").usdc.toLowerCase() ? erc20Abi : POLYMARKET_SET_APPROVAL_FOR_ALL_ABI;
|
|
1317
|
+
const decoded = decodeFunctionData({
|
|
1318
|
+
abi,
|
|
1319
|
+
data: transaction.data
|
|
1320
|
+
});
|
|
1321
|
+
return {
|
|
1322
|
+
to: transaction.to,
|
|
1323
|
+
functionName: decoded.functionName,
|
|
1324
|
+
args: decoded.args ?? []
|
|
1325
|
+
};
|
|
1326
|
+
}
|
|
828
1327
|
|
|
829
|
-
export { POLYMARKET_CHAIN_ID, POLYMARKET_CLOB_AUTH_DOMAIN, POLYMARKET_CLOB_DOMAIN, POLYMARKET_ENDPOINTS, POLYMARKET_EXCHANGE_ADDRESSES, PolymarketApiError, PolymarketAuthError, PolymarketExchangeClient, PolymarketInfoClient, buildHmacSignature, buildL1Headers, buildL2Headers, buildPolymarketOrderAmounts, buildSignedOrderPayload, cancelAllPolymarketOrders, cancelMarketPolymarketOrders, cancelPolymarketOrder, cancelPolymarketOrders, createPolymarketApiKey, derivePolymarketApiKey, fetchPolymarketMarket, fetchPolymarketMarkets, fetchPolymarketMidpoint, fetchPolymarketOrderbook, fetchPolymarketPrice, fetchPolymarketPriceHistory, normalizeNumberArrayish, normalizeStringArrayish, placePolymarketOrder, resolveExchangeAddress, resolvePolymarketBaseUrl };
|
|
1328
|
+
export { POLYMARKET_CHAIN_ID, POLYMARKET_CLOB_AUTH_DOMAIN, POLYMARKET_CLOB_DOMAIN, POLYMARKET_ENDPOINTS, POLYMARKET_EXCHANGE_ADDRESSES, PolymarketApiError, PolymarketAuthError, PolymarketExchangeClient, PolymarketInfoClient, buildHmacSignature, buildL1Headers, buildL2Headers, buildPolymarketApprovalTransactions, buildPolymarketOrderAmounts, buildPolymarketOutcomeTokenApprovalTransactions, buildPolymarketUsdcApprovalTransaction, buildSignedOrderPayload, cancelAllPolymarketOrders, cancelMarketPolymarketOrders, cancelPolymarketOrder, cancelPolymarketOrders, createOrDerivePolymarketApiKey, createPolymarketApiKey, decodePolymarketBootstrapTransaction, derivePolymarketApiKey, fetchPolymarketActivity, fetchPolymarketApprovalState, fetchPolymarketClosedPositions, fetchPolymarketDepositAddresses, fetchPolymarketMarket, fetchPolymarketMarkets, fetchPolymarketMidpoint, fetchPolymarketOrderbook, fetchPolymarketPositionValue, fetchPolymarketPositions, fetchPolymarketPrice, fetchPolymarketPriceHistory, fetchPolymarketPublicProfile, normalizeNumberArrayish, normalizeStringArrayish, placePolymarketOrder, resolveExchangeAddress, resolvePolymarketBaseUrl, resolvePolymarketBootstrapContracts };
|
|
830
1329
|
//# sourceMappingURL=index.js.map
|
|
831
1330
|
//# sourceMappingURL=index.js.map
|