httpcat-cli 0.3.0 → 0.3.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.
Files changed (322) hide show
  1. package/.github/workflows/ci.yml +3 -0
  2. package/.github/workflows/rc-publish.yml +6 -0
  3. package/.github/workflows/release.yml +102 -0
  4. package/.github/workflows/sync-version.yml +31 -2
  5. package/README.md +1408 -109
  6. package/additions.txt +3 -0
  7. package/bun.lock +260 -25
  8. package/dist/agent/autonomous-trader.d.ts.map +1 -0
  9. package/dist/agent/autonomous-trader.js +362 -0
  10. package/dist/agent/autonomous-trader.js.map +1 -0
  11. package/dist/agent/ax-agent.d.ts.map +1 -1
  12. package/dist/agent/ax-agent.js +356 -18
  13. package/dist/agent/ax-agent.js.map +1 -1
  14. package/dist/agent/event-client.d.ts.map +1 -0
  15. package/dist/agent/event-client.js +82 -0
  16. package/dist/agent/event-client.js.map +1 -0
  17. package/dist/agent/log-stream.d.ts.map +1 -0
  18. package/dist/agent/log-stream.js +95 -0
  19. package/dist/agent/log-stream.js.map +1 -0
  20. package/dist/agent/memory/conversation-session.d.ts.map +1 -0
  21. package/dist/agent/memory/conversation-session.js +232 -0
  22. package/dist/agent/memory/conversation-session.js.map +1 -0
  23. package/dist/agent/memory/conversation-store.d.ts.map +1 -0
  24. package/dist/agent/memory/conversation-store.js +214 -0
  25. package/dist/agent/memory/conversation-store.js.map +1 -0
  26. package/dist/agent/memory/database-schema.d.ts.map +1 -0
  27. package/dist/agent/memory/database-schema.js +355 -0
  28. package/dist/agent/memory/database-schema.js.map +1 -0
  29. package/dist/agent/memory/decision-tracker.d.ts.map +1 -0
  30. package/dist/agent/memory/decision-tracker.js +274 -0
  31. package/dist/agent/memory/decision-tracker.js.map +1 -0
  32. package/dist/agent/memory/memory-manager.d.ts.map +1 -0
  33. package/dist/agent/memory/memory-manager.js +187 -0
  34. package/dist/agent/memory/memory-manager.js.map +1 -0
  35. package/dist/agent/memory/types.d.ts.map +1 -0
  36. package/dist/agent/memory/types.js +5 -0
  37. package/dist/agent/memory/types.js.map +1 -0
  38. package/dist/agent/message-formatter.d.ts.map +1 -0
  39. package/dist/agent/message-formatter.js +76 -0
  40. package/dist/agent/message-formatter.js.map +1 -0
  41. package/dist/agent/position-db.d.ts.map +1 -0
  42. package/dist/agent/position-db.js +154 -0
  43. package/dist/agent/position-db.js.map +1 -0
  44. package/dist/agent/simple-chat-ui-static.d.ts.map +1 -0
  45. package/dist/agent/simple-chat-ui-static.js +129 -0
  46. package/dist/agent/simple-chat-ui-static.js.map +1 -0
  47. package/dist/agent/simple-chat-ui.d.ts.map +1 -0
  48. package/dist/agent/simple-chat-ui.js +90 -0
  49. package/dist/agent/simple-chat-ui.js.map +1 -0
  50. package/dist/agent/tools.d.ts.map +1 -1
  51. package/dist/agent/tools.js +297 -4
  52. package/dist/agent/tools.js.map +1 -1
  53. package/dist/agent/ui.d.ts.map +1 -0
  54. package/dist/agent/ui.js +84 -0
  55. package/dist/agent/ui.js.map +1 -0
  56. package/dist/agent/unified-runtime.d.ts.map +1 -0
  57. package/dist/agent/unified-runtime.js +397 -0
  58. package/dist/agent/unified-runtime.js.map +1 -0
  59. package/dist/client.d.ts.map +1 -1
  60. package/dist/client.js +272 -21
  61. package/dist/client.js.map +1 -1
  62. package/dist/commands/account.d.ts.map +1 -1
  63. package/dist/commands/account.js +187 -33
  64. package/dist/commands/account.js.map +1 -1
  65. package/dist/commands/agent.d.ts.map +1 -0
  66. package/dist/commands/agent.js +125 -0
  67. package/dist/commands/agent.js.map +1 -0
  68. package/dist/commands/approve.d.ts.map +1 -0
  69. package/dist/commands/approve.js +505 -0
  70. package/dist/commands/approve.js.map +1 -0
  71. package/dist/commands/automation.d.ts.map +1 -0
  72. package/dist/commands/automation.js +346 -0
  73. package/dist/commands/automation.js.map +1 -0
  74. package/dist/commands/balances.d.ts.map +1 -1
  75. package/dist/commands/balances.js +226 -73
  76. package/dist/commands/balances.js.map +1 -1
  77. package/dist/commands/buy.d.ts.map +1 -1
  78. package/dist/commands/buy.js +149 -146
  79. package/dist/commands/buy.js.map +1 -1
  80. package/dist/commands/call.d.ts.map +1 -0
  81. package/dist/commands/call.js +51 -0
  82. package/dist/commands/call.js.map +1 -0
  83. package/dist/commands/cex.d.ts.map +1 -0
  84. package/dist/commands/cex.js +958 -0
  85. package/dist/commands/cex.js.map +1 -0
  86. package/dist/commands/chat.d.ts.map +1 -1
  87. package/dist/commands/chat.js +169 -411
  88. package/dist/commands/chat.js.map +1 -1
  89. package/dist/commands/claim.d.ts.map +1 -1
  90. package/dist/commands/claim.js +313 -29
  91. package/dist/commands/claim.js.map +1 -1
  92. package/dist/commands/create.d.ts.map +1 -1
  93. package/dist/commands/create.js +151 -43
  94. package/dist/commands/create.js.map +1 -1
  95. package/dist/commands/gasless-swap.d.ts.map +1 -0
  96. package/dist/commands/gasless-swap.js +232 -0
  97. package/dist/commands/gasless-swap.js.map +1 -0
  98. package/dist/commands/health.d.ts.map +1 -1
  99. package/dist/commands/health.js +63 -7
  100. package/dist/commands/health.js.map +1 -1
  101. package/dist/commands/info.d.ts.map +1 -1
  102. package/dist/commands/info.js +131 -47
  103. package/dist/commands/info.js.map +1 -1
  104. package/dist/commands/launchpad.d.ts.map +1 -0
  105. package/dist/commands/launchpad.js +708 -0
  106. package/dist/commands/launchpad.js.map +1 -0
  107. package/dist/commands/list.d.ts.map +1 -1
  108. package/dist/commands/list.js +57 -23
  109. package/dist/commands/list.js.map +1 -1
  110. package/dist/commands/market.d.ts.map +1 -0
  111. package/dist/commands/market.js +960 -0
  112. package/dist/commands/market.js.map +1 -0
  113. package/dist/commands/mcp-install.d.ts.map +1 -0
  114. package/dist/commands/mcp-install.js +387 -0
  115. package/dist/commands/mcp-install.js.map +1 -0
  116. package/dist/commands/opps.d.ts.map +1 -0
  117. package/dist/commands/opps.js +409 -0
  118. package/dist/commands/opps.js.map +1 -0
  119. package/dist/commands/perps.d.ts.map +1 -0
  120. package/dist/commands/perps.js +248 -0
  121. package/dist/commands/perps.js.map +1 -0
  122. package/dist/commands/portfolio.d.ts.map +1 -0
  123. package/dist/commands/portfolio.js +679 -0
  124. package/dist/commands/portfolio.js.map +1 -0
  125. package/dist/commands/positions.d.ts.map +1 -1
  126. package/dist/commands/positions.js +76 -47
  127. package/dist/commands/positions.js.map +1 -1
  128. package/dist/commands/predict.d.ts.map +1 -0
  129. package/dist/commands/predict.js +280 -0
  130. package/dist/commands/predict.js.map +1 -0
  131. package/dist/commands/predictions.d.ts.map +1 -0
  132. package/dist/commands/predictions.js +486 -0
  133. package/dist/commands/predictions.js.map +1 -0
  134. package/dist/commands/risk.d.ts.map +1 -0
  135. package/dist/commands/risk.js +225 -0
  136. package/dist/commands/risk.js.map +1 -0
  137. package/dist/commands/security.d.ts.map +1 -0
  138. package/dist/commands/security.js +244 -0
  139. package/dist/commands/security.js.map +1 -0
  140. package/dist/commands/sell.d.ts.map +1 -1
  141. package/dist/commands/sell.js +67 -34
  142. package/dist/commands/sell.js.map +1 -1
  143. package/dist/commands/send.d.ts.map +1 -0
  144. package/dist/commands/send.js +733 -0
  145. package/dist/commands/send.js.map +1 -0
  146. package/dist/commands/sign.d.ts.map +1 -0
  147. package/dist/commands/sign.js +1048 -0
  148. package/dist/commands/sign.js.map +1 -0
  149. package/dist/commands/swap.d.ts.map +1 -0
  150. package/dist/commands/swap.js +744 -0
  151. package/dist/commands/swap.js.map +1 -0
  152. package/dist/commands/system.d.ts.map +1 -0
  153. package/dist/commands/system.js +417 -0
  154. package/dist/commands/system.js.map +1 -0
  155. package/dist/commands/tools/index.d.ts.map +1 -0
  156. package/dist/commands/tools/index.js +2040 -0
  157. package/dist/commands/tools/index.js.map +1 -0
  158. package/dist/commands/trade.d.ts.map +1 -0
  159. package/dist/commands/trade.js +237 -0
  160. package/dist/commands/trade.js.map +1 -0
  161. package/dist/commands/transactions.d.ts.map +1 -1
  162. package/dist/commands/transactions.js +29 -17
  163. package/dist/commands/transactions.js.map +1 -1
  164. package/dist/commands/update.d.ts.map +1 -0
  165. package/dist/commands/update.js +429 -0
  166. package/dist/commands/update.js.map +1 -0
  167. package/dist/config.d.ts.map +1 -1
  168. package/dist/config.js +351 -40
  169. package/dist/config.js.map +1 -1
  170. package/dist/index.js +4524 -924
  171. package/dist/index.js.map +1 -1
  172. package/dist/interactive/art.d.ts.map +1 -1
  173. package/dist/interactive/art.js +33 -1
  174. package/dist/interactive/art.js.map +1 -1
  175. package/dist/interactive/shell.d.ts.map +1 -1
  176. package/dist/interactive/shell.js +467 -2652
  177. package/dist/interactive/shell.js.map +1 -1
  178. package/dist/mcp/context.d.ts.map +1 -0
  179. package/dist/mcp/context.js +211 -0
  180. package/dist/mcp/context.js.map +1 -0
  181. package/dist/mcp/onboarding.d.ts.map +1 -0
  182. package/dist/mcp/onboarding.js +266 -0
  183. package/dist/mcp/onboarding.js.map +1 -0
  184. package/dist/mcp/resources.d.ts.map +1 -0
  185. package/dist/mcp/resources.js +222 -0
  186. package/dist/mcp/resources.js.map +1 -0
  187. package/dist/mcp/server.d.ts.map +1 -1
  188. package/dist/mcp/server.js +51 -1
  189. package/dist/mcp/server.js.map +1 -1
  190. package/dist/mcp/tools.d.ts.map +1 -1
  191. package/dist/mcp/tools.js +4119 -169
  192. package/dist/mcp/tools.js.map +1 -1
  193. package/dist/mcp/types.d.ts.map +1 -1
  194. package/dist/types/agent-info.d.ts.map +1 -0
  195. package/dist/types/agent-info.js +11 -0
  196. package/dist/types/agent-info.js.map +1 -0
  197. package/dist/ui/components/ScrollableList.d.ts.map +1 -0
  198. package/dist/ui/components/ScrollableList.js +72 -0
  199. package/dist/ui/components/ScrollableList.js.map +1 -0
  200. package/dist/ui/components/ThemeProvider.d.ts.map +1 -0
  201. package/dist/ui/components/ThemeProvider.js +87 -0
  202. package/dist/ui/components/ThemeProvider.js.map +1 -0
  203. package/dist/ui/components/ThemedBox.d.ts.map +1 -0
  204. package/dist/ui/components/ThemedBox.js +24 -0
  205. package/dist/ui/components/ThemedBox.js.map +1 -0
  206. package/dist/ui/components/agent/ChatHeader.d.ts.map +1 -0
  207. package/dist/ui/components/agent/ChatHeader.js +39 -0
  208. package/dist/ui/components/agent/ChatHeader.js.map +1 -0
  209. package/dist/ui/components/agent/Header.d.ts.map +1 -0
  210. package/dist/ui/components/agent/Header.js +14 -0
  211. package/dist/ui/components/agent/Header.js.map +1 -0
  212. package/dist/ui/components/agent/Input.d.ts.map +1 -0
  213. package/dist/ui/components/agent/Input.js +23 -0
  214. package/dist/ui/components/agent/Input.js.map +1 -0
  215. package/dist/ui/components/agent/Output.d.ts.map +1 -0
  216. package/dist/ui/components/agent/Output.js +23 -0
  217. package/dist/ui/components/agent/Output.js.map +1 -0
  218. package/dist/ui/components/chat/TokenChatUI.d.ts.map +1 -0
  219. package/dist/ui/components/chat/TokenChatUI.js +133 -0
  220. package/dist/ui/components/chat/TokenChatUI.js.map +1 -0
  221. package/dist/ui/components/shell/ShellHeader.d.ts.map +1 -0
  222. package/dist/ui/components/shell/ShellHeader.js +31 -0
  223. package/dist/ui/components/shell/ShellHeader.js.map +1 -0
  224. package/dist/ui/components/shell/ShellInput.d.ts.map +1 -0
  225. package/dist/ui/components/shell/ShellInput.js +151 -0
  226. package/dist/ui/components/shell/ShellInput.js.map +1 -0
  227. package/dist/ui/components/shell/ShellOutput.d.ts.map +1 -0
  228. package/dist/ui/components/shell/ShellOutput.js +8 -0
  229. package/dist/ui/components/shell/ShellOutput.js.map +1 -0
  230. package/dist/ui/hooks/useChatWebSocket.d.ts.map +1 -0
  231. package/dist/ui/hooks/useChatWebSocket.js +76 -0
  232. package/dist/ui/hooks/useChatWebSocket.js.map +1 -0
  233. package/dist/ui/hooks/useCommandHistory.d.ts.map +1 -0
  234. package/dist/ui/hooks/useCommandHistory.js +70 -0
  235. package/dist/ui/hooks/useCommandHistory.js.map +1 -0
  236. package/dist/ui/hooks/useDebounce.d.ts.map +1 -0
  237. package/dist/ui/hooks/useDebounce.js +17 -0
  238. package/dist/ui/hooks/useDebounce.js.map +1 -0
  239. package/dist/ui/hooks/useLogStream.d.ts.map +1 -0
  240. package/dist/ui/hooks/useLogStream.js +20 -0
  241. package/dist/ui/hooks/useLogStream.js.map +1 -0
  242. package/dist/ui/hooks/useVirtualScroll.d.ts.map +1 -0
  243. package/dist/ui/hooks/useVirtualScroll.js +70 -0
  244. package/dist/ui/hooks/useVirtualScroll.js.map +1 -0
  245. package/dist/utils/admin.d.ts.map +1 -0
  246. package/dist/utils/admin.js +144 -0
  247. package/dist/utils/admin.js.map +1 -0
  248. package/dist/utils/autoSetup.d.ts.map +1 -0
  249. package/dist/utils/autoSetup.js +252 -0
  250. package/dist/utils/autoSetup.js.map +1 -0
  251. package/dist/utils/build-constants.d.ts.map +1 -0
  252. package/dist/utils/build-constants.js +10 -0
  253. package/dist/utils/build-constants.js.map +1 -0
  254. package/dist/utils/constants.d.ts.map +1 -1
  255. package/dist/utils/errors.d.ts.map +1 -1
  256. package/dist/utils/errors.js +10 -1
  257. package/dist/utils/errors.js.map +1 -1
  258. package/dist/utils/formatting.d.ts.map +1 -1
  259. package/dist/utils/formatting.js +46 -9
  260. package/dist/utils/formatting.js.map +1 -1
  261. package/dist/utils/llm-cli-config.d.ts.map +1 -0
  262. package/dist/utils/llm-cli-config.js +963 -0
  263. package/dist/utils/llm-cli-config.js.map +1 -0
  264. package/dist/utils/llm-cli-detector.d.ts.map +1 -0
  265. package/dist/utils/llm-cli-detector.js +202 -0
  266. package/dist/utils/llm-cli-detector.js.map +1 -0
  267. package/dist/utils/loading.d.ts.map +1 -1
  268. package/dist/utils/loading.js +25 -3
  269. package/dist/utils/loading.js.map +1 -1
  270. package/dist/utils/maintenance.d.ts.map +1 -0
  271. package/dist/utils/maintenance.js +17 -0
  272. package/dist/utils/maintenance.js.map +1 -0
  273. package/dist/utils/mcp-config.d.ts.map +1 -0
  274. package/dist/utils/mcp-config.js +77 -0
  275. package/dist/utils/mcp-config.js.map +1 -0
  276. package/dist/utils/privateKeyPrompt.d.ts.map +1 -1
  277. package/dist/utils/privateKeyPrompt.js +308 -129
  278. package/dist/utils/privateKeyPrompt.js.map +1 -1
  279. package/dist/utils/process-cleanup.d.ts.map +1 -0
  280. package/dist/utils/process-cleanup.js +136 -0
  281. package/dist/utils/process-cleanup.js.map +1 -0
  282. package/dist/utils/retry.d.ts.map +1 -0
  283. package/dist/utils/retry.js +56 -0
  284. package/dist/utils/retry.js.map +1 -0
  285. package/dist/utils/rpc-helpers.d.ts.map +1 -0
  286. package/dist/utils/rpc-helpers.js +70 -0
  287. package/dist/utils/rpc-helpers.js.map +1 -0
  288. package/dist/utils/rpc-transport.d.ts.map +1 -0
  289. package/dist/utils/rpc-transport.js +87 -0
  290. package/dist/utils/rpc-transport.js.map +1 -0
  291. package/dist/utils/shell-setup.d.ts.map +1 -0
  292. package/dist/utils/shell-setup.js +531 -0
  293. package/dist/utils/shell-setup.js.map +1 -0
  294. package/dist/utils/status.d.ts.map +1 -1
  295. package/dist/utils/status.js +34 -5
  296. package/dist/utils/status.js.map +1 -1
  297. package/dist/utils/token-resolver.d.ts.map +1 -1
  298. package/dist/utils/token-resolver.js +51 -8
  299. package/dist/utils/token-resolver.js.map +1 -1
  300. package/dist/utils/x402-caller.d.ts.map +1 -0
  301. package/dist/utils/x402-caller.js +17 -0
  302. package/dist/utils/x402-caller.js.map +1 -0
  303. package/docs/README.md +28 -0
  304. package/docs/agent/README.md +18 -0
  305. package/docs/api/README.md +41 -0
  306. package/docs/cli/README.md +42 -0
  307. package/docs/guides/README.md +26 -0
  308. package/docs/implementation/README.md +18 -0
  309. package/docs/planning/README.md +19 -0
  310. package/docs/testing/README.md +15 -0
  311. package/docs/ux/README.md +16 -0
  312. package/issues.txt +2 -0
  313. package/package.json +24 -9
  314. package/scripts/cat-spin.sh +417 -0
  315. package/scripts/deprecate-rc-versions.js +58 -0
  316. package/scripts/inject-build-constants.js +43 -0
  317. package/scripts/monitor-foobar.js +117 -0
  318. package/swap.logs +61 -0
  319. package/swapping.txt +108 -0
  320. package/test.txt +12 -0
  321. package/tests/fixtures/test-data.json +16 -0
  322. package/Screenshot 2025-12-21 at 8.56.02/342/200/257PM.png +0 -0
@@ -0,0 +1,708 @@
1
+ import { Command } from "commander";
2
+ import { HttpcatClient } from "../client.js";
3
+ import { config } from "../config.js";
4
+ import { randomUUID } from "crypto";
5
+ import chalk from "chalk";
6
+ import { privateKeyToAccount } from "viem/accounts";
7
+ // Import command functions
8
+ import { createToken, displayCreateResult, processPhotoUrl, isFilePath, } from "./create.js";
9
+ import { buyToken, displayBuyResult, displayBuyResultCompact, } from "./buy.js";
10
+ import { sellToken, displaySellResult } from "./sell.js";
11
+ import { listTokens, displayTokenList } from "./list.js";
12
+ import { getTokenInfo, displayTokenInfo } from "./info.js";
13
+ import { getPositions, displayPositions } from "./positions.js";
14
+ import { viewFees, claimFees, displayFees, displayClaimResult, getUserCreatedTokens, getAllTokenFees, displayAllFees, displayTokenCreationGuide, claimAllFees, } from "./claim.js";
15
+ // Import utilities
16
+ import { withLoading } from "../utils/loading.js";
17
+ import { outputJson, outputError } from "../headless/json-output.js";
18
+ import { handleError, getExitCode } from "../utils/errors.js";
19
+ import { promptForPrivateKey } from "../utils/privateKeyPrompt.js";
20
+ // ============================================================================
21
+ // Shared Utilities (duplicated from index.ts to avoid circular dependencies)
22
+ // ============================================================================
23
+ function getPrivateKey(cliPrivateKey, accountIndex) {
24
+ if (cliPrivateKey)
25
+ return cliPrivateKey;
26
+ const envKey = process.env.HTTPCAT_PRIVATE_KEY;
27
+ if (envKey)
28
+ return envKey;
29
+ // Use account system
30
+ try {
31
+ const index = accountIndex !== undefined
32
+ ? accountIndex
33
+ : config.getActiveAccountIndex();
34
+ return config.getAccountPrivateKey(index);
35
+ }
36
+ catch (error) {
37
+ // Fall back to legacy format if account system not set up
38
+ return config.get("privateKey");
39
+ }
40
+ }
41
+ function isConfigured(cliPrivateKey) {
42
+ if (cliPrivateKey)
43
+ return true;
44
+ return config.isConfigured();
45
+ }
46
+ async function ensureWalletUnlocked() {
47
+ const password = config.getPassword();
48
+ if (!password) {
49
+ // No password required - ensure session is initialized
50
+ config.ensureSessionValid();
51
+ return;
52
+ }
53
+ if (!config.isSessionValid()) {
54
+ // Need to prompt for password
55
+ const inquirer = (await import("inquirer")).default;
56
+ const answers = await inquirer.prompt([
57
+ {
58
+ type: "password",
59
+ name: "password",
60
+ message: "Enter password to unlock wallet:",
61
+ mask: "•",
62
+ },
63
+ ]);
64
+ await config.unlockSession(answers.password);
65
+ }
66
+ }
67
+ // ============================================================================
68
+ // Launchpad Command Group
69
+ // ============================================================================
70
+ export function createLaunchpadCommand() {
71
+ const launchpadCommand = new Command("launchpad")
72
+ .description("402.cat Launchpad operations (bonding curve tokens)")
73
+ .addHelpText("after", `
74
+ Examples:
75
+ httpcat launchpad create "My Token" "MTK"
76
+ httpcat launchpad buy MTK 0.10
77
+ httpcat launchpad sell MTK 50%
78
+ httpcat launchpad list --sort mcap
79
+ httpcat launchpad info MTK
80
+ httpcat launchpad positions
81
+ httpcat launchpad claim view MTK
82
+ httpcat launchpad claim execute MTK --execute
83
+ `);
84
+ // Create subcommand
85
+ launchpadCommand
86
+ .command("create")
87
+ .alias("new")
88
+ .description("Create a new launchpad token ($0.01)")
89
+ .argument("<name>", 'Token name (e.g., "My Token")')
90
+ .argument("<symbol>", 'Token symbol/ticker (e.g., "MTK", 3-10 characters)')
91
+ .option("-p, --photo <url|path>", "Photo URL or file path for token logo")
92
+ .option("-w, --website <url>", "Website URL")
93
+ .addHelpText("after", `
94
+ Examples:
95
+ httpcat launchpad create "My Token" "MTK"
96
+ httpcat launchpad create "Moon Cat" "MOON" --website https://mooncat.io
97
+ httpcat launchpad create "Test" "TEST" --photo https://example.com/logo.png
98
+ httpcat launchpad create "Test" "TEST" --photo ./logo.png
99
+ `)
100
+ .action(async (name, symbol, options, command) => {
101
+ try {
102
+ // Fallback: get arguments from command object if not provided as parameters
103
+ const args = command.processedArgs || command.args || [];
104
+ const actualName = name || args[0];
105
+ const actualSymbol = symbol || args[1];
106
+ // Validate required arguments
107
+ if (!actualName || typeof actualName !== "string") {
108
+ throw new Error("Token name is required. Usage: httpcat launchpad create <name> <symbol> [options]");
109
+ }
110
+ if (!actualSymbol || typeof actualSymbol !== "string") {
111
+ throw new Error("Token symbol is required. Usage: httpcat launchpad create <name> <symbol> [options]");
112
+ }
113
+ const globalOpts = command.parent?.parent?.opts() || {};
114
+ const accountIndex = globalOpts.account;
115
+ // Ensure wallet is unlocked
116
+ await ensureWalletUnlocked();
117
+ let privateKey = getPrivateKey(globalOpts.privateKey, accountIndex);
118
+ // If not configured and not in JSON mode, prompt interactively
119
+ if (!isConfigured(globalOpts.privateKey)) {
120
+ if (globalOpts.json) {
121
+ console.error('❌ Not configured. Run "httpcat config" first or use --private-key flag.');
122
+ process.exit(2);
123
+ }
124
+ // Interactive prompt for private key
125
+ privateKey = await promptForPrivateKey();
126
+ }
127
+ const client = await HttpcatClient.create(privateKey);
128
+ // Generate default robohash URL if no photo provided
129
+ let photoToUse = options.photo;
130
+ if (!photoToUse) {
131
+ const uuid = randomUUID();
132
+ photoToUse = `https://robohash.org/${uuid}?set=set4`;
133
+ }
134
+ // Process photo if it's a file path (show loading state)
135
+ let processedPhotoUrl = photoToUse;
136
+ if (photoToUse && isFilePath(photoToUse)) {
137
+ processedPhotoUrl = await withLoading(async () => processPhotoUrl(photoToUse), {
138
+ message: "Uploading image...",
139
+ json: globalOpts.json,
140
+ quiet: globalOpts.quiet,
141
+ spinner: "cat",
142
+ clearOnSuccess: true,
143
+ });
144
+ }
145
+ // Create token (show loading state)
146
+ const result = await withLoading(() => createToken(client, {
147
+ name: actualName.trim(),
148
+ symbol: actualSymbol.trim(),
149
+ photoUrl: processedPhotoUrl,
150
+ websiteUrl: options.website,
151
+ }), {
152
+ message: "Creating token...",
153
+ json: globalOpts.json,
154
+ quiet: globalOpts.quiet,
155
+ spinner: "cat",
156
+ clearOnSuccess: true,
157
+ });
158
+ if (globalOpts.json) {
159
+ outputJson("create_token", result);
160
+ }
161
+ else if (!globalOpts.quiet) {
162
+ displayCreateResult(result);
163
+ }
164
+ process.exit(0);
165
+ }
166
+ catch (error) {
167
+ const globalOpts = command.parent?.parent?.opts() || {};
168
+ // Handle errors normally - show the actual error from the backend
169
+ if (globalOpts.json) {
170
+ outputError("create_token", error, getExitCode(error));
171
+ }
172
+ else {
173
+ handleError(error, globalOpts.verbose);
174
+ }
175
+ process.exit(getExitCode(error));
176
+ }
177
+ });
178
+ // Buy subcommand
179
+ launchpadCommand
180
+ .command("buy")
181
+ .alias("b")
182
+ .description("Buy tokens from bonding curve")
183
+ .argument("<identifier>", "Token identifier (address, symbol, or ID)")
184
+ .argument("<amount>", "Amount to buy (ETH/USDC)")
185
+ .option("-r, --repeat <count>", "Execute multiple buys in sequence", parseInt)
186
+ .option("-d, --delay <ms>", "Delay between repeated buys (milliseconds)", parseInt)
187
+ .addHelpText("after", `
188
+ Examples:
189
+ httpcat launchpad buy MTK 0.10
190
+ httpcat launchpad buy 0x123... 0.05
191
+ httpcat launchpad buy MTK 0.01 --repeat 10 --delay 1000
192
+ `)
193
+ .action(async (identifier, amount, options, command) => {
194
+ try {
195
+ const globalOpts = command.parent?.parent?.opts() || {};
196
+ const accountIndex = globalOpts.account;
197
+ // Ensure wallet is unlocked
198
+ await ensureWalletUnlocked();
199
+ let privateKey = getPrivateKey(globalOpts.privateKey, accountIndex);
200
+ if (!isConfigured(globalOpts.privateKey)) {
201
+ if (globalOpts.json) {
202
+ console.error('❌ Not configured. Run "httpcat config" first or use --private-key flag.');
203
+ process.exit(2);
204
+ }
205
+ privateKey = await promptForPrivateKey();
206
+ }
207
+ const client = await HttpcatClient.create(privateKey);
208
+ const network = client.getNetwork();
209
+ const isTestMode = network === "eip155:84532" ||
210
+ network === "eip155:11155111" ||
211
+ network.includes("sepolia");
212
+ const silent = globalOpts.json || globalOpts.quiet;
213
+ // Amount validation is handled by buyToken function
214
+ // It validates only for active tokens in DB, skips for universal buys
215
+ const repeat = options.repeat || 1;
216
+ const delay = options.delay || 0;
217
+ if (repeat > 1 && !globalOpts.quiet) {
218
+ console.log(chalk.cyan(`\nExecuting ${repeat} buys with ${delay}ms delay\n`));
219
+ }
220
+ const results = [];
221
+ for (let i = 0; i < repeat; i++) {
222
+ if (repeat > 1 && !silent) {
223
+ console.log(chalk.dim(`Buy ${i + 1}/${repeat}...`));
224
+ }
225
+ const result = await withLoading(() => buyToken(client, identifier, amount.toString(), isTestMode, silent || i > 0, privateKey), {
226
+ message: repeat > 1 ? `Buying (${i + 1}/${repeat})...` : "Buying...",
227
+ json: globalOpts.json,
228
+ quiet: globalOpts.quiet,
229
+ spinner: "cat",
230
+ clearOnSuccess: true,
231
+ });
232
+ results.push(result);
233
+ if (!silent) {
234
+ if (repeat > 1) {
235
+ displayBuyResultCompact(result);
236
+ }
237
+ else {
238
+ displayBuyResult(result);
239
+ }
240
+ }
241
+ // Delay between buys (except after the last one)
242
+ if (i < repeat - 1 && delay > 0) {
243
+ await new Promise((resolve) => setTimeout(resolve, delay));
244
+ }
245
+ }
246
+ if (globalOpts.json) {
247
+ outputJson("buy_token", repeat > 1 ? results : results[0]);
248
+ }
249
+ process.exit(0);
250
+ }
251
+ catch (error) {
252
+ const globalOpts = command.parent?.parent?.opts() || {};
253
+ if (globalOpts.json) {
254
+ outputError("buy_token", error, getExitCode(error));
255
+ }
256
+ else {
257
+ handleError(error, globalOpts.verbose);
258
+ }
259
+ process.exit(getExitCode(error));
260
+ }
261
+ });
262
+ // Sell subcommand
263
+ launchpadCommand
264
+ .command("sell")
265
+ .alias("s")
266
+ .description("Sell tokens to bonding curve ($0.01)")
267
+ .argument("<identifier>", "Token identifier (address, symbol, or ID)")
268
+ .argument("<amount>", "Amount to sell (tokens or percentage like '50%')")
269
+ .addHelpText("after", `
270
+ Examples:
271
+ httpcat launchpad sell MTK 1000
272
+ httpcat launchpad sell MTK 50%
273
+ httpcat launchpad sell 0x123... 100%
274
+ `)
275
+ .action(async (identifier, amount, options, command) => {
276
+ try {
277
+ const globalOpts = command.parent?.parent?.opts() || {};
278
+ const accountIndex = globalOpts.account;
279
+ await ensureWalletUnlocked();
280
+ let privateKey = getPrivateKey(globalOpts.privateKey, accountIndex);
281
+ if (!isConfigured(globalOpts.privateKey)) {
282
+ if (globalOpts.json) {
283
+ console.error('❌ Not configured. Run "httpcat config" first or use --private-key flag.');
284
+ process.exit(2);
285
+ }
286
+ privateKey = await promptForPrivateKey();
287
+ }
288
+ const client = await HttpcatClient.create(privateKey);
289
+ const silent = globalOpts.json || globalOpts.quiet;
290
+ const result = await withLoading(() => sellToken(client, identifier, amount.toString(), silent, privateKey), {
291
+ message: "Selling...",
292
+ json: globalOpts.json,
293
+ quiet: globalOpts.quiet,
294
+ spinner: "cat",
295
+ clearOnSuccess: true,
296
+ });
297
+ if (globalOpts.json) {
298
+ outputJson("sell_token", result);
299
+ }
300
+ else if (!globalOpts.quiet) {
301
+ displaySellResult(result);
302
+ }
303
+ process.exit(0);
304
+ }
305
+ catch (error) {
306
+ const globalOpts = command.parent?.parent?.opts() || {};
307
+ if (globalOpts.json) {
308
+ outputError("sell_token", error, getExitCode(error));
309
+ }
310
+ else {
311
+ handleError(error, globalOpts.verbose);
312
+ }
313
+ process.exit(getExitCode(error));
314
+ }
315
+ });
316
+ // List subcommand
317
+ launchpadCommand
318
+ .command("list")
319
+ .alias("ls")
320
+ .description("List all launchpad tokens (FREE)")
321
+ .option("-p, --page <number>", "Page number", "1")
322
+ .option("-l, --limit <number>", "Items per page", "20")
323
+ .option("-s, --sort <sort>", "Sort by: mcap, created, name, volume", "mcap")
324
+ .option("-f, --filter <filter>", "Filter: active, graduated, all", "active")
325
+ .addHelpText("after", `
326
+ Examples:
327
+ httpcat launchpad list
328
+ httpcat launchpad list --sort mcap --limit 50
329
+ httpcat launchpad list --filter graduated
330
+ `)
331
+ .action(async (options, command) => {
332
+ try {
333
+ const globalOpts = command.parent?.parent?.opts() || {};
334
+ const accountIndex = globalOpts.account;
335
+ await ensureWalletUnlocked();
336
+ let privateKey = getPrivateKey(globalOpts.privateKey, accountIndex);
337
+ if (!isConfigured(globalOpts.privateKey)) {
338
+ if (globalOpts.json) {
339
+ console.error('❌ Not configured. Run "httpcat config" first or use --private-key flag.');
340
+ process.exit(2);
341
+ }
342
+ privateKey = await promptForPrivateKey();
343
+ }
344
+ const client = await HttpcatClient.create(privateKey);
345
+ const result = await withLoading(() => listTokens(client, parseInt(options.page), parseInt(options.limit), options.sort), {
346
+ message: "Fetching tokens...",
347
+ json: globalOpts.json,
348
+ quiet: globalOpts.quiet,
349
+ spinner: "cat",
350
+ clearOnSuccess: true,
351
+ });
352
+ if (globalOpts.json) {
353
+ outputJson("list_tokens", result);
354
+ }
355
+ else if (!globalOpts.quiet) {
356
+ displayTokenList(result);
357
+ }
358
+ process.exit(0);
359
+ }
360
+ catch (error) {
361
+ const globalOpts = command.parent?.parent?.opts() || {};
362
+ if (globalOpts.json) {
363
+ outputError("list_tokens", error, getExitCode(error));
364
+ }
365
+ else {
366
+ handleError(error, globalOpts.verbose);
367
+ }
368
+ process.exit(getExitCode(error));
369
+ }
370
+ });
371
+ // Info subcommand
372
+ launchpadCommand
373
+ .command("info")
374
+ .alias("i")
375
+ .description("Get launchpad token information (FREE)")
376
+ .argument("<identifier>", "Token identifier (address, symbol, or ID)")
377
+ .addHelpText("after", `
378
+ Examples:
379
+ httpcat launchpad info MTK
380
+ httpcat launchpad info 0x123...
381
+ `)
382
+ .action(async (identifier, options, command) => {
383
+ try {
384
+ const globalOpts = command.parent?.parent?.opts() || {};
385
+ const accountIndex = globalOpts.account;
386
+ await ensureWalletUnlocked();
387
+ let privateKey = getPrivateKey(globalOpts.privateKey, accountIndex);
388
+ if (!isConfigured(globalOpts.privateKey)) {
389
+ if (globalOpts.json) {
390
+ console.error('❌ Not configured. Run "httpcat config" first or use --private-key flag.');
391
+ process.exit(2);
392
+ }
393
+ privateKey = await promptForPrivateKey();
394
+ }
395
+ const client = await HttpcatClient.create(privateKey);
396
+ const silent = globalOpts.json || globalOpts.quiet;
397
+ const result = await withLoading(() => getTokenInfo(client, identifier, undefined, silent), {
398
+ message: "Fetching token info...",
399
+ json: globalOpts.json,
400
+ quiet: globalOpts.quiet,
401
+ spinner: "cat",
402
+ clearOnSuccess: true,
403
+ });
404
+ if (globalOpts.json) {
405
+ outputJson("token_info", result);
406
+ }
407
+ else if (!globalOpts.quiet) {
408
+ displayTokenInfo(result);
409
+ }
410
+ process.exit(0);
411
+ }
412
+ catch (error) {
413
+ const globalOpts = command.parent?.parent?.opts() || {};
414
+ if (globalOpts.json) {
415
+ outputError("token_info", error, getExitCode(error));
416
+ }
417
+ else {
418
+ handleError(error, globalOpts.verbose);
419
+ }
420
+ process.exit(getExitCode(error));
421
+ }
422
+ });
423
+ // Positions subcommand
424
+ launchpadCommand
425
+ .command("positions")
426
+ .description("Get launchpad token positions (FREE)")
427
+ .option("--active", "Show only active tokens (on bonding curve)")
428
+ .option("--graduated", "Show only graduated tokens (on Uniswap)")
429
+ .addHelpText("after", `
430
+ Examples:
431
+ httpcat launchpad positions
432
+ httpcat launchpad positions --active
433
+ httpcat launchpad positions --graduated
434
+ `)
435
+ .action(async (options, command) => {
436
+ try {
437
+ const globalOpts = command.parent?.parent?.opts() || {};
438
+ const accountIndex = globalOpts.account;
439
+ await ensureWalletUnlocked();
440
+ let privateKey = getPrivateKey(globalOpts.privateKey, accountIndex);
441
+ if (!isConfigured(globalOpts.privateKey)) {
442
+ if (globalOpts.json) {
443
+ console.error('❌ Not configured. Run "httpcat config" first or use --private-key flag.');
444
+ process.exit(2);
445
+ }
446
+ privateKey = await promptForPrivateKey();
447
+ }
448
+ const client = await HttpcatClient.create(privateKey);
449
+ // Derive user address from private key
450
+ const account = privateKeyToAccount(privateKey);
451
+ const userAddress = account.address;
452
+ let result = await withLoading(() => getPositions(client, userAddress), {
453
+ message: "Fetching positions...",
454
+ json: globalOpts.json,
455
+ quiet: globalOpts.quiet,
456
+ spinner: "cat",
457
+ clearOnSuccess: true,
458
+ });
459
+ // Determine filter
460
+ const filter = options.active
461
+ ? "active"
462
+ : options.graduated
463
+ ? "graduated"
464
+ : "all";
465
+ // Filter results for JSON output
466
+ if (globalOpts.json && filter !== "all") {
467
+ const filteredPositions = result.positions.filter((p) => filter === "active"
468
+ ? p.token.status !== "graduated"
469
+ : p.token.status === "graduated");
470
+ result = {
471
+ ...result,
472
+ positions: filteredPositions,
473
+ total: filteredPositions.length,
474
+ };
475
+ outputJson("positions", result);
476
+ }
477
+ else if (globalOpts.json) {
478
+ outputJson("positions", result);
479
+ }
480
+ else if (!globalOpts.quiet) {
481
+ displayPositions(result, filter);
482
+ }
483
+ process.exit(0);
484
+ }
485
+ catch (error) {
486
+ const globalOpts = command.parent?.parent?.opts() || {};
487
+ if (globalOpts.json) {
488
+ outputError("positions", error, getExitCode(error));
489
+ }
490
+ else {
491
+ handleError(error, globalOpts.verbose);
492
+ }
493
+ process.exit(getExitCode(error));
494
+ }
495
+ });
496
+ // Claim subgroup
497
+ const claimCommand = launchpadCommand
498
+ .command("claim")
499
+ .description("View and claim launchpad fees (claims)");
500
+ claimCommand
501
+ .command("view")
502
+ .description("View accumulated claims (FREE)")
503
+ .argument("[identifier]", "Optional token identifier. If omitted, shows all your tokens.")
504
+ .option("--all", "Show all your tokens")
505
+ .addHelpText("after", `
506
+ Examples:
507
+ httpcat launchpad claim view # View all your tokens
508
+ httpcat launchpad claim view MTK # View specific token
509
+ httpcat launchpad claim view 0x123...
510
+ `)
511
+ .action(async (identifier, options, command) => {
512
+ try {
513
+ const globalOpts = command.parent?.parent?.parent?.opts() || {};
514
+ const accountIndex = globalOpts.account;
515
+ await ensureWalletUnlocked();
516
+ let privateKey = getPrivateKey(globalOpts.privateKey, accountIndex);
517
+ if (!isConfigured(globalOpts.privateKey)) {
518
+ if (globalOpts.json) {
519
+ console.error('❌ Not configured. Run "httpcat config" first or use --private-key flag.');
520
+ process.exit(2);
521
+ }
522
+ privateKey = await promptForPrivateKey();
523
+ }
524
+ const client = await HttpcatClient.create(privateKey);
525
+ const silent = globalOpts.json || globalOpts.quiet;
526
+ const account = privateKeyToAccount(privateKey);
527
+ const callerAddress = account.address;
528
+ if (!identifier || options.all) {
529
+ // View all tokens
530
+ const userTokens = await withLoading(() => getUserCreatedTokens(client, callerAddress), {
531
+ message: "Finding your tokens...",
532
+ json: globalOpts.json,
533
+ quiet: globalOpts.quiet,
534
+ spinner: "cat",
535
+ clearOnSuccess: true,
536
+ });
537
+ if (userTokens.length === 0) {
538
+ if (globalOpts.json) {
539
+ outputJson("user_tokens", { tokens: [] });
540
+ }
541
+ else if (!globalOpts.quiet) {
542
+ displayTokenCreationGuide();
543
+ }
544
+ process.exit(0);
545
+ }
546
+ const allFees = await withLoading(() => getAllTokenFees(client, userTokens, silent), {
547
+ message: "Fetching available claims...",
548
+ json: globalOpts.json,
549
+ quiet: globalOpts.quiet,
550
+ spinner: "cat",
551
+ clearOnSuccess: true,
552
+ });
553
+ if (globalOpts.json) {
554
+ outputJson("all_claims", allFees);
555
+ }
556
+ else if (!globalOpts.quiet) {
557
+ displayAllFees(allFees);
558
+ }
559
+ }
560
+ else {
561
+ // View specific token
562
+ const result = await withLoading(() => viewFees(client, identifier, silent), {
563
+ message: "Fetching claim information...",
564
+ json: globalOpts.json,
565
+ quiet: globalOpts.quiet,
566
+ spinner: "cat",
567
+ clearOnSuccess: true,
568
+ });
569
+ if (globalOpts.json) {
570
+ outputJson("view_fees", result);
571
+ }
572
+ else if (!globalOpts.quiet) {
573
+ displayFees(result);
574
+ }
575
+ }
576
+ process.exit(0);
577
+ }
578
+ catch (error) {
579
+ const globalOpts = command.parent?.parent?.parent?.opts() || {};
580
+ if (globalOpts.json) {
581
+ outputError("view_fees", error, getExitCode(error));
582
+ }
583
+ else {
584
+ handleError(error, globalOpts.verbose);
585
+ }
586
+ process.exit(getExitCode(error));
587
+ }
588
+ });
589
+ claimCommand
590
+ .command("execute")
591
+ .alias("claim")
592
+ .description("Claim accumulated fees ($0.01)")
593
+ .argument("[identifier]", "Optional token identifier. If omitted and --all is used, claims all tokens.")
594
+ .option("--execute", "Execute the claim transaction (required)")
595
+ .option("--all", "Claim fees for all your tokens")
596
+ .addHelpText("after", `
597
+ Examples:
598
+ httpcat launchpad claim execute --all # Claim all tokens
599
+ httpcat launchpad claim execute MTK # Claim specific token
600
+ httpcat launchpad claim execute MTK --execute
601
+ `)
602
+ .action(async (identifier, options, command) => {
603
+ try {
604
+ const globalOpts = command.parent?.parent?.parent?.opts() || {};
605
+ const accountIndex = globalOpts.account;
606
+ await ensureWalletUnlocked();
607
+ let privateKey = getPrivateKey(globalOpts.privateKey, accountIndex);
608
+ if (!isConfigured(globalOpts.privateKey)) {
609
+ if (globalOpts.json) {
610
+ console.error('❌ Not configured. Run "httpcat config" first or use --private-key flag.');
611
+ process.exit(2);
612
+ }
613
+ privateKey = await promptForPrivateKey();
614
+ }
615
+ const client = await HttpcatClient.create(privateKey);
616
+ const silent = globalOpts.json || globalOpts.quiet;
617
+ const account = privateKeyToAccount(privateKey);
618
+ const callerAddress = account.address;
619
+ if ((!identifier && options.all) || options.all) {
620
+ // Claim all tokens
621
+ const userTokens = await withLoading(() => getUserCreatedTokens(client, callerAddress), {
622
+ message: "Finding your tokens...",
623
+ json: globalOpts.json,
624
+ quiet: globalOpts.quiet,
625
+ spinner: "cat",
626
+ clearOnSuccess: true,
627
+ });
628
+ if (userTokens.length === 0) {
629
+ if (globalOpts.json) {
630
+ outputJson("user_tokens", { tokens: [] });
631
+ }
632
+ else if (!globalOpts.quiet) {
633
+ displayTokenCreationGuide();
634
+ }
635
+ process.exit(0);
636
+ }
637
+ const results = await claimAllFees(client, userTokens, callerAddress, silent);
638
+ if (globalOpts.json) {
639
+ outputJson("claim_all_fees", {
640
+ success: results.success,
641
+ failed: results.failed,
642
+ });
643
+ }
644
+ else if (!globalOpts.quiet) {
645
+ console.log();
646
+ console.log(chalk.magenta.bold(`✅ Claimed fees for ${results.success.length} token(s)`));
647
+ if (results.failed.length > 0) {
648
+ console.log(chalk.yellow(`⚠️ Failed to claim fees for ${results.failed.length} token(s)`));
649
+ }
650
+ console.log();
651
+ }
652
+ }
653
+ else if (identifier) {
654
+ // Claim specific token
655
+ if (!options.execute) {
656
+ // Preview mode - just view fees
657
+ const viewResult = await withLoading(() => viewFees(client, identifier, silent), {
658
+ message: "Fetching fees...",
659
+ json: globalOpts.json,
660
+ quiet: globalOpts.quiet,
661
+ spinner: "cat",
662
+ clearOnSuccess: true,
663
+ });
664
+ if (globalOpts.json) {
665
+ outputJson("claim_fees_preview", viewResult);
666
+ }
667
+ else if (!globalOpts.quiet) {
668
+ displayFees(viewResult);
669
+ console.log();
670
+ console.log(chalk.yellow("⚠️ This is a preview. Use --execute to claim."));
671
+ }
672
+ process.exit(0);
673
+ return;
674
+ }
675
+ // Execute claim
676
+ const result = await withLoading(() => claimFees(client, identifier, callerAddress, silent), {
677
+ message: "Claiming fees...",
678
+ json: globalOpts.json,
679
+ quiet: globalOpts.quiet,
680
+ spinner: "cat",
681
+ clearOnSuccess: true,
682
+ });
683
+ if (globalOpts.json) {
684
+ outputJson("claim_fees", result);
685
+ }
686
+ else if (!globalOpts.quiet) {
687
+ displayClaimResult(result);
688
+ }
689
+ }
690
+ else {
691
+ throw new Error("Please specify a token identifier or use --all flag");
692
+ }
693
+ process.exit(0);
694
+ }
695
+ catch (error) {
696
+ const globalOpts = command.parent?.parent?.parent?.opts() || {};
697
+ if (globalOpts.json) {
698
+ outputError("claim_fees", error, getExitCode(error));
699
+ }
700
+ else {
701
+ handleError(error, globalOpts.verbose);
702
+ }
703
+ process.exit(getExitCode(error));
704
+ }
705
+ });
706
+ return launchpadCommand;
707
+ }
708
+ //# sourceMappingURL=launchpad.js.map