perp-cli 0.6.4 → 0.7.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/README.md +7 -2
- package/dist/api/public/hyperliquid.d.ts +2 -2
- package/dist/api/public/hyperliquid.js +0 -10
- package/dist/api/public/lighter.d.ts +2 -1
- package/dist/api/public/pacifica.d.ts +2 -1
- package/dist/arb/index.d.ts +7 -4
- package/dist/arb/index.js +5 -4
- package/dist/arb/sizing.d.ts +1 -1
- package/dist/arb/state.d.ts +1 -1
- package/dist/arb/state.js +4 -3
- package/dist/arb/utils.d.ts +0 -10
- package/dist/arb/utils.js +0 -42
- package/dist/bot/apex/guard.d.ts +26 -0
- package/dist/bot/apex/guard.js +86 -0
- package/dist/bot/apex/index.d.ts +6 -0
- package/dist/bot/apex/index.js +4 -0
- package/dist/bot/apex/pulse.d.ts +22 -0
- package/dist/bot/apex/pulse.js +107 -0
- package/dist/bot/apex/radar.d.ts +17 -0
- package/dist/bot/apex/radar.js +150 -0
- package/dist/bot/conditions.d.ts +1 -1
- package/dist/bot/config.d.ts +5 -1
- package/dist/bot/config.js +1 -1
- package/dist/bot/engine.d.ts +23 -2
- package/dist/bot/engine.js +296 -351
- package/dist/bot/index.d.ts +16 -0
- package/dist/bot/index.js +10 -0
- package/dist/bot/indicators.d.ts +29 -0
- package/dist/bot/indicators.js +144 -0
- package/dist/bot/reflect.d.ts +34 -0
- package/dist/bot/reflect.js +155 -0
- package/dist/bot/strategies/aggressive-taker.d.ts +36 -0
- package/dist/bot/strategies/aggressive-taker.js +125 -0
- package/dist/bot/strategies/apex-strategy.d.ts +36 -0
- package/dist/bot/strategies/apex-strategy.js +185 -0
- package/dist/bot/strategies/avellaneda-mm.d.ts +27 -0
- package/dist/bot/strategies/avellaneda-mm.js +111 -0
- package/dist/bot/strategies/basis-arb.d.ts +27 -0
- package/dist/bot/strategies/basis-arb.js +97 -0
- package/dist/bot/strategies/claude-agent.d.ts +31 -0
- package/dist/bot/strategies/claude-agent.js +155 -0
- package/dist/bot/strategies/dca-strategy.d.ts +25 -0
- package/dist/bot/strategies/dca-strategy.js +59 -0
- package/dist/bot/strategies/engine-mm.d.ts +29 -0
- package/dist/bot/strategies/engine-mm.js +141 -0
- package/dist/bot/strategies/funding-arb-strategy.d.ts +32 -0
- package/dist/bot/strategies/funding-arb-strategy.js +168 -0
- package/dist/bot/strategies/funding-arb-v2.d.ts +32 -0
- package/dist/bot/strategies/funding-arb-v2.js +222 -0
- package/dist/bot/strategies/funding-auto.d.ts +1 -0
- package/dist/bot/strategies/funding-auto.js +572 -0
- package/dist/bot/strategies/grid-mm.d.ts +25 -0
- package/dist/bot/strategies/grid-mm.js +99 -0
- package/dist/bot/strategies/grid-strategy.d.ts +39 -0
- package/dist/bot/strategies/grid-strategy.js +176 -0
- package/dist/bot/strategies/hedge-agent.d.ts +25 -0
- package/dist/bot/strategies/hedge-agent.js +79 -0
- package/dist/bot/strategies/liquidation-mm.d.ts +25 -0
- package/dist/bot/strategies/liquidation-mm.js +108 -0
- package/dist/bot/strategies/mean-reversion.d.ts +35 -0
- package/dist/bot/strategies/mean-reversion.js +118 -0
- package/dist/bot/strategies/momentum-breakout.d.ts +36 -0
- package/dist/bot/strategies/momentum-breakout.js +159 -0
- package/dist/bot/strategies/regime-mm.d.ts +25 -0
- package/dist/bot/strategies/regime-mm.js +111 -0
- package/dist/bot/strategies/rfq-agent.d.ts +25 -0
- package/dist/bot/strategies/rfq-agent.js +71 -0
- package/dist/bot/strategies/simple-mm.d.ts +25 -0
- package/dist/bot/strategies/simple-mm.js +76 -0
- package/dist/bot/strategy-registry.d.ts +9 -0
- package/dist/bot/strategy-registry.js +14 -0
- package/dist/bot/strategy-types.d.ts +64 -0
- package/dist/bot/strategy-types.js +5 -0
- package/dist/bot/trade-journal.d.ts +27 -0
- package/dist/bot/trade-journal.js +53 -0
- package/dist/bot/tui/BotDashboard.d.ts +49 -0
- package/dist/bot/tui/BotDashboard.js +93 -0
- package/dist/bot/tui/index.d.ts +6 -0
- package/dist/bot/tui/index.js +8 -0
- package/dist/bridge-engine.d.ts +0 -1
- package/dist/bridge-engine.js +0 -1
- package/dist/cache.d.ts +0 -1
- package/dist/cache.js +0 -1
- package/dist/commands/account.d.ts +1 -1
- package/dist/commands/account.js +94 -91
- package/dist/commands/agent.d.ts +1 -1
- package/dist/commands/arb/index.d.ts +1 -1
- package/dist/commands/arb/index.js +1 -1
- package/dist/commands/arb-auto.d.ts +1 -1
- package/dist/commands/arb-auto.js +1 -1
- package/dist/commands/arb.d.ts +1 -1
- package/dist/commands/bot.d.ts +1 -1
- package/dist/commands/bot.js +198 -14
- package/dist/commands/dashboard.d.ts +1 -1
- package/dist/commands/dashboard.js +1 -1
- package/dist/commands/funds.d.ts +1 -1
- package/dist/commands/funds.js +33 -20
- package/dist/commands/history.d.ts +1 -1
- package/dist/commands/history.js +5 -4
- package/dist/commands/manage.d.ts +2 -3
- package/dist/commands/manage.js +11 -18
- package/dist/commands/market.d.ts +1 -1
- package/dist/commands/market.js +7 -7
- package/dist/commands/plan.d.ts +1 -1
- package/dist/commands/rebalance.d.ts +1 -1
- package/dist/commands/rebalance.js +8 -9
- package/dist/commands/risk.d.ts +1 -1
- package/dist/commands/settings.d.ts +1 -1
- package/dist/commands/settings.js +3 -1
- package/dist/commands/trade.d.ts +1 -1
- package/dist/commands/trade.js +39 -52
- package/dist/commands/wallet.d.ts +0 -2
- package/dist/commands/wallet.js +0 -5
- package/dist/constants.d.ts +0 -3
- package/dist/constants.js +0 -4
- package/dist/cross-chain-margin.d.ts +1 -1
- package/dist/dashboard/index.d.ts +4 -0
- package/dist/dashboard/index.js +3 -0
- package/dist/dashboard/server.d.ts +1 -1
- package/dist/dashboard/server.js +1 -1
- package/dist/dashboard/ws-feeds.d.ts +1 -1
- package/dist/event-stream.d.ts +1 -1
- package/dist/exchanges/aster.d.ts +58 -0
- package/dist/exchanges/aster.js +409 -0
- package/dist/exchanges/capabilities.d.ts +74 -0
- package/dist/exchanges/capabilities.js +44 -0
- package/dist/exchanges/hyperliquid-spot.d.ts +1 -1
- package/dist/exchanges/hyperliquid-spot.js +20 -12
- package/dist/exchanges/hyperliquid.d.ts +8 -2
- package/dist/exchanges/hyperliquid.js +21 -6
- package/dist/exchanges/index.d.ts +11 -0
- package/dist/exchanges/index.js +10 -0
- package/dist/exchanges/interface.d.ts +3 -0
- package/dist/exchanges/lighter-spot.d.ts +13 -0
- package/dist/exchanges/lighter-spot.js +98 -26
- package/dist/exchanges/lighter.d.ts +9 -3
- package/dist/exchanges/lighter.js +18 -8
- package/dist/exchanges/nado.d.ts +52 -0
- package/dist/exchanges/nado.js +223 -0
- package/dist/exchanges/pacifica.d.ts +7 -1
- package/dist/exchanges/pacifica.js +17 -2
- package/dist/exchanges/registry.d.ts +13 -0
- package/dist/exchanges/registry.js +37 -0
- package/dist/exchanges/spot-interface.d.ts +9 -0
- package/dist/funding/rates.js +1 -1
- package/dist/index.js +2 -6
- package/dist/jobs.js +1 -1
- package/dist/liquidity.d.ts +1 -2
- package/dist/liquidity.js +12 -5
- package/dist/mcp-server.js +4 -2
- package/dist/pacifica/constants.d.ts +0 -3
- package/dist/pacifica/constants.js +0 -4
- package/dist/pacifica/types/account.d.ts +0 -8
- package/dist/pacifica/types/lake.d.ts +0 -6
- package/dist/pacifica/types/position.d.ts +0 -12
- package/dist/pacifica/types/ws.d.ts +0 -24
- package/dist/pacifica/types/ws.js +1 -41
- package/dist/plan-executor.d.ts +1 -1
- package/dist/rebalance.d.ts +1 -7
- package/dist/rebalance.js +0 -6
- package/dist/risk.d.ts +1 -1
- package/dist/risk.js +3 -1
- package/dist/smart-order.d.ts +1 -1
- package/dist/strategies/dca.d.ts +1 -1
- package/dist/strategies/funding-arb.d.ts +1 -1
- package/dist/strategies/funding-arb.js +193 -181
- package/dist/strategies/grid.d.ts +1 -1
- package/dist/strategies/grid.js +1 -1
- package/dist/strategies/index.d.ts +12 -0
- package/dist/strategies/index.js +7 -0
- package/dist/strategies/split-order.d.ts +1 -1
- package/dist/strategies/trailing-stop.d.ts +1 -1
- package/dist/strategies/twap.d.ts +1 -1
- package/dist/trade-validator.d.ts +1 -1
- package/package.json +7 -1
- package/skills/perp-cli/SKILL.md +20 -0
- package/skills/perp-cli/references/commands.md +22 -8
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
import { Command } from "commander";
|
|
2
|
-
import type { ExchangeAdapter } from "../exchanges/
|
|
2
|
+
import type { ExchangeAdapter } from "../exchanges/index.js";
|
|
3
3
|
export declare function registerDashboardCommands(program: Command, getAdapterForExchange: (exchange: string) => Promise<ExchangeAdapter>, isJson: () => boolean, getHLAdapterForDex?: (dex: string) => Promise<ExchangeAdapter>): void;
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import chalk from "chalk";
|
|
2
|
-
import { startDashboard } from "../dashboard/
|
|
2
|
+
import { startDashboard } from "../dashboard/index.js";
|
|
3
3
|
const KNOWN_HIP3_DEXES = ["xyz", "flx", "hyna", "km", "cash", "vntl"];
|
|
4
4
|
const HL_INFO_URL = "https://api.hyperliquid.xyz/info";
|
|
5
5
|
/** Lightweight check: query HL info API directly for dex positions (no SDK/WebSocket needed) */
|
package/dist/commands/funds.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
import { Command } from "commander";
|
|
2
|
-
import type { ExchangeAdapter } from "../exchanges/
|
|
2
|
+
import type { ExchangeAdapter } from "../exchanges/index.js";
|
|
3
3
|
import type { Network } from "../pacifica/index.js";
|
|
4
4
|
export declare function registerFundsCommands(program: Command, getAdapter: () => Promise<ExchangeAdapter>, isJson: () => boolean, getNetwork: () => Network): void;
|
package/dist/commands/funds.js
CHANGED
|
@@ -1,8 +1,7 @@
|
|
|
1
1
|
import chalk from "chalk";
|
|
2
|
-
import { printJson, formatUsd, jsonOk } from "../utils.js";
|
|
3
|
-
import { PacificaAdapter } from "../exchanges/pacifica.js";
|
|
4
|
-
import { HyperliquidAdapter } from "../exchanges/hyperliquid.js";
|
|
2
|
+
import { printJson, formatUsd, jsonOk, jsonError } from "../utils.js";
|
|
5
3
|
import { logExecution } from "../execution-log.js";
|
|
4
|
+
import { hasPacificaSdk, hasEvmAddress, isWithdrawCapable, isUsdTransferCapable, hasLighterAccount } from "../exchanges/capabilities.js";
|
|
6
5
|
const DEFAULT_RELAYER = "http://localhost:3100";
|
|
7
6
|
function getRelayerUrl() {
|
|
8
7
|
return process.env.PERP_RELAYER_URL || DEFAULT_RELAYER;
|
|
@@ -38,14 +37,16 @@ export function registerFundsCommands(program, getAdapter, isJson, getNetwork) {
|
|
|
38
37
|
if (!isJson())
|
|
39
38
|
console.log(chalk.cyan(`\n Depositing $${formatUsd(amountNum)} via relayer (gasless)...\n`));
|
|
40
39
|
const adapter = await getAdapter();
|
|
41
|
-
if (
|
|
40
|
+
if (adapter.name !== "pacifica")
|
|
42
41
|
throw new Error("Requires --exchange pacifica");
|
|
42
|
+
const { PacificaAdapter } = await import("../exchanges/pacifica.js");
|
|
43
|
+
const pacAdapter = adapter;
|
|
43
44
|
try {
|
|
44
45
|
const buildRes = await fetch(`${getRelayerUrl()}/deposit/pacifica/build`, {
|
|
45
46
|
method: "POST",
|
|
46
47
|
headers: { "Content-Type": "application/json" },
|
|
47
48
|
body: JSON.stringify({
|
|
48
|
-
userPubkey:
|
|
49
|
+
userPubkey: pacAdapter.keypair.publicKey.toBase58(),
|
|
49
50
|
amount: amountNum,
|
|
50
51
|
testnet: getNetwork() === "testnet",
|
|
51
52
|
}),
|
|
@@ -61,7 +62,7 @@ export function registerFundsCommands(program, getAdapter, isJson, getNetwork) {
|
|
|
61
62
|
}
|
|
62
63
|
const { Transaction } = await import("@solana/web3.js");
|
|
63
64
|
const tx = Transaction.from(Buffer.from(transaction, "base64"));
|
|
64
|
-
tx.partialSign(
|
|
65
|
+
tx.partialSign(pacAdapter.keypair);
|
|
65
66
|
const signed = tx.serialize().toString("base64");
|
|
66
67
|
const submitRes = await fetch(`${getRelayerUrl()}/deposit/pacifica/submit`, {
|
|
67
68
|
method: "POST",
|
|
@@ -104,15 +105,17 @@ export function registerFundsCommands(program, getAdapter, isJson, getNetwork) {
|
|
|
104
105
|
console.log(chalk.gray(" Requires: SOL for gas (~0.005 SOL) + USDC on Solana\n"));
|
|
105
106
|
}
|
|
106
107
|
const adapter = await getAdapter();
|
|
107
|
-
if (
|
|
108
|
+
if (adapter.name !== "pacifica")
|
|
108
109
|
throw new Error("Requires --exchange pacifica");
|
|
110
|
+
const { PacificaAdapter: PacAdapterCls } = await import("../exchanges/pacifica.js");
|
|
111
|
+
const pacDirect = adapter;
|
|
109
112
|
try {
|
|
110
113
|
const { Connection, Transaction } = await import("@solana/web3.js");
|
|
111
114
|
const { buildDepositInstruction } = await import("../pacifica/deposit.js");
|
|
112
115
|
const network = getNetwork();
|
|
113
116
|
const rpcUrl = network === "testnet" ? "https://api.devnet.solana.com" : "https://api.mainnet-beta.solana.com";
|
|
114
117
|
const connection = new Connection(rpcUrl, "confirmed");
|
|
115
|
-
const solBalance = await connection.getBalance(
|
|
118
|
+
const solBalance = await connection.getBalance(pacDirect.keypair.publicKey);
|
|
116
119
|
if (solBalance < 5_000_000) {
|
|
117
120
|
console.error(chalk.red(" Insufficient SOL for gas. Need ~0.005 SOL."));
|
|
118
121
|
console.error(chalk.gray(" Tip: Use relayer for gasless deposits (start relayer server)\n"));
|
|
@@ -120,7 +123,7 @@ export function registerFundsCommands(program, getAdapter, isJson, getNetwork) {
|
|
|
120
123
|
}
|
|
121
124
|
const { PublicKey } = await import("@solana/web3.js");
|
|
122
125
|
const USDC_MINT = new PublicKey("EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v");
|
|
123
|
-
const tokenAccounts = await connection.getParsedTokenAccountsByOwner(
|
|
126
|
+
const tokenAccounts = await connection.getParsedTokenAccountsByOwner(pacDirect.keypair.publicKey, { mint: USDC_MINT });
|
|
124
127
|
const usdcBalance = tokenAccounts.value.length > 0
|
|
125
128
|
? tokenAccounts.value[0].account.data.parsed.info.tokenAmount.uiAmount ?? 0
|
|
126
129
|
: 0;
|
|
@@ -128,11 +131,11 @@ export function registerFundsCommands(program, getAdapter, isJson, getNetwork) {
|
|
|
128
131
|
console.error(chalk.red(` Insufficient USDC on Solana. Have: $${formatUsd(usdcBalance)}, need: $${formatUsd(amountNum)}`));
|
|
129
132
|
process.exit(1);
|
|
130
133
|
}
|
|
131
|
-
const ix = await buildDepositInstruction(
|
|
134
|
+
const ix = await buildDepositInstruction(pacDirect.keypair.publicKey, amountNum, network);
|
|
132
135
|
const tx = new Transaction().add(ix);
|
|
133
|
-
tx.feePayer =
|
|
136
|
+
tx.feePayer = pacDirect.keypair.publicKey;
|
|
134
137
|
tx.recentBlockhash = (await connection.getLatestBlockhash()).blockhash;
|
|
135
|
-
tx.sign(
|
|
138
|
+
tx.sign(pacDirect.keypair);
|
|
136
139
|
const sig = await connection.sendRawTransaction(tx.serialize());
|
|
137
140
|
await connection.confirmTransaction(sig, "confirmed");
|
|
138
141
|
logExecution({
|
|
@@ -173,7 +176,13 @@ export function registerFundsCommands(program, getAdapter, isJson, getNetwork) {
|
|
|
173
176
|
console.log(chalk.cyan(`\n Depositing $${formatUsd(amountNum)} via relayer (gasless)...\n`));
|
|
174
177
|
const { ethers } = await import("ethers");
|
|
175
178
|
const { loadPrivateKey } = await import("../config.js");
|
|
176
|
-
|
|
179
|
+
let pk;
|
|
180
|
+
try {
|
|
181
|
+
pk = await loadPrivateKey("hyperliquid");
|
|
182
|
+
}
|
|
183
|
+
catch (err) {
|
|
184
|
+
throw new Error(`Private key not configured for Hyperliquid. Run: perp init`);
|
|
185
|
+
}
|
|
177
186
|
const wallet = new ethers.Wallet(pk);
|
|
178
187
|
try {
|
|
179
188
|
const res = await fetch(`${getRelayerUrl()}/deposit/hyperliquid`, {
|
|
@@ -475,7 +484,7 @@ export function registerFundsCommands(program, getAdapter, isJson, getNetwork) {
|
|
|
475
484
|
if (isNaN(amountNum) || amountNum <= 0)
|
|
476
485
|
throw new Error("Invalid amount");
|
|
477
486
|
const adapter = await getAdapter();
|
|
478
|
-
if (!(adapter
|
|
487
|
+
if (!hasPacificaSdk(adapter) || !isWithdrawCapable(adapter))
|
|
479
488
|
throw new Error("Requires --exchange pacifica");
|
|
480
489
|
const dest = opts.to || adapter.publicKey;
|
|
481
490
|
if (!isJson()) {
|
|
@@ -483,7 +492,7 @@ export function registerFundsCommands(program, getAdapter, isJson, getNetwork) {
|
|
|
483
492
|
console.log(` Destination: ${dest}`);
|
|
484
493
|
}
|
|
485
494
|
try {
|
|
486
|
-
const result = await adapter.
|
|
495
|
+
const result = await adapter.withdraw(String(amountNum), dest);
|
|
487
496
|
logExecution({
|
|
488
497
|
type: "bridge", exchange: "pacifica", symbol: "USDC", side: "withdraw",
|
|
489
498
|
size: String(amountNum), status: "success", dryRun: false,
|
|
@@ -515,7 +524,7 @@ export function registerFundsCommands(program, getAdapter, isJson, getNetwork) {
|
|
|
515
524
|
if (isNaN(amountNum) || amountNum <= 0)
|
|
516
525
|
throw new Error("Invalid amount");
|
|
517
526
|
const adapter = await getAdapter();
|
|
518
|
-
if (!(adapter
|
|
527
|
+
if (adapter.name !== "hyperliquid" || !hasEvmAddress(adapter) || !isWithdrawCapable(adapter))
|
|
519
528
|
throw new Error("Requires --exchange hyperliquid");
|
|
520
529
|
const dest = opts.to || adapter.address;
|
|
521
530
|
if (!isJson()) {
|
|
@@ -562,8 +571,7 @@ export function registerFundsCommands(program, getAdapter, isJson, getNetwork) {
|
|
|
562
571
|
if (isNaN(amountNum) || amountNum <= 0)
|
|
563
572
|
throw new Error("Invalid amount");
|
|
564
573
|
const adapter = await getAdapter();
|
|
565
|
-
|
|
566
|
-
if (!(adapter instanceof LighterAdapter))
|
|
574
|
+
if (!hasLighterAccount(adapter) || !isWithdrawCapable(adapter))
|
|
567
575
|
throw new Error("Requires --exchange lighter");
|
|
568
576
|
if (!isJson()) {
|
|
569
577
|
console.log(chalk.cyan(`\n Withdrawing $${formatUsd(amountNum)} USDC from Lighter...\n`));
|
|
@@ -571,7 +579,7 @@ export function registerFundsCommands(program, getAdapter, isJson, getNetwork) {
|
|
|
571
579
|
console.log(` Address: ${adapter.address}`);
|
|
572
580
|
}
|
|
573
581
|
try {
|
|
574
|
-
const result = await adapter.withdraw(amountNum, parseInt(opts.assetId), parseInt(opts.route));
|
|
582
|
+
const result = await adapter.withdraw(String(amountNum), "", { assetId: parseInt(opts.assetId), routeType: parseInt(opts.route) });
|
|
575
583
|
logExecution({
|
|
576
584
|
type: "bridge", exchange: "lighter", symbol: "USDC", side: "withdraw",
|
|
577
585
|
size: String(amountNum), status: "success", dryRun: false,
|
|
@@ -604,7 +612,7 @@ export function registerFundsCommands(program, getAdapter, isJson, getNetwork) {
|
|
|
604
612
|
if (isNaN(amountNum) || amountNum <= 0)
|
|
605
613
|
throw new Error("Invalid amount");
|
|
606
614
|
const adapter = await getAdapter();
|
|
607
|
-
if (!(adapter
|
|
615
|
+
if (!isUsdTransferCapable(adapter))
|
|
608
616
|
throw new Error("Requires --exchange hyperliquid");
|
|
609
617
|
if (!isJson())
|
|
610
618
|
console.log(chalk.cyan(`\n Transferring $${formatUsd(amountNum)} USDC to ${destination}...\n`));
|
|
@@ -654,8 +662,13 @@ export function registerFundsCommands(program, getAdapter, isJson, getNetwork) {
|
|
|
654
662
|
console.log(chalk.gray(` Check: perp funds bridge-status --hash ${result.messageHash}\n`));
|
|
655
663
|
}
|
|
656
664
|
else {
|
|
665
|
+
if (isJson()) {
|
|
666
|
+
printJson(jsonError("RELAYER_UNAVAILABLE", "CCTP bridge requires relayer server. Start: cd packages/relayer && pnpm start"));
|
|
667
|
+
process.exit(1);
|
|
668
|
+
}
|
|
657
669
|
console.error(chalk.red("\n CCTP bridge requires relayer server."));
|
|
658
670
|
console.error(chalk.gray(" Start: cd packages/relayer && pnpm start\n"));
|
|
671
|
+
process.exit(1);
|
|
659
672
|
}
|
|
660
673
|
});
|
|
661
674
|
funds
|
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
import { Command } from "commander";
|
|
2
|
-
import type { ExchangeAdapter } from "../exchanges/
|
|
2
|
+
import type { ExchangeAdapter } from "../exchanges/index.js";
|
|
3
3
|
export declare function registerHistoryCommands(program: Command, isJson: () => boolean, getAdapterForExchange?: (exchange: string) => Promise<ExchangeAdapter>): void;
|
package/dist/commands/history.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import chalk from "chalk";
|
|
2
2
|
import { printJson, jsonOk, jsonError, makeTable, formatUsd, formatPnl, withJsonErrors } from "../utils.js";
|
|
3
3
|
import { readExecutionLog, getExecutionStats, pruneExecutionLog } from "../execution-log.js";
|
|
4
|
-
import { loadArbState } from "../arb/
|
|
4
|
+
import { loadArbState } from "../arb/index.js";
|
|
5
5
|
import { readPositionHistory, getPositionStats } from "../position-history.js";
|
|
6
6
|
import { saveEquitySnapshot, readEquityHistory, computePnlMetrics, computeDailyPnl, aggregateWeekly, } from "../equity-tracker.js";
|
|
7
7
|
const EXCHANGES = ["pacifica", "hyperliquid", "lighter"];
|
|
@@ -899,8 +899,8 @@ function registerPnlSubcommands(parent, getAdapterForExchange, isJson) {
|
|
|
899
899
|
process.on("SIGINT", () => controller.abort());
|
|
900
900
|
// Initial snapshot
|
|
901
901
|
const snaps = await takeSnapshot(getAdapterForExchange, exchanges);
|
|
902
|
-
|
|
903
|
-
console.log(`${chalk.gray(new Date().toLocaleTimeString())} Total equity: $${formatUsd(
|
|
902
|
+
let prevTotal = snaps.reduce((s, sn) => s + sn.equity, 0);
|
|
903
|
+
console.log(`${chalk.gray(new Date().toLocaleTimeString())} Total equity: $${formatUsd(prevTotal)}`);
|
|
904
904
|
while (!controller.signal.aborted) {
|
|
905
905
|
await new Promise((resolve) => {
|
|
906
906
|
const timer = setTimeout(resolve, intervalMs);
|
|
@@ -911,9 +911,10 @@ function registerPnlSubcommands(parent, getAdapterForExchange, isJson) {
|
|
|
911
911
|
try {
|
|
912
912
|
const s = await takeSnapshot(getAdapterForExchange, exchanges);
|
|
913
913
|
const t = s.reduce((sum, sn) => sum + sn.equity, 0);
|
|
914
|
-
const delta = t -
|
|
914
|
+
const delta = t - prevTotal;
|
|
915
915
|
console.log(`${chalk.gray(new Date().toLocaleTimeString())} ` +
|
|
916
916
|
`Total: $${formatUsd(t)} ${formatPnl(delta)}`);
|
|
917
|
+
prevTotal = t;
|
|
917
918
|
}
|
|
918
919
|
catch (err) {
|
|
919
920
|
console.error(chalk.red(`Snapshot error: ${err instanceof Error ? err.message : err}`));
|
|
@@ -1,4 +1,3 @@
|
|
|
1
1
|
import { Command } from "commander";
|
|
2
|
-
import type { ExchangeAdapter } from "../exchanges/
|
|
3
|
-
|
|
4
|
-
export declare function registerManageCommands(program: Command, getAdapter: () => Promise<ExchangeAdapter>, isJson: () => boolean, getPacificaAdapter: () => PacificaAdapter): void;
|
|
2
|
+
import type { ExchangeAdapter } from "../exchanges/index.js";
|
|
3
|
+
export declare function registerManageCommands(program: Command, getAdapter: () => Promise<ExchangeAdapter>, isJson: () => boolean, getPacificaAdapter: () => unknown): void;
|
package/dist/commands/manage.js
CHANGED
|
@@ -1,15 +1,16 @@
|
|
|
1
|
-
import { PacificaAdapter } from "../exchanges/pacifica.js";
|
|
2
1
|
import { printJson, jsonOk } from "../utils.js";
|
|
3
2
|
import { setEnvVar } from "./init.js";
|
|
4
3
|
import chalk from "chalk";
|
|
4
|
+
import { hasPacificaSdk, hasLighterAccount } from "../exchanges/capabilities.js";
|
|
5
5
|
export function registerManageCommands(program, getAdapter, isJson, getPacificaAdapter) {
|
|
6
6
|
const manage = program.command("manage").description("Exchange account settings (margin, subaccount, API keys, builder)");
|
|
7
7
|
// Ensure adapter is initialized before accessing PacificaAdapter
|
|
8
8
|
async function pac() {
|
|
9
9
|
const adapter = await getAdapter();
|
|
10
|
-
if (!(adapter
|
|
10
|
+
if (!hasPacificaSdk(adapter)) {
|
|
11
11
|
throw new Error("This command requires --exchange pacifica");
|
|
12
12
|
}
|
|
13
|
+
// Cast sdk to any to allow calling Pacifica SDK methods without importing the concrete type
|
|
13
14
|
return adapter;
|
|
14
15
|
}
|
|
15
16
|
manage
|
|
@@ -30,13 +31,8 @@ export function registerManageCommands(program, getAdapter, isJson, getPacificaA
|
|
|
30
31
|
const withdrawCmd = manage
|
|
31
32
|
.command("withdraw <amount> <address>")
|
|
32
33
|
.description("Use 'perp withdraw pacifica <amount>'")
|
|
33
|
-
.action(async (
|
|
34
|
+
.action(async (_amount, _address) => {
|
|
34
35
|
console.log(chalk.yellow("\n Use 'perp withdraw pacifica <amount>' instead.\n"));
|
|
35
|
-
const a = await pac();
|
|
36
|
-
const result = await a.sdk.withdraw({ amount, dest_address: address }, a.publicKey, a.signer);
|
|
37
|
-
if (isJson())
|
|
38
|
-
return printJson(jsonOk(result));
|
|
39
|
-
console.log(chalk.green(`\n Withdrawal of $${amount} to ${address} submitted.\n`));
|
|
40
36
|
});
|
|
41
37
|
withdrawCmd._hidden = true;
|
|
42
38
|
// Subaccounts
|
|
@@ -59,7 +55,7 @@ export function registerManageCommands(program, getAdapter, isJson, getPacificaA
|
|
|
59
55
|
const result = await a.sdk.listSubaccounts(a.publicKey, a.signer);
|
|
60
56
|
if (isJson())
|
|
61
57
|
return printJson(jsonOk(result));
|
|
62
|
-
|
|
58
|
+
console.log(JSON.stringify(result, null, 2));
|
|
63
59
|
});
|
|
64
60
|
sub
|
|
65
61
|
.command("transfer <from> <to> <amount>")
|
|
@@ -91,7 +87,7 @@ export function registerManageCommands(program, getAdapter, isJson, getPacificaA
|
|
|
91
87
|
const result = await a.sdk.listAgentWallets(a.publicKey, a.signer);
|
|
92
88
|
if (isJson())
|
|
93
89
|
return printJson(jsonOk(result));
|
|
94
|
-
|
|
90
|
+
console.log(JSON.stringify(result, null, 2));
|
|
95
91
|
});
|
|
96
92
|
agent
|
|
97
93
|
.command("revoke <wallet>")
|
|
@@ -124,7 +120,6 @@ export function registerManageCommands(program, getAdapter, isJson, getPacificaA
|
|
|
124
120
|
if (isJson())
|
|
125
121
|
return printJson(jsonOk(result));
|
|
126
122
|
console.log(chalk.green(`\n Lake created for ${symbol.toUpperCase()} with $${amount}.\n`));
|
|
127
|
-
printJson(jsonOk(result));
|
|
128
123
|
});
|
|
129
124
|
lake
|
|
130
125
|
.command("deposit <lakeId> <amount>")
|
|
@@ -195,7 +190,7 @@ export function registerManageCommands(program, getAdapter, isJson, getPacificaA
|
|
|
195
190
|
const result = await a.sdk.getBuilderOverview(a.publicKey);
|
|
196
191
|
if (isJson())
|
|
197
192
|
return printJson(jsonOk(result));
|
|
198
|
-
|
|
193
|
+
console.log(JSON.stringify(result, null, 2));
|
|
199
194
|
});
|
|
200
195
|
builder
|
|
201
196
|
.command("trades <code>")
|
|
@@ -205,7 +200,7 @@ export function registerManageCommands(program, getAdapter, isJson, getPacificaA
|
|
|
205
200
|
const result = await a.sdk.getBuilderTrades(code);
|
|
206
201
|
if (isJson())
|
|
207
202
|
return printJson(jsonOk(result));
|
|
208
|
-
|
|
203
|
+
console.log(JSON.stringify(result, null, 2));
|
|
209
204
|
});
|
|
210
205
|
builder
|
|
211
206
|
.command("leaderboard <code>")
|
|
@@ -215,7 +210,7 @@ export function registerManageCommands(program, getAdapter, isJson, getPacificaA
|
|
|
215
210
|
const result = await a.sdk.getBuilderLeaderboard(code);
|
|
216
211
|
if (isJson())
|
|
217
212
|
return printJson(jsonOk(result));
|
|
218
|
-
|
|
213
|
+
console.log(JSON.stringify(result, null, 2));
|
|
219
214
|
});
|
|
220
215
|
builder
|
|
221
216
|
.command("update-fee <code> <feeRate>")
|
|
@@ -250,7 +245,6 @@ export function registerManageCommands(program, getAdapter, isJson, getPacificaA
|
|
|
250
245
|
if (isJson())
|
|
251
246
|
return printJson(jsonOk(result));
|
|
252
247
|
console.log(chalk.green(`\n API key "${name}" created.\n`));
|
|
253
|
-
printJson(jsonOk(result));
|
|
254
248
|
});
|
|
255
249
|
apikey
|
|
256
250
|
.command("list")
|
|
@@ -260,7 +254,7 @@ export function registerManageCommands(program, getAdapter, isJson, getPacificaA
|
|
|
260
254
|
const result = await a.sdk.listApiKeys(a.publicKey, a.signer);
|
|
261
255
|
if (isJson())
|
|
262
256
|
return printJson(jsonOk(result));
|
|
263
|
-
|
|
257
|
+
console.log(JSON.stringify(result, null, 2));
|
|
264
258
|
});
|
|
265
259
|
apikey
|
|
266
260
|
.command("revoke <key>")
|
|
@@ -279,8 +273,7 @@ export function registerManageCommands(program, getAdapter, isJson, getPacificaA
|
|
|
279
273
|
.option("--key-index <n>", "API key index (4-254, default: 4)", "4")
|
|
280
274
|
.action(async (opts) => {
|
|
281
275
|
const adapter = await getAdapter();
|
|
282
|
-
|
|
283
|
-
if (!(adapter instanceof LighterAdapter)) {
|
|
276
|
+
if (!hasLighterAccount(adapter)) {
|
|
284
277
|
throw new Error("This command requires --exchange lighter");
|
|
285
278
|
}
|
|
286
279
|
const keyIndex = parseInt(opts.keyIndex);
|
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
import { Command } from "commander";
|
|
2
|
-
import type { ExchangeAdapter } from "../exchanges/
|
|
2
|
+
import type { ExchangeAdapter } from "../exchanges/index.js";
|
|
3
3
|
export declare function registerMarketCommands(program: Command, getAdapter: () => Promise<ExchangeAdapter>, isJson: () => boolean, getAdapterForExchange?: (exchange: string) => Promise<ExchangeAdapter>): void;
|
package/dist/commands/market.js
CHANGED
|
@@ -1,7 +1,6 @@
|
|
|
1
|
-
import { PacificaAdapter } from "../exchanges/pacifica.js";
|
|
2
|
-
import { HyperliquidAdapter } from "../exchanges/hyperliquid.js";
|
|
3
1
|
import { makeTable, formatUsd, formatPercent, printJson, jsonOk, jsonError, withJsonErrors } from "../utils.js";
|
|
4
2
|
import chalk from "chalk";
|
|
3
|
+
import { hasPacificaSdk, isDexCapable } from "../exchanges/capabilities.js";
|
|
5
4
|
const EXCHANGES = ["pacifica", "hyperliquid", "lighter"];
|
|
6
5
|
export function registerMarketCommands(program, getAdapter, isJson, getAdapterForExchange) {
|
|
7
6
|
const market = program.command("market").description("Market data commands");
|
|
@@ -30,7 +29,7 @@ export function registerMarketCommands(program, getAdapter, isJson, getAdapterFo
|
|
|
30
29
|
const adapter = await getAdapterForExchange(ex);
|
|
31
30
|
grouped[ex] = await adapter.getMarkets();
|
|
32
31
|
// --hip3: fetch HIP-3 dex markets
|
|
33
|
-
if (opts.hip3 && ex === "hyperliquid" && adapter
|
|
32
|
+
if (opts.hip3 && ex === "hyperliquid" && isDexCapable(adapter)) {
|
|
34
33
|
const dexes = await adapter.listDeployedDexes();
|
|
35
34
|
await Promise.allSettled(dexes.map(async (d) => {
|
|
36
35
|
const dexAdapter = Object.create(adapter);
|
|
@@ -67,7 +66,7 @@ export function registerMarketCommands(program, getAdapter, isJson, getAdapterFo
|
|
|
67
66
|
const markets = await adapter.getMarkets();
|
|
68
67
|
// --hip3: fetch HIP-3 dex markets
|
|
69
68
|
const hip3 = {};
|
|
70
|
-
if (opts.hip3 && adapter
|
|
69
|
+
if (opts.hip3 && isDexCapable(adapter)) {
|
|
71
70
|
const dexes = await adapter.listDeployedDexes();
|
|
72
71
|
await Promise.allSettled(dexes.map(async (d) => {
|
|
73
72
|
const dexAdapter = Object.create(adapter);
|
|
@@ -127,8 +126,9 @@ export function registerMarketCommands(program, getAdapter, isJson, getAdapterFo
|
|
|
127
126
|
return;
|
|
128
127
|
}
|
|
129
128
|
const adapter = await getAdapter();
|
|
130
|
-
if (adapter
|
|
131
|
-
const
|
|
129
|
+
if (hasPacificaSdk(adapter)) {
|
|
130
|
+
const sdk = adapter.sdk;
|
|
131
|
+
const prices = await sdk.getPrices();
|
|
132
132
|
if (isJson())
|
|
133
133
|
return printJson(jsonOk(prices));
|
|
134
134
|
const rows = prices.map((p) => [
|
|
@@ -351,7 +351,7 @@ export function registerMarketCommands(program, getAdapter, isJson, getAdapterFo
|
|
|
351
351
|
.action(async () => {
|
|
352
352
|
await withJsonErrors(isJson(), async () => {
|
|
353
353
|
const adapter = await getAdapter();
|
|
354
|
-
if (!(adapter
|
|
354
|
+
if (!(isDexCapable(adapter))) {
|
|
355
355
|
if (isJson())
|
|
356
356
|
return printJson(jsonError("INVALID_EXCHANGE", "HIP-3 dexes are only available on Hyperliquid. Use -e hyperliquid."));
|
|
357
357
|
console.error(chalk.red("\n HIP-3 dexes are only available on Hyperliquid. Use -e hyperliquid.\n"));
|
package/dist/commands/plan.d.ts
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
import { Command } from "commander";
|
|
2
|
-
import type { ExchangeAdapter } from "../exchanges/
|
|
2
|
+
import type { ExchangeAdapter } from "../exchanges/index.js";
|
|
3
3
|
export declare function registerPlanCommands(program: Command, getAdapter: () => Promise<ExchangeAdapter>, isJson: () => boolean): void;
|
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
import { Command } from "commander";
|
|
2
|
-
import type { ExchangeAdapter } from "../exchanges/
|
|
2
|
+
import type { ExchangeAdapter } from "../exchanges/index.js";
|
|
3
3
|
export declare function registerRebalanceCommands(program: Command, getAdapterForExchange: (exchange: string) => Promise<ExchangeAdapter>, isJson: () => boolean): void;
|
|
@@ -229,29 +229,28 @@ export function registerRebalanceCommands(program, getAdapterForExchange, isJson
|
|
|
229
229
|
* Execute a withdrawal from a source exchange.
|
|
230
230
|
*/
|
|
231
231
|
async function executeWithdraw(move, adapters) {
|
|
232
|
+
const { hasPacificaSdk, isWithdrawCapable, hasEvmAddress } = await import("../exchanges/capabilities.js");
|
|
232
233
|
const adapter = adapters.get(move.from);
|
|
233
234
|
if (!adapter)
|
|
234
235
|
throw new Error(`No adapter for ${move.from}`);
|
|
235
|
-
switch (
|
|
236
|
+
switch (adapter.name) {
|
|
236
237
|
case "pacifica": {
|
|
237
|
-
|
|
238
|
-
if (!(adapter instanceof PacificaAdapter))
|
|
238
|
+
if (!hasPacificaSdk(adapter))
|
|
239
239
|
throw new Error("Invalid adapter");
|
|
240
|
-
|
|
240
|
+
const sdk = adapter.sdk;
|
|
241
|
+
await sdk.withdraw({ amount: String(move.amount), dest_address: adapter.publicKey }, adapter.publicKey, adapter.signer);
|
|
241
242
|
break;
|
|
242
243
|
}
|
|
243
244
|
case "hyperliquid": {
|
|
244
|
-
|
|
245
|
-
if (!(adapter instanceof HyperliquidAdapter))
|
|
245
|
+
if (!isWithdrawCapable(adapter) || !hasEvmAddress(adapter))
|
|
246
246
|
throw new Error("Invalid adapter");
|
|
247
247
|
await adapter.withdraw(String(move.amount), adapter.address);
|
|
248
248
|
break;
|
|
249
249
|
}
|
|
250
250
|
case "lighter": {
|
|
251
|
-
|
|
252
|
-
if (!(adapter instanceof LighterAdapter))
|
|
251
|
+
if (!isWithdrawCapable(adapter))
|
|
253
252
|
throw new Error("Invalid adapter");
|
|
254
|
-
await adapter.withdraw(move.amount);
|
|
253
|
+
await adapter.withdraw(String(move.amount), "");
|
|
255
254
|
break;
|
|
256
255
|
}
|
|
257
256
|
default:
|
package/dist/commands/risk.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { Command } from "commander";
|
|
2
|
-
import type { ExchangeAdapter } from "../exchanges/
|
|
2
|
+
import type { ExchangeAdapter } from "../exchanges/index.js";
|
|
3
3
|
/** Run health check and return results + render. Exported for use by status --health. */
|
|
4
4
|
export declare function runHealthCheck(isJson: () => boolean): Promise<void>;
|
|
5
5
|
export declare function registerRiskCommands(program: Command, getAdapterForExchange: (exchange: string) => Promise<ExchangeAdapter>, isJson: () => boolean): void;
|
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
import { Command } from "commander";
|
|
2
|
-
import type { ExchangeAdapter } from "../exchanges/
|
|
2
|
+
import type { ExchangeAdapter } from "../exchanges/index.js";
|
|
3
3
|
export declare function registerSettingsCommands(program: Command, isJson: () => boolean, getAdapterForExchange?: (exchange: string) => Promise<ExchangeAdapter>): void;
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import chalk from "chalk";
|
|
2
|
-
import { printJson, jsonOk, withJsonErrors } from "../utils.js";
|
|
2
|
+
import { printJson, jsonOk, jsonError, withJsonErrors } from "../utils.js";
|
|
3
3
|
import { loadSettings, saveSettings } from "../settings.js";
|
|
4
4
|
import { ENV_FILE, loadEnvFile, setEnvVar, EXCHANGE_ENV_MAP, validateKey } from "./init.js";
|
|
5
5
|
// Resolve exchange alias → env var key
|
|
@@ -80,6 +80,8 @@ export function registerSettingsCommands(program, isJson, getAdapterForExchange)
|
|
|
80
80
|
console.log(chalk.yellow("\n Referrals disabled. No codes will be sent.\n"));
|
|
81
81
|
}
|
|
82
82
|
else {
|
|
83
|
+
if (isJson())
|
|
84
|
+
return printJson(jsonError("INVALID_ARGS", `Invalid action "${action}". Usage: perp settings referrals <on|off>`));
|
|
83
85
|
console.error(chalk.red(`\n Usage: perp settings referrals <on|off>\n`));
|
|
84
86
|
}
|
|
85
87
|
});
|
package/dist/commands/trade.d.ts
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
import { Command } from "commander";
|
|
2
|
-
import type { ExchangeAdapter } from "../exchanges/
|
|
2
|
+
import type { ExchangeAdapter } from "../exchanges/index.js";
|
|
3
3
|
export declare function registerTradeCommands(program: Command, getAdapter: () => Promise<ExchangeAdapter>, isJson: () => boolean, isDryRun?: () => boolean, getAdapterForExchange?: (exchange: string) => Promise<ExchangeAdapter>): void;
|