dexterm-cli 0.1.6 → 0.2.0
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/packages/agents/src/schema.js +22 -1
- package/dist/packages/agents/src/spectator.js +3 -1
- package/dist/packages/agents/src/story.js +11 -2
- package/dist/packages/agents/src/tiers.js +36 -2
- package/dist/packages/agents/src/tools.js +35 -2
- package/dist/packages/autotrade/assets/exit-profile.schema.json +492 -0
- package/dist/packages/autotrade/assets/limits.schema.json +569 -0
- package/dist/packages/autotrade/assets/profiles/moonbag.json +46 -0
- package/dist/packages/autotrade/assets/profiles/runner.json +88 -0
- package/dist/packages/autotrade/assets/profiles/scalp.json +88 -0
- package/dist/packages/autotrade/assets/profiles/swing.json +88 -0
- package/dist/packages/autotrade/assets/strategies/moonbag.json +101 -0
- package/dist/packages/autotrade/assets/strategies/runner.json +101 -0
- package/dist/packages/autotrade/assets/strategies/sample-dip-ladder.json +188 -0
- package/dist/packages/autotrade/assets/strategies/scalp.json +98 -0
- package/dist/packages/autotrade/assets/strategies/swing.json +97 -0
- package/dist/packages/autotrade/assets/strategies/yolo.json +157 -0
- package/dist/packages/autotrade/assets/tapes/yolo-rehearsal.json +1 -0
- package/dist/packages/autotrade/examples/executor/README.md +70 -0
- package/dist/packages/autotrade/examples/executor/jsonl-tail-executor.mjs +57 -0
- package/dist/packages/autotrade/examples/executor/kit.mjs +144 -0
- package/dist/packages/autotrade/examples/executor/signal-cmd-executor.mjs +25 -0
- package/dist/packages/autotrade/examples/executor/telegram-bot-recipe.md +47 -0
- package/dist/packages/autotrade/examples/executor/webhook-executor.mjs +47 -0
- package/dist/packages/autotrade/src/account.js +74 -0
- package/dist/packages/autotrade/src/backtest.js +358 -0
- package/dist/packages/autotrade/src/basis-text.js +32 -0
- package/dist/packages/autotrade/src/chat/approvals.js +484 -0
- package/dist/packages/autotrade/src/chat/audit.js +140 -0
- package/dist/packages/autotrade/src/chat/config.js +95 -0
- package/dist/packages/autotrade/src/chat/connector.js +24 -0
- package/dist/packages/autotrade/src/chat/control.js +104 -0
- package/dist/packages/autotrade/src/chat/fake.js +100 -0
- package/dist/packages/autotrade/src/chat/format.js +71 -0
- package/dist/packages/autotrade/src/chat/hub.js +187 -0
- package/dist/packages/autotrade/src/chat/index.js +18 -0
- package/dist/packages/autotrade/src/chat/notify.js +302 -0
- package/dist/packages/autotrade/src/chat/pairing.js +46 -0
- package/dist/packages/autotrade/src/chat/redact.js +48 -0
- package/dist/packages/autotrade/src/chat/secrets.js +106 -0
- package/dist/packages/autotrade/src/chat/service.js +251 -0
- package/dist/packages/autotrade/src/chat/telegram.js +290 -0
- package/dist/packages/autotrade/src/desk-executor.js +188 -0
- package/dist/packages/autotrade/src/engine.js +401 -0
- package/dist/packages/autotrade/src/execution-port.js +97 -0
- package/dist/packages/autotrade/src/executor-health.js +217 -0
- package/dist/packages/autotrade/src/fleet-config.js +169 -0
- package/dist/packages/autotrade/src/fleet-control.js +276 -0
- package/dist/packages/autotrade/src/fleet.js +642 -0
- package/dist/packages/autotrade/src/forward.js +355 -0
- package/dist/packages/autotrade/src/index.js +72 -0
- package/dist/packages/autotrade/src/journey.js +477 -0
- package/dist/packages/autotrade/src/ledger.js +108 -0
- package/dist/packages/autotrade/src/limits.js +682 -0
- package/dist/packages/autotrade/src/live-source.js +182 -0
- package/dist/packages/autotrade/src/monitor-daemon.js +715 -0
- package/dist/packages/autotrade/src/monitor.js +190 -0
- package/dist/packages/autotrade/src/ollama-sessions.js +137 -0
- package/dist/packages/autotrade/src/outbox.js +394 -0
- package/dist/packages/autotrade/src/paper-accounts.js +72 -0
- package/dist/packages/autotrade/src/paper-limits.js +87 -0
- package/dist/packages/autotrade/src/real-mode.js +688 -0
- package/dist/packages/autotrade/src/receipts.js +330 -0
- package/dist/packages/autotrade/src/replay.js +198 -0
- package/dist/packages/autotrade/src/report.js +168 -0
- package/dist/packages/autotrade/src/runner-config.js +99 -0
- package/dist/packages/autotrade/src/runner.js +923 -0
- package/dist/packages/autotrade/src/safety.js +243 -0
- package/dist/packages/autotrade/src/service-guard.js +125 -0
- package/dist/packages/autotrade/src/service-install.js +213 -0
- package/dist/packages/autotrade/src/service-recover.js +232 -0
- package/dist/packages/autotrade/src/service.js +289 -0
- package/dist/packages/autotrade/src/session.js +269 -0
- package/dist/packages/autotrade/src/sessions.js +503 -0
- package/dist/packages/autotrade/src/signal-channels.js +312 -0
- package/dist/packages/autotrade/src/signal.js +196 -0
- package/dist/packages/autotrade/src/store.js +250 -0
- package/dist/packages/autotrade/src/strategy.js +258 -0
- package/dist/packages/autotrade/src/trade-ledger.js +241 -0
- package/dist/packages/autotrade/src/yolo.js +140 -0
- package/dist/packages/cli/assets/claude/analyst-system.md +4 -4
- package/dist/packages/cli/assets/claude/plugin/skills/token-dossier/SKILL.md +1 -1
- package/dist/packages/cli/src/ai-cmd.js +412 -0
- package/dist/packages/cli/src/analyst/backend.js +83 -15
- package/dist/packages/cli/src/analyst/codex.js +15 -9
- package/dist/packages/cli/src/analyst/ollama.js +263 -0
- package/dist/packages/cli/src/analyst/session.js +5 -2
- package/dist/packages/cli/src/app-help-gen.js +56 -8
- package/dist/packages/cli/src/autotrade-cmd/audit.js +74 -0
- package/dist/packages/cli/src/autotrade-cmd/backtest.js +216 -0
- package/dist/packages/cli/src/autotrade-cmd/executor.js +91 -0
- package/dist/packages/cli/src/autotrade-cmd/flatten.js +64 -0
- package/dist/packages/cli/src/autotrade-cmd/fleet.js +401 -0
- package/dist/packages/cli/src/autotrade-cmd/forward.js +283 -0
- package/dist/packages/cli/src/autotrade-cmd/journey.js +208 -0
- package/dist/packages/cli/src/autotrade-cmd/limits.js +393 -0
- package/dist/packages/cli/src/autotrade-cmd/receipt.js +63 -0
- package/dist/packages/cli/src/autotrade-cmd/report.js +79 -0
- package/dist/packages/cli/src/autotrade-cmd/requests.js +79 -0
- package/dist/packages/cli/src/autotrade-cmd/run.js +657 -0
- package/dist/packages/cli/src/autotrade-cmd/service.js +873 -0
- package/dist/packages/cli/src/autotrade-cmd/signal.js +824 -0
- package/dist/packages/cli/src/autotrade-cmd/stop.js +76 -0
- package/dist/packages/cli/src/autotrade-cmd/strategies.js +198 -0
- package/dist/packages/cli/src/autotrade-cmd/strategy-control.js +174 -0
- package/dist/packages/cli/src/autotrade-cmd/telegram-host.js +101 -0
- package/dist/packages/cli/src/autotrade-cmd.js +214 -0
- package/dist/packages/cli/src/display.js +156 -17
- package/dist/packages/cli/src/doctor.js +62 -3
- package/dist/packages/cli/src/export.js +10 -2
- package/dist/packages/cli/src/index.js +1 -1
- package/dist/packages/cli/src/ledger-cmd.js +290 -0
- package/dist/packages/cli/src/live/chart-fills.js +46 -0
- package/dist/packages/cli/src/live/index.js +23 -89
- package/dist/packages/cli/src/live/screens/token-live.js +9 -6
- package/dist/packages/cli/src/live/trade.js +12 -457
- package/dist/packages/cli/src/live/watchlist.js +1 -1
- package/dist/packages/cli/src/main.js +147 -190
- package/dist/packages/cli/src/mcp-cmd.js +7 -1
- package/dist/packages/cli/src/plan-cmd.js +1 -1
- package/dist/packages/cli/src/pnl-app.js +31 -21
- package/dist/packages/cli/src/pnl-card.js +162 -21
- package/dist/packages/cli/src/popup.js +22 -6
- package/dist/packages/cli/src/record-cmd.js +141 -20
- package/dist/packages/cli/src/screens/agent-hud.js +34 -2
- package/dist/packages/cli/src/screens/analyst-session.js +7 -4
- package/dist/packages/cli/src/screens/analyst.js +3 -2
- package/dist/packages/cli/src/screens/autotrade-journey.js +134 -0
- package/dist/packages/cli/src/screens/autotrade-keys.js +182 -0
- package/dist/packages/cli/src/screens/autotrade-proposals.js +123 -0
- package/dist/packages/cli/src/screens/autotrade-screen.js +776 -0
- package/dist/packages/cli/src/screens/autotrade-ui.js +650 -0
- package/dist/packages/cli/src/screens/autotrade-worker.js +91 -0
- package/dist/packages/cli/src/screens/brain.js +37 -11
- package/dist/packages/cli/src/screens/overlay.js +5 -2
- package/dist/packages/cli/src/screens/plans.js +5 -17
- package/dist/packages/cli/src/screens/pnl-chip.js +9 -8
- package/dist/packages/cli/src/screens/positions.js +6 -28
- package/dist/packages/cli/src/screens/ticket.js +38 -205
- package/dist/packages/cli/src/screens/token.js +3 -3
- package/dist/packages/cli/src/state.js +25 -19
- package/dist/packages/cli/src/telegram-cmd.js +454 -0
- package/dist/packages/cli/src/trade.js +3 -128
- package/dist/packages/cli/src/version.js +1 -1
- package/dist/packages/cli/src/wallet-cmd.js +39 -340
- package/dist/packages/cli/src/wallet-command.js +8 -11
- package/dist/packages/cli/src/widgets.js +0 -12
- package/dist/packages/custom/src/config.js +20 -2
- package/dist/packages/custom/src/schema.js +35 -10
- package/dist/packages/custom/src/workspace.js +3 -3
- package/dist/packages/data/src/basis.js +191 -0
- package/dist/packages/data/src/detail.js +53 -2
- package/dist/packages/data/src/index.js +0 -14
- package/dist/packages/data/src/store.js +14 -5
- package/dist/packages/data/src/trade/agent/paper-desk.js +228 -16
- package/dist/packages/data/src/trade/agent/rendezvous.js +3 -2
- package/dist/packages/data/src/trade/bridge.js +4 -102
- package/dist/packages/data/src/trade/ledger/export.js +101 -0
- package/dist/packages/data/src/trade/ledger/file.js +135 -0
- package/dist/packages/data/src/trade/ledger/fold.js +191 -0
- package/dist/packages/data/src/trade/ledger/index.js +9 -0
- package/dist/packages/data/src/trade/ledger/schema.js +83 -0
- package/dist/packages/data/src/trade/ledger/sources.js +307 -0
- package/dist/packages/data/src/trade/ledger/stats.js +123 -0
- package/dist/packages/data/src/trade/ledger/tags.js +116 -0
- package/dist/packages/data/src/trade/ledger/view.js +51 -0
- package/dist/packages/data/src/trade/plans/index.js +0 -1
- package/dist/packages/data/src/trade/plans/service.js +3 -27
- package/dist/packages/mcp/assets/kb/app-help/autotrade-chat.md +48 -0
- package/dist/packages/mcp/assets/kb/app-help/autotrade-executor-kit.md +44 -0
- package/dist/packages/mcp/assets/kb/app-help/autotrade-journey.md +46 -0
- package/dist/packages/mcp/assets/kb/app-help/autotrade-limits.md +48 -0
- package/dist/packages/mcp/assets/kb/app-help/autotrade-parallel.md +42 -0
- package/dist/packages/mcp/assets/kb/app-help/autotrade-real-signal.md +45 -0
- package/dist/packages/mcp/assets/kb/app-help/autotrade-runner.md +35 -0
- package/dist/packages/mcp/assets/kb/app-help/autotrade-stop.md +37 -0
- package/dist/packages/mcp/assets/kb/app-help/autotrade-strategies.md +35 -0
- package/dist/packages/mcp/assets/kb/app-help/autotrade-telegram.md +40 -0
- package/dist/packages/mcp/assets/kb/app-help/chart-trade-markers.md +42 -0
- package/dist/packages/mcp/assets/kb/app-help/link-a-wallet.md +4 -10
- package/dist/packages/mcp/assets/kb/app-help/live-trading.md +38 -0
- package/dist/packages/mcp/assets/kb/app-help/live-yolo.md +34 -0
- package/dist/packages/mcp/assets/kb/app-help/order-plans.md +1 -1
- package/dist/packages/mcp/assets/kb/app-help/price-or-marketcap.md +5 -2
- package/dist/packages/mcp/assets/kb/app-help/screen-analyst.md +3 -0
- package/dist/packages/mcp/assets/kb/app-help/screen-autotrade.md +229 -0
- package/dist/packages/mcp/assets/kb/app-help/screen-kol.md +3 -0
- package/dist/packages/mcp/assets/kb/app-help/screen-newpairs.md +3 -0
- package/dist/packages/mcp/assets/kb/app-help/screen-positions.md +3 -0
- package/dist/packages/mcp/assets/kb/app-help/screen-screener.md +3 -0
- package/dist/packages/mcp/assets/kb/app-help/screen-token.md +3 -0
- package/dist/packages/mcp/assets/kb/app-help/screen-trending.md +3 -0
- package/dist/packages/mcp/assets/kb/app-help/screen-watchlist.md +3 -0
- package/dist/packages/mcp/assets/kb/app-help/standing-mandates.md +1 -1
- package/dist/packages/mcp/assets/kb/app-help/trade-ledger.md +54 -0
- package/dist/packages/mcp/assets/kb/app-help/use-local-model.md +38 -0
- package/dist/packages/mcp/assets/kb/docs/docs-agents-agent-paper-trading.md +4 -1
- package/dist/packages/mcp/assets/kb/docs/docs-agents-reading-your-trade-ledger.md +31 -0
- package/dist/packages/mcp/assets/kb/docs/docs-agents-untrusted-by-default.md +1 -1
- package/dist/packages/mcp/assets/kb/docs/docs-analyst-if-claude-is-missing.md +1 -1
- package/dist/packages/mcp/assets/kb/docs/docs-analyst-use-a-local-model-instead.md +27 -0
- package/dist/packages/mcp/assets/kb/docs/docs-analyst-what-it-sees.md +2 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-backtests-and-their-limits.md +56 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-change-a-strategy-by-chat.md +51 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-checking-the-record-of-a-run.md +28 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-comparing-them.md +41 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-exits-and-wakes.md +76 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-how-a-stop-reaches-the-runner.md +32 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-on-the-q-screen.md +38 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-one-strategy-or-all-of-them.md +35 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-paper-accounts.md +50 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-presets.md +37 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-running-it-all-day.md +31 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-sessions-and-their-limits.md +31 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-several-strategies-at-once.md +33 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-stopping-it.md +37 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-strategies-and-presets.md +34 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-the-always-on-service.md +57 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-the-autotrade-json-file.md +48 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-the-heartbeat.md +27 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-the-run-file-and-the-heartbeat.md +34 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-the-runner-and-candidate-sessions.md +45 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-what-each-session-shows-first.md +31 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-what-it-costs-claude-usage-per-session.md +58 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-what-it-is-paper-self-directed.md +50 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-what-it-will-not-do.md +31 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-which-account-day-caps-and-the-usage-guard.md +44 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade-your-strategies.md +37 -0
- package/dist/packages/mcp/assets/kb/docs/docs-autotrade.md +22 -0
- package/dist/packages/mcp/assets/kb/docs/docs-beginners-before-any-experimental-trading.md +2 -2
- package/dist/packages/mcp/assets/kb/docs/docs-beginners.md +1 -1
- package/dist/packages/mcp/assets/kb/docs/docs-build-a-strategy-by-chat-1-ask-for-a-strategy.md +27 -0
- package/dist/packages/mcp/assets/kb/docs/docs-build-a-strategy-by-chat-2-backtest-it-held-out-split.md +31 -0
- package/dist/packages/mcp/assets/kb/docs/docs-build-a-strategy-by-chat-3-forward-test-it-on-live-data.md +44 -0
- package/dist/packages/mcp/assets/kb/docs/docs-build-a-strategy-by-chat-4-promote-it-to-always-on-paper.md +36 -0
- package/dist/packages/mcp/assets/kb/docs/docs-build-a-strategy-by-chat-5-real-only-if-you-choose.md +36 -0
- package/dist/packages/mcp/assets/kb/docs/docs-build-a-strategy-by-chat-the-ladder.md +39 -0
- package/dist/packages/mcp/assets/kb/docs/docs-build-a-strategy-by-chat-the-report.md +31 -0
- package/dist/packages/mcp/assets/kb/docs/docs-build-a-strategy-by-chat-what-the-analyst-knows.md +30 -0
- package/dist/packages/mcp/assets/kb/docs/docs-build-a-strategy-by-chat.md +24 -0
- package/dist/packages/mcp/assets/kb/docs/docs-configuration-chart-markers.md +30 -0
- package/dist/packages/mcp/assets/kb/docs/docs-configuration-chart-y-axis.md +1 -1
- package/dist/packages/mcp/assets/kb/docs/docs-configuration-environment-variables.md +4 -1
- package/dist/packages/mcp/assets/kb/docs/docs-configuration-files-on-disk.md +1 -0
- package/dist/packages/mcp/assets/kb/docs/docs-configuration-headless-recorder-dexterm-record.md +3 -1
- package/dist/packages/mcp/assets/kb/docs/docs-configuration-price-display-mode.md +8 -6
- package/dist/packages/mcp/assets/kb/docs/docs-copy-trading-stage-2-the-one-key-mirror-ticket-a-proposal.md +1 -1
- package/dist/packages/mcp/assets/kb/docs/docs-copy-trading-stage-3-capped-auto-mirror-default-off-less.md +1 -1
- package/dist/packages/mcp/assets/kb/docs/docs-copy-trading-what-is-proven-what-is-not.md +1 -1
- package/dist/packages/mcp/assets/kb/docs/docs-copy-trading.md +1 -1
- package/dist/packages/mcp/assets/kb/docs/docs-data-sources-recorded-history-and-retention.md +36 -0
- package/dist/packages/mcp/assets/kb/docs/docs-data-sources-sources.md +1 -0
- package/dist/packages/mcp/assets/kb/docs/docs-getting-started-first-run.md +1 -1
- package/dist/packages/mcp/assets/kb/docs/docs-getting-started-install.md +3 -3
- package/dist/packages/mcp/assets/kb/docs/docs-getting-started-requirements.md +1 -1
- package/dist/packages/mcp/assets/kb/docs/docs-getting-started.md +1 -1
- package/dist/packages/mcp/assets/kb/docs/docs-going-real-executor-health.md +38 -0
- package/dist/packages/mcp/assets/kb/docs/docs-going-real-paper-vs-real.md +33 -0
- package/dist/packages/mcp/assets/kb/docs/docs-going-real-the-digest.md +36 -0
- package/dist/packages/mcp/assets/kb/docs/docs-going-real-the-executor-kit.md +48 -0
- package/dist/packages/mcp/assets/kb/docs/docs-going-real-the-whole-path.md +37 -0
- package/dist/packages/mcp/assets/kb/docs/docs-going-real-what-dexterm-does-and-never-does.md +44 -0
- package/dist/packages/mcp/assets/kb/docs/docs-going-real-your-limits.md +77 -0
- package/dist/packages/mcp/assets/kb/docs/docs-going-real.md +24 -0
- package/dist/packages/mcp/assets/kb/docs/docs-live-trading-changed-in-0-1-7.md +26 -0
- package/dist/packages/mcp/assets/kb/docs/docs-live-trading-real-mode-your-strategy-s-trades-to-your.md +31 -0
- package/dist/packages/mcp/assets/kb/docs/docs-live-trading-stopping.md +28 -0
- package/dist/packages/mcp/assets/kb/docs/docs-live-trading-the-short-version.md +34 -0
- package/dist/packages/mcp/assets/kb/docs/docs-live-trading-using-a-trading-bot-with-dexterm.md +31 -0
- package/dist/packages/mcp/assets/kb/docs/docs-live-trading-what-dexterm-does-not-do.md +30 -0
- package/dist/packages/mcp/assets/kb/docs/docs-live-trading-what-dexterm-does.md +29 -0
- package/dist/packages/mcp/assets/kb/docs/docs-live-trading.md +23 -0
- package/dist/packages/mcp/assets/kb/docs/docs-ollama-another-machine.md +28 -0
- package/dist/packages/mcp/assets/kb/docs/docs-ollama-autotrade-on-a-local-model.md +29 -0
- package/dist/packages/mcp/assets/kb/docs/docs-ollama-check-your-model-dexterm-ai-probe.md +38 -0
- package/dist/packages/mcp/assets/kb/docs/docs-ollama-how-we-checked.md +27 -0
- package/dist/packages/mcp/assets/kb/docs/docs-ollama-models-without-tool-calling.md +32 -0
- package/dist/packages/mcp/assets/kb/docs/docs-ollama-pick-the-engine-globally-or-per-surface.md +43 -0
- package/dist/packages/mcp/assets/kb/docs/docs-ollama-restriction-profiles.md +35 -0
- package/dist/packages/mcp/assets/kb/docs/docs-ollama-set-it-up-in-two-minutes.md +39 -0
- package/dist/packages/mcp/assets/kb/docs/docs-ollama-troubleshooting.md +35 -0
- package/dist/packages/mcp/assets/kb/docs/docs-ollama-what-runs-on-a-local-model.md +39 -0
- package/dist/packages/mcp/assets/kb/docs/docs-ollama-what-stays-outside-the-model.md +36 -0
- package/dist/packages/mcp/assets/kb/docs/docs-ollama-which-model.md +38 -0
- package/dist/packages/mcp/assets/kb/docs/docs-ollama-your-own-agent-on-the-local-model.md +28 -0
- package/dist/packages/mcp/assets/kb/docs/docs-ollama.md +28 -0
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-letting-an-agent-paper-trade-experimental.md +3 -4
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-link-a-wallet-read-only.md +30 -0
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-order-plans-and-standing-mandates.md +3 -4
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-panic.md +4 -7
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-paper-only-mandates.md +6 -7
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-pnl-cards.md +7 -7
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-the-safety-model.md +34 -0
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-the-ticket.md +3 -4
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-the-trade-ledger.md +42 -0
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-the-wallet.md +4 -5
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-trade-moments.md +4 -5
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading.md +4 -5
- package/dist/packages/mcp/assets/kb/docs/docs-popup-chart-buy-and-sell-markers.md +37 -0
- package/dist/packages/mcp/assets/kb/docs/docs-popup-chart-what-it-shows.md +2 -1
- package/dist/packages/mcp/assets/kb/docs/docs-real-mode-receipts-what-your-executor-did.md +42 -0
- package/dist/packages/mcp/assets/kb/docs/docs-real-mode-safety.md +34 -0
- package/dist/packages/mcp/assets/kb/docs/docs-real-mode-set-it-up.md +47 -0
- package/dist/packages/mcp/assets/kb/docs/docs-real-mode-the-channels.md +42 -0
- package/dist/packages/mcp/assets/kb/docs/docs-real-mode-the-signal.md +48 -0
- package/dist/packages/mcp/assets/kb/docs/docs-real-mode-what-it-is.md +35 -0
- package/dist/packages/mcp/assets/kb/docs/docs-real-mode-what-it-will-not-do.md +34 -0
- package/dist/packages/mcp/assets/kb/docs/docs-real-mode-where-you-see-it.md +34 -0
- package/dist/packages/mcp/assets/kb/docs/docs-real-mode.md +27 -0
- package/dist/packages/mcp/assets/kb/docs/docs-screens-autotrade-paper.md +26 -0
- package/dist/packages/mcp/assets/kb/docs/docs-screens-order-plans.md +1 -1
- package/dist/packages/mcp/assets/kb/docs/docs-screens-token-screen.md +2 -0
- package/dist/packages/mcp/assets/kb/docs/docs-spectator-the-brain-view-and-the-pnl-chip.md +1 -1
- package/dist/packages/mcp/assets/kb/docs/docs-telegram-approve-one-tap-entries.md +50 -0
- package/dist/packages/mcp/assets/kb/docs/docs-telegram-control-the-commands.md +43 -0
- package/dist/packages/mcp/assets/kb/docs/docs-telegram-if-something-goes-wrong.md +30 -0
- package/dist/packages/mcp/assets/kb/docs/docs-telegram-notify-what-reaches-your-phone.md +41 -0
- package/dist/packages/mcp/assets/kb/docs/docs-telegram-set-it-up.md +47 -0
- package/dist/packages/mcp/assets/kb/docs/docs-telegram-the-record.md +26 -0
- package/dist/packages/mcp/assets/kb/docs/docs-telegram-what-it-is.md +33 -0
- package/dist/packages/mcp/assets/kb/docs/docs-telegram-what-it-will-not-do.md +31 -0
- package/dist/packages/mcp/assets/kb/docs/docs-telegram.md +23 -0
- package/dist/packages/mcp/assets/kb/docs/docs-troubleshooting-common-questions.md +1 -1
- package/dist/packages/mcp/assets/kb/docs/docs-troubleshooting-doctor-lines.md +4 -0
- package/dist/packages/mcp/assets/kb/docs/docs-voice-linux-and-windows.md +1 -1
- package/dist/packages/mcp/assets/kb/docs/docs-voice.md +1 -1
- package/dist/packages/mcp/assets/kb/docs/docs-yolo-1-replay-it-on-your-own-history.md +42 -0
- package/dist/packages/mcp/assets/kb/docs/docs-yolo-2-run-it-on-paper.md +34 -0
- package/dist/packages/mcp/assets/kb/docs/docs-yolo-3-watch-it-and-stop-it.md +32 -0
- package/dist/packages/mcp/assets/kb/docs/docs-yolo-the-rules.md +37 -0
- package/dist/packages/mcp/assets/kb/docs/docs-yolo-what-it-is.md +34 -0
- package/dist/packages/mcp/assets/kb/docs/docs-yolo-what-it-will-not-do.md +31 -0
- package/dist/packages/mcp/assets/kb/docs/docs-yolo.md +26 -0
- package/dist/packages/mcp/assets/kb/entries/autotrade.md +40 -0
- package/dist/packages/mcp/src/app-help.js +1 -1
- package/dist/packages/mcp/src/autotrade-tools.js +1107 -0
- package/dist/packages/mcp/src/backtest-requests.js +71 -0
- package/dist/packages/mcp/src/engine/config.js +159 -0
- package/dist/packages/mcp/src/engine/index.js +10 -0
- package/dist/packages/mcp/src/engine/loop.js +101 -0
- package/dist/packages/mcp/src/engine/mcp-client.js +123 -0
- package/dist/packages/mcp/src/engine/ollama.js +258 -0
- package/dist/packages/mcp/src/engine/probe.js +110 -0
- package/dist/packages/mcp/src/engine/reason.js +35 -0
- package/dist/packages/mcp/src/engine/restrictions.js +111 -0
- package/dist/packages/mcp/src/index.js +7 -1
- package/dist/packages/mcp/src/ledger-tools.js +494 -0
- package/dist/packages/mcp/src/paper-agent.js +2 -0
- package/dist/packages/mcp/src/server.js +138 -19
- package/dist/packages/packs/src/backtest.js +3 -1
- package/dist/packages/popup/src/pages/chart-lib.js +134 -21
- package/dist/packages/popup/src/pages/chart.css +9 -0
- package/dist/packages/popup/src/pages/chart.html +3 -1
- package/dist/packages/popup/src/pages/chart.js +104 -7
- package/dist/packages/popup/src/protocol.js +2 -0
- package/dist/packages/popup/src/server.js +4 -0
- package/dist/packages/recorder/src/index.js +2 -0
- package/dist/packages/recorder/src/recorder.js +63 -6
- package/dist/packages/recorder/src/retention.js +100 -0
- package/dist/packages/recorder/src/schema.js +34 -1
- package/dist/packages/recorder/src/ticks.js +237 -0
- package/dist/packages/tui/src/index.js +1 -0
- package/dist/packages/tui/src/keymap.js +28 -1
- package/dist/packages/tui/src/markers.js +219 -0
- package/dist/packages/tui/src/widgets.js +149 -2
- package/package.json +2 -1
- package/dist/packages/data/src/trade/caps.js +0 -323
- package/dist/packages/data/src/trade/executor.js +0 -933
- package/dist/packages/data/src/trade/plans/executor-live.js +0 -220
- package/dist/packages/data/src/trade/rpc-exec.js +0 -229
- package/dist/packages/data/src/trade/signer/client.js +0 -197
- package/dist/packages/data/src/trade/signer/fast-wallet.js +0 -154
- package/dist/packages/data/src/trade/signer/host.js +0 -97
- package/dist/packages/data/src/trade/signer/main.js +0 -121
- package/dist/packages/data/src/trade/signer/probe-builder.js +0 -85
- package/dist/packages/data/src/trade/signer/protocol.js +0 -92
- package/dist/packages/data/src/trade/signer/service.js +0 -400
- package/dist/packages/data/src/trade/signer/sol-usd-feed.js +0 -98
- package/dist/packages/data/src/trade/sol-usd.js +0 -86
- package/dist/packages/data/src/trade/swap-build.js +0 -108
- package/dist/packages/data/src/trade/token-delta.js +0 -201
- package/dist/packages/data/vendor/solana-web3/LICENSE +0 -20
- package/dist/packages/data/vendor/solana-web3/NOTICE.md +0 -13
- package/dist/packages/data/vendor/solana-web3/index.iife.min.js +0 -20
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-a-live-ticket.md +0 -42
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-before-you-press-size-vs-caps.md +0 -34
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-devnet-signer-mainnet-token.md +0 -35
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-jupiter-rate-limits.md +0 -33
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-link-a-wallet.md +0 -32
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-live-trading-devnet-first.md +0 -30
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-mainnet.md +0 -31
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-the-live-fire-path-devnet-the-fast-wallet.md +0 -41
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-the-signer-process.md +0 -34
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-what-the-live-path-keeps.md +0 -37
- package/dist/packages/mcp/assets/kb/docs/docs-paper-trading-your-first-live-trade.md +0 -41
|
@@ -0,0 +1,98 @@
|
|
|
1
|
+
{
|
|
2
|
+
"kind": "strategy",
|
|
3
|
+
"schema": "dexterm-strategy/1",
|
|
4
|
+
"id": "scalp",
|
|
5
|
+
"name": "Scalp (quick play)",
|
|
6
|
+
"version": "1.0.0",
|
|
7
|
+
"description": "Fresh momentum on a young coin: a 5-minute push with buyers in control, small size, fast partial profits, a tight trail, a 20-minute clock and a -25% hard stop.",
|
|
8
|
+
"mode": "paper",
|
|
9
|
+
"bankroll": {
|
|
10
|
+
"startUsd": 1000
|
|
11
|
+
},
|
|
12
|
+
"entry": {
|
|
13
|
+
"screen": "liq >= 30K vol5m >= 5K !flag:mint !flag:freeze",
|
|
14
|
+
"ageHours": {
|
|
15
|
+
"min": 0,
|
|
16
|
+
"max": 6
|
|
17
|
+
},
|
|
18
|
+
"safety": {
|
|
19
|
+
"maxTop10Pct": 35,
|
|
20
|
+
"maxDevPct": 5,
|
|
21
|
+
"requireNoMintAuthority": true,
|
|
22
|
+
"requireNoFreezeAuthority": true,
|
|
23
|
+
"maxMcapSplitX": 5,
|
|
24
|
+
"youngVertical": {
|
|
25
|
+
"maxAgeHours": 1,
|
|
26
|
+
"maxH1Pct": 250
|
|
27
|
+
},
|
|
28
|
+
"unknownHolders": "reject"
|
|
29
|
+
},
|
|
30
|
+
"triggers": [
|
|
31
|
+
{
|
|
32
|
+
"kind": "momentum",
|
|
33
|
+
"m5MinPct": 3,
|
|
34
|
+
"buySellMin": 1.2
|
|
35
|
+
}
|
|
36
|
+
],
|
|
37
|
+
"triggerMode": "any",
|
|
38
|
+
"decide": "agent",
|
|
39
|
+
"candidateTtlSec": 300
|
|
40
|
+
},
|
|
41
|
+
"exits": {
|
|
42
|
+
"default": "scalp",
|
|
43
|
+
"profiles": [
|
|
44
|
+
"builtin:scalp",
|
|
45
|
+
"builtin:swing"
|
|
46
|
+
]
|
|
47
|
+
},
|
|
48
|
+
"sizing": {
|
|
49
|
+
"mode": "pct",
|
|
50
|
+
"pct": 5,
|
|
51
|
+
"maxPctOfBankroll": 10,
|
|
52
|
+
"maxUsd": 500,
|
|
53
|
+
"minUsd": 5
|
|
54
|
+
},
|
|
55
|
+
"risk": {
|
|
56
|
+
"perTrade": {
|
|
57
|
+
"maxLossPctOfBankroll": 10,
|
|
58
|
+
"assumedLossPctNoStop": 100
|
|
59
|
+
},
|
|
60
|
+
"dailyLossHaltPct": 10,
|
|
61
|
+
"drawdown": {
|
|
62
|
+
"sizeDownAtPct": 15,
|
|
63
|
+
"sizeDownMult": 0.5,
|
|
64
|
+
"recoverBelowPct": 8,
|
|
65
|
+
"haltAtPct": 25
|
|
66
|
+
},
|
|
67
|
+
"maxConcurrent": 2,
|
|
68
|
+
"maxExposurePct": 25,
|
|
69
|
+
"lossStreak": {
|
|
70
|
+
"losses": 3,
|
|
71
|
+
"cooldownMin": 60
|
|
72
|
+
},
|
|
73
|
+
"maxEntriesPerDay": 12,
|
|
74
|
+
"perCoin": {
|
|
75
|
+
"maxEntries": 2,
|
|
76
|
+
"cooldownMin": 10
|
|
77
|
+
}
|
|
78
|
+
},
|
|
79
|
+
"agent": {
|
|
80
|
+
"model": "sonnet",
|
|
81
|
+
"maxSessions": 2,
|
|
82
|
+
"budgetUsdPerSession": 0.5,
|
|
83
|
+
"budgetUsdPerDay": 10,
|
|
84
|
+
"maxTurns": 60,
|
|
85
|
+
"deltaEverySec": 15,
|
|
86
|
+
"decideWithinSec": 90,
|
|
87
|
+
"sessionMaxMin": 240,
|
|
88
|
+
"onTimeout": "skip"
|
|
89
|
+
},
|
|
90
|
+
"execution": {
|
|
91
|
+
"slippageBps": 100,
|
|
92
|
+
"feeBps": 30,
|
|
93
|
+
"networkFeeUsd": 0.02,
|
|
94
|
+
"latencyMs": 3000,
|
|
95
|
+
"maxPriceImpactPct": 8,
|
|
96
|
+
"minExitLiquidityUsd": 2000
|
|
97
|
+
}
|
|
98
|
+
}
|
|
@@ -0,0 +1,97 @@
|
|
|
1
|
+
{
|
|
2
|
+
"kind": "strategy",
|
|
3
|
+
"schema": "dexterm-strategy/1",
|
|
4
|
+
"id": "swing",
|
|
5
|
+
"name": "Swing (intraday trend)",
|
|
6
|
+
"version": "1.0.0",
|
|
7
|
+
"description": "An intraday trend on a coin that has already held a pool for an hour or more: medium size, thirds at +50% and +100%, a 25% trail, a 90-minute review and thesis-break exits instead of a hard stop.",
|
|
8
|
+
"mode": "paper",
|
|
9
|
+
"bankroll": {
|
|
10
|
+
"startUsd": 1000
|
|
11
|
+
},
|
|
12
|
+
"entry": {
|
|
13
|
+
"screen": "liq >= 30K vol1h > 15K !flag:mint !flag:freeze",
|
|
14
|
+
"ageHours": {
|
|
15
|
+
"min": 1,
|
|
16
|
+
"max": 168
|
|
17
|
+
},
|
|
18
|
+
"safety": {
|
|
19
|
+
"maxTop10Pct": 35,
|
|
20
|
+
"maxDevPct": 5,
|
|
21
|
+
"requireNoMintAuthority": true,
|
|
22
|
+
"requireNoFreezeAuthority": true,
|
|
23
|
+
"maxMcapSplitX": 5,
|
|
24
|
+
"youngVertical": {
|
|
25
|
+
"maxAgeHours": 1,
|
|
26
|
+
"maxH1Pct": 250
|
|
27
|
+
},
|
|
28
|
+
"unknownHolders": "reject"
|
|
29
|
+
},
|
|
30
|
+
"triggers": [
|
|
31
|
+
{
|
|
32
|
+
"kind": "screen"
|
|
33
|
+
}
|
|
34
|
+
],
|
|
35
|
+
"triggerMode": "any",
|
|
36
|
+
"decide": "agent",
|
|
37
|
+
"candidateTtlSec": 300
|
|
38
|
+
},
|
|
39
|
+
"exits": {
|
|
40
|
+
"default": "swing",
|
|
41
|
+
"profiles": [
|
|
42
|
+
"builtin:swing",
|
|
43
|
+
"builtin:runner",
|
|
44
|
+
"builtin:scalp"
|
|
45
|
+
]
|
|
46
|
+
},
|
|
47
|
+
"sizing": {
|
|
48
|
+
"mode": "pct",
|
|
49
|
+
"pct": 10,
|
|
50
|
+
"maxPctOfBankroll": 15,
|
|
51
|
+
"maxUsd": 500,
|
|
52
|
+
"minUsd": 5
|
|
53
|
+
},
|
|
54
|
+
"risk": {
|
|
55
|
+
"perTrade": {
|
|
56
|
+
"maxLossPctOfBankroll": 10,
|
|
57
|
+
"assumedLossPctNoStop": 100
|
|
58
|
+
},
|
|
59
|
+
"dailyLossHaltPct": 15,
|
|
60
|
+
"drawdown": {
|
|
61
|
+
"sizeDownAtPct": 25,
|
|
62
|
+
"sizeDownMult": 0.5,
|
|
63
|
+
"recoverBelowPct": 15,
|
|
64
|
+
"haltAtPct": 40
|
|
65
|
+
},
|
|
66
|
+
"maxConcurrent": 2,
|
|
67
|
+
"maxExposurePct": 35,
|
|
68
|
+
"lossStreak": {
|
|
69
|
+
"losses": 3,
|
|
70
|
+
"cooldownMin": 60
|
|
71
|
+
},
|
|
72
|
+
"maxEntriesPerDay": 8,
|
|
73
|
+
"perCoin": {
|
|
74
|
+
"maxEntries": 1,
|
|
75
|
+
"cooldownMin": 30
|
|
76
|
+
}
|
|
77
|
+
},
|
|
78
|
+
"agent": {
|
|
79
|
+
"model": "sonnet",
|
|
80
|
+
"maxSessions": 2,
|
|
81
|
+
"budgetUsdPerSession": 0.5,
|
|
82
|
+
"budgetUsdPerDay": 10,
|
|
83
|
+
"maxTurns": 60,
|
|
84
|
+
"deltaEverySec": 15,
|
|
85
|
+
"decideWithinSec": 90,
|
|
86
|
+
"sessionMaxMin": 240,
|
|
87
|
+
"onTimeout": "skip"
|
|
88
|
+
},
|
|
89
|
+
"execution": {
|
|
90
|
+
"slippageBps": 100,
|
|
91
|
+
"feeBps": 30,
|
|
92
|
+
"networkFeeUsd": 0.02,
|
|
93
|
+
"latencyMs": 3000,
|
|
94
|
+
"maxPriceImpactPct": 8,
|
|
95
|
+
"minExitLiquidityUsd": 2000
|
|
96
|
+
}
|
|
97
|
+
}
|
|
@@ -0,0 +1,157 @@
|
|
|
1
|
+
{
|
|
2
|
+
"kind": "strategy",
|
|
3
|
+
"schema": "dexterm-strategy/1",
|
|
4
|
+
"id": "yolo",
|
|
5
|
+
"name": "YOLO full port (HIGH RISK)",
|
|
6
|
+
"version": "1.0.0",
|
|
7
|
+
"description": "HIGH RISK, PAPER only. One early-momentum entry at a time, the biggest size the paper book allows behind it. Holder-safety gates first: LP burned or locked, no mint or freeze authority, the LARP check, minimum liquidity. Take the cost back at about 2x, then a free bag with a loose trail; thesis-break and liquidity-pull exits, a time stop, never the same coin twice. Most entries lose and one rug can zero the wallet.",
|
|
8
|
+
"mode": "paper",
|
|
9
|
+
"highRisk": true,
|
|
10
|
+
"bankroll": {
|
|
11
|
+
"startUsd": 200
|
|
12
|
+
},
|
|
13
|
+
"entry": {
|
|
14
|
+
"screen": "liq >= 25K vol5m >= 5K lplocked >= 90 !flag:mint !flag:freeze",
|
|
15
|
+
"ageHours": {
|
|
16
|
+
"min": 0,
|
|
17
|
+
"max": 2
|
|
18
|
+
},
|
|
19
|
+
"safety": {
|
|
20
|
+
"maxTop10Pct": 30,
|
|
21
|
+
"maxDevPct": 5,
|
|
22
|
+
"requireNoMintAuthority": true,
|
|
23
|
+
"requireNoFreezeAuthority": true,
|
|
24
|
+
"maxMcapSplitX": 3,
|
|
25
|
+
"youngVertical": {
|
|
26
|
+
"maxAgeHours": 2,
|
|
27
|
+
"maxH1Pct": 150
|
|
28
|
+
},
|
|
29
|
+
"unknownHolders": "reject",
|
|
30
|
+
"larp": {
|
|
31
|
+
"maxScore": 49,
|
|
32
|
+
"unknown": "reject"
|
|
33
|
+
}
|
|
34
|
+
},
|
|
35
|
+
"triggers": [
|
|
36
|
+
{
|
|
37
|
+
"kind": "momentum",
|
|
38
|
+
"m5MinPct": 3,
|
|
39
|
+
"buySellMin": 1.3
|
|
40
|
+
}
|
|
41
|
+
],
|
|
42
|
+
"triggerMode": "any",
|
|
43
|
+
"decide": "agent",
|
|
44
|
+
"candidateTtlSec": 180
|
|
45
|
+
},
|
|
46
|
+
"exits": {
|
|
47
|
+
"default": "yolo",
|
|
48
|
+
"profiles": [
|
|
49
|
+
{
|
|
50
|
+
"kind": "exit-profile",
|
|
51
|
+
"id": "yolo",
|
|
52
|
+
"name": "YOLO (cost back at 2x, free bag)",
|
|
53
|
+
"version": "1.2.0",
|
|
54
|
+
"description": "The whole stake on one young pair. At about 2x, sell the slice that pays back the position cost; the rest rides as a free bag on a loose 50% trail. Liquidity pulls, dev sells and dead volume exit at once; a -50% stop and a 45-minute time stop keep a full-port position from bleeding out slowly.",
|
|
55
|
+
"fit": {
|
|
56
|
+
"summary": "A young pair (0-2 h) with LP burned or locked, no mint or freeze authority, a LARP score below the high band, liquidity >= $25k and a first clean 5-minute push.",
|
|
57
|
+
"minLiquidityUsd": 25000,
|
|
58
|
+
"ageHours": { "min": 0, "max": 2 },
|
|
59
|
+
"maxTop10Pct": 30,
|
|
60
|
+
"signals": ["first clean 5m push with buyers ahead of sellers", "liquidity rising with price", "many distinct buyers, top-2 share low"]
|
|
61
|
+
},
|
|
62
|
+
"sizing": { "maxSizePctOfBankroll": 25 },
|
|
63
|
+
"tpLadder": [],
|
|
64
|
+
"trailingStop": null,
|
|
65
|
+
"costRecovery": { "atPct": 100, "maxSellFrac": 0.6 },
|
|
66
|
+
"bagTrail": { "trailPct": 50 },
|
|
67
|
+
"timeStop": { "minutes": 45, "ifBelowPct": 20, "action": "exit" },
|
|
68
|
+
"hardStop": {
|
|
69
|
+
"enabled": true,
|
|
70
|
+
"atPct": -50,
|
|
71
|
+
"why": "The whole wallet rides on one coin: a -50% stop ends a slow bleed. A rug or a pulled pool still fills near -100%, whatever the stop says."
|
|
72
|
+
},
|
|
73
|
+
"thesisBreak": {
|
|
74
|
+
"liquidityDropPct": 30,
|
|
75
|
+
"liquidityWindowMin": 5,
|
|
76
|
+
"mcapDivergenceX": 5,
|
|
77
|
+
"devSell": { "exitOnAnyDevSell": true, "topHolderSellPctOfBag": 30 },
|
|
78
|
+
"volumeDeath": { "m5TradesBelow": 5, "forMinutes": 20 }
|
|
79
|
+
},
|
|
80
|
+
"reentry": {
|
|
81
|
+
"allowed": false,
|
|
82
|
+
"cooldownMinutes": 0,
|
|
83
|
+
"maxEntriesPerCoinPerSession": 1,
|
|
84
|
+
"requires": "never the same coin twice: a full-port entry is never repeated"
|
|
85
|
+
},
|
|
86
|
+
"carry": { "allowed": false, "requiresTpFilled": 0, "maxRemainderPctOfBankroll": 0 },
|
|
87
|
+
"reprofileTo": [],
|
|
88
|
+
"wake": { "onTpFilled": false, "onTimeReview": false, "drawdownPct": -30, "thesisWarnFrac": 0.6, "noAnswer": "exit", "onCostRecovered": true },
|
|
89
|
+
"maxHoldMinutes": 1440,
|
|
90
|
+
"notes": [
|
|
91
|
+
"The bag trail arms on the cost-recovery sell; before that the stop, the time stop, the thesis breaks and the rug floor exit.",
|
|
92
|
+
"An agent can tighten or exit early, never loosen a stop or a trail."
|
|
93
|
+
]
|
|
94
|
+
}
|
|
95
|
+
]
|
|
96
|
+
},
|
|
97
|
+
"sizing": {
|
|
98
|
+
"mode": "pct",
|
|
99
|
+
"pct": 25,
|
|
100
|
+
"maxPctOfBankroll": 25,
|
|
101
|
+
"maxUsd": 1000,
|
|
102
|
+
"minUsd": 5
|
|
103
|
+
},
|
|
104
|
+
"risk": {
|
|
105
|
+
"perTrade": {
|
|
106
|
+
"maxLossPctOfBankroll": 25,
|
|
107
|
+
"assumedLossPctNoStop": 100
|
|
108
|
+
},
|
|
109
|
+
"dailyLossHaltPct": 60,
|
|
110
|
+
"drawdown": {
|
|
111
|
+
"sizeDownAtPct": 50,
|
|
112
|
+
"sizeDownMult": 1,
|
|
113
|
+
"recoverBelowPct": 10,
|
|
114
|
+
"haltAtPct": 80
|
|
115
|
+
},
|
|
116
|
+
"maxConcurrent": 1,
|
|
117
|
+
"maxExposurePct": 100,
|
|
118
|
+
"lossStreak": {
|
|
119
|
+
"losses": 3,
|
|
120
|
+
"cooldownMin": 60
|
|
121
|
+
},
|
|
122
|
+
"maxEntriesPerDay": 6,
|
|
123
|
+
"perCoin": {
|
|
124
|
+
"maxEntries": 1,
|
|
125
|
+
"cooldownMin": 10080
|
|
126
|
+
},
|
|
127
|
+
"recoveredBags": {
|
|
128
|
+
"countAsOpen": true,
|
|
129
|
+
"maxBags": 1
|
|
130
|
+
}
|
|
131
|
+
},
|
|
132
|
+
"agent": {
|
|
133
|
+
"model": "sonnet",
|
|
134
|
+
"maxSessions": 1,
|
|
135
|
+
"budgetUsdPerSession": 0.5,
|
|
136
|
+
"budgetUsdPerDay": 5,
|
|
137
|
+
"maxTurns": 60,
|
|
138
|
+
"deltaEverySec": 15,
|
|
139
|
+
"decideWithinSec": 45,
|
|
140
|
+
"sessionMaxMin": 240,
|
|
141
|
+
"onTimeout": "skip"
|
|
142
|
+
},
|
|
143
|
+
"execution": {
|
|
144
|
+
"slippageBps": 300,
|
|
145
|
+
"feeBps": 30,
|
|
146
|
+
"networkFeeUsd": 0.02,
|
|
147
|
+
"latencyMs": 3000,
|
|
148
|
+
"maxPriceImpactPct": 3,
|
|
149
|
+
"minExitLiquidityUsd": 5000
|
|
150
|
+
},
|
|
151
|
+
"notes": [
|
|
152
|
+
"HIGH RISK. Paper only: dexterm holds no key and places no live order. Experimental; not financial advice. Self-directed only.",
|
|
153
|
+
"Paper: the runner's book caps one position at 25% (the ceiling for every strategy); the replay below measures full port.",
|
|
154
|
+
"Run it: `dexterm autotrade run yolo --paper` (`--replay builtin:yolo-rehearsal --stub` for a short fixture run).",
|
|
155
|
+
"`dexterm autotrade yolo-replay yolo` shows what full-port compounding did on your recorded history: rugs, the loss spread and how often it zeroed the wallet."
|
|
156
|
+
]
|
|
157
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"schema":"dexterm-autotrade-tape/1","source":"FIXTURE: yolo devnet rehearsal (synthetic)","extractedAt":"2026-10-22T00:00:00.000Z","window":{"from":1792800000000,"to":1792805940000},"note":"REHEARSAL FIXTURE, NOT MARKET DATA. Synthetic price paths written for the yolo devnet rehearsal, on three real, long-lived mainnet mint addresses (so the devnet signer can read their mint and freeze authority and their liquidity). The symbols, prices, ages and liquidity here are made up. Paths: a 3x push with the cost taken back and the bag trailed out; a flat entry the time stop closes; a pool pulled by half (the liquidity-pull exit). Never a performance sample.","columns":["t","kind","price","mcap","mcapResolved","mcapFlagged","liq","vol5m","vol1h","vol24","buys5m","sells5m","buys24","sells24","chg5m","chg1h","chg6h","chg24h","holders","top10","dev","mintAuth","freezeAuth","org"],"mints":[{"mint":"DezXAZ8z7PnrnRJjz3wXBoRgixCa6xjnB7YaB1pPB263","symbol":"REHA","launchpad":"pump.fun","createdAt":1792798800000,"rows":[[1792800000000,"live",1e-05,10000,10000,0,60000,10800.0,108000.0,540000.0,40,20,800,400,5.0,0.0,0.0,0.0,900,22.5,2.1,0,0,62.0],[1792800060000,"live",1.25e-05,12500,12500,0,66000,11700.0,117000.0,585000.0,45,20,900,400,25.0,25.0,25.0,25.0,905,22.5,2.1,0,0,62.0],[1792800120000,"live",1.5000000000000002e-05,15000,15000,0,72000,11700.0,117000.0,585000.0,45,20,900,400,50.0,50.0,50.0,50.0,910,22.5,2.1,0,0,62.0],[1792800180000,"live",1.7500000000000002e-05,17500,17500,0,78000,11700.0,117000.0,585000.0,45,20,900,400,75.0,75.0,75.0,75.0,915,22.5,2.1,0,0,62.0],[1792800240000,"live",2e-05,20000,20000,0,84000,11700.0,117000.0,585000.0,45,20,900,400,100.0,100.0,100.0,100.0,920,22.5,2.1,0,0,62.0],[1792800300000,"live",2.25e-05,22500,22500,0,90000,11700.0,117000.0,585000.0,45,20,900,400,125.0,125.0,125.0,125.0,925,22.5,2.1,0,0,62.0],[1792800360000,"live",2.5e-05,25000,25000,0,96000,11700.0,117000.0,585000.0,45,20,900,400,100.0,150.0,150.0,150.0,930,22.5,2.1,0,0,62.0],[1792800420000,"live",2.75e-05,27500,27500,0,102000,11700.0,117000.0,585000.0,45,20,900,400,83.33,175.0,175.0,175.0,935,22.5,2.1,0,0,62.0],[1792800480000,"live",3.0000000000000004e-05,30000,30000,0,108000,11700.0,117000.0,585000.0,45,20,900,400,71.43,200.0,200.0,200.0,940,22.5,2.1,0,0,62.0],[1792800540000,"live",2.7899999999999997e-05,27900,27900,0,106000,9900.0,99000.0,495000.0,25,30,500,600,39.5,179.0,179.0,179.0,945,22.5,2.1,0,0,62.0],[1792800600000,"live",2.58e-05,25800,25800,0,104000,9900.0,99000.0,495000.0,25,30,500,600,14.67,158.0,158.0,158.0,950,22.5,2.1,0,0,62.0],[1792800660000,"live",2.37e-05,23700,23700,0,102000,9900.0,99000.0,495000.0,25,30,500,600,-5.2,137.0,137.0,137.0,955,22.5,2.1,0,0,62.0],[1792800720000,"live",2.16e-05,21600,21600,0,100000,9900.0,99000.0,495000.0,25,30,500,600,-21.45,116.0,116.0,116.0,960,22.5,2.1,0,0,62.0],[1792800780000,"live",1.9499999999999996e-05,19500,19500,0,98000,9900.0,99000.0,495000.0,25,30,500,600,-35.0,95.0,95.0,95.0,965,22.5,2.1,0,0,62.0],[1792800840000,"live",1.74e-05,17400,17400,0,96000,9900.0,99000.0,495000.0,25,30,500,600,-37.63,74.0,74.0,74.0,970,22.5,2.1,0,0,62.0],[1792800900000,"live",1.53e-05,15300,15300,0,94000,9900.0,99000.0,495000.0,25,30,500,600,-40.7,53.0,53.0,53.0,975,22.5,2.1,0,0,62.0],[1792800960000,"live",1.3199999999999999e-05,13200,13200,0,92000,9900.0,99000.0,495000.0,25,30,500,600,-44.3,32.0,32.0,32.0,980,22.5,2.1,0,0,62.0],[1792801020000,"live",1.32e-05,13200,13200,0,92000,5400.0,54000.0,270000.0,15,15,300,300,-38.89,32.0,32.0,32.0,985,22.5,2.1,0,0,62.0],[1792801080000,"live",1.32e-05,13200,13200,0,92000,5400.0,54000.0,270000.0,15,15,300,300,-32.31,32.0,32.0,32.0,990,22.5,2.1,0,0,62.0],[1792801140000,"live",1.32e-05,13200,13200,0,92000,5400.0,54000.0,270000.0,15,15,300,300,-24.14,32.0,32.0,32.0,995,22.5,2.1,0,0,62.0],[1792801200000,"live",1.32e-05,13200,13200,0,92000,5400.0,54000.0,270000.0,15,15,300,300,-13.73,32.0,32.0,32.0,1000,22.5,2.1,0,0,62.0]]},{"mint":"7GCihgDB8fe6KNjn2MYtkzZcRjQy3t9GHdC8uHYmW2hr","symbol":"REHC","launchpad":"pump.fun","createdAt":1792800600000,"rows":[[1792801800000,"live",2e-05,20000,20000,0,70000,10800.0,108000.0,540000.0,40,20,800,400,5.0,0.0,0.0,0.0,900,22.5,2.1,0,0,62.0],[1792801860000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,3.0,3.0,3.0,3.0,905,22.5,2.1,0,0,62.0],[1792801920000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-2.0,-2.0,-2.0,-2.0,910,22.5,2.1,0,0,62.0],[1792801980000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,3.0,3.0,3.0,3.0,915,22.5,2.1,0,0,62.0],[1792802040000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-2.0,-2.0,-2.0,-2.0,920,22.5,2.1,0,0,62.0],[1792802100000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,3.0,3.0,3.0,3.0,925,22.5,2.1,0,0,62.0],[1792802160000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,930,22.5,2.1,0,0,62.0],[1792802220000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,935,22.5,2.1,0,0,62.0],[1792802280000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,940,22.5,2.1,0,0,62.0],[1792802340000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,945,22.5,2.1,0,0,62.0],[1792802400000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,950,22.5,2.1,0,0,62.0],[1792802460000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,955,22.5,2.1,0,0,62.0],[1792802520000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,960,22.5,2.1,0,0,62.0],[1792802580000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,965,22.5,2.1,0,0,62.0],[1792802640000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,970,22.5,2.1,0,0,62.0],[1792802700000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,975,22.5,2.1,0,0,62.0],[1792802760000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,980,22.5,2.1,0,0,62.0],[1792802820000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,985,22.5,2.1,0,0,62.0],[1792802880000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,990,22.5,2.1,0,0,62.0],[1792802940000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,995,22.5,2.1,0,0,62.0],[1792803000000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,1000,22.5,2.1,0,0,62.0],[1792803060000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,1005,22.5,2.1,0,0,62.0],[1792803120000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,1010,22.5,2.1,0,0,62.0],[1792803180000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,1015,22.5,2.1,0,0,62.0],[1792803240000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,1020,22.5,2.1,0,0,62.0],[1792803300000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,1025,22.5,2.1,0,0,62.0],[1792803360000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,1030,22.5,2.1,0,0,62.0],[1792803420000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,1035,22.5,2.1,0,0,62.0],[1792803480000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,1040,22.5,2.1,0,0,62.0],[1792803540000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,1045,22.5,2.1,0,0,62.0],[1792803600000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,1050,22.5,2.1,0,0,62.0],[1792803660000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,1055,22.5,2.1,0,0,62.0],[1792803720000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,1060,22.5,2.1,0,0,62.0],[1792803780000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,1065,22.5,2.1,0,0,62.0],[1792803840000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,1070,22.5,2.1,0,0,62.0],[1792803900000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,1075,22.5,2.1,0,0,62.0],[1792803960000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,1080,22.5,2.1,0,0,62.0],[1792804020000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,1085,22.5,2.1,0,0,62.0],[1792804080000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,1090,22.5,2.1,0,0,62.0],[1792804140000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,1095,22.5,2.1,0,0,62.0],[1792804200000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,1100,22.5,2.1,0,0,62.0],[1792804260000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,1105,22.5,2.1,0,0,62.0],[1792804320000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,1110,22.5,2.1,0,0,62.0],[1792804380000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,1115,22.5,2.1,0,0,62.0],[1792804440000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,1120,22.5,2.1,0,0,62.0],[1792804500000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,1125,22.5,2.1,0,0,62.0],[1792804560000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,1130,22.5,2.1,0,0,62.0],[1792804620000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,1135,22.5,2.1,0,0,62.0],[1792804680000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,1140,22.5,2.1,0,0,62.0],[1792804740000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,1145,22.5,2.1,0,0,62.0],[1792804800000,"live",1.9600000000000002e-05,19600,19600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,-4.85,-2.0,-2.0,-2.0,1150,22.5,2.1,0,0,62.0],[1792804860000,"live",2.0600000000000003e-05,20600,20600,0,70000,4320.0,43200.0,216000.0,12,12,240,240,5.1,3.0,3.0,3.0,1155,22.5,2.1,0,0,62.0]]},{"mint":"EKpQGSJtjMFqKZ9KQanSqYXRcF8fBopzLHYxdM65zcjm","symbol":"REHB","launchpad":"pump.fun","createdAt":1792804200000,"rows":[[1792805400000,"live",5e-06,5000,5000,0,80000,10800.0,108000.0,540000.0,40,20,800,400,5.0,0.0,0.0,0.0,900,22.5,2.1,0,0,62.0],[1792805460000,"live",5.2e-06,5200,5200,0,81000,9000.0,90000.0,450000.0,30,20,600,400,4.0,4.0,4.0,4.0,905,22.5,2.1,0,0,62.0],[1792805520000,"live",5.1e-06,5100,5100,0,80500,7560.0,75600.0,378000.0,20,22,400,440,2.0,2.0,2.0,2.0,910,22.5,2.1,0,0,62.0],[1792805580000,"live",2.4e-06,2400,2400,0,40000,12600.0,126000.0,630000.0,10,60,200,1200,-52.0,-52.0,-52.0,-52.0,915,22.5,2.1,0,0,62.0],[1792805640000,"live",1.9e-06,1900,1900,0,36000,8640.0,86400.0,432000.0,8,40,160,800,-62.0,-62.0,-62.0,-62.0,920,22.5,2.1,0,0,62.0],[1792805700000,"live",1.8e-06,1800,1800,0,35000,2880.0,28800.0,144000.0,6,10,120,200,-64.0,-64.0,-64.0,-64.0,925,22.5,2.1,0,0,62.0],[1792805760000,"live",1.8e-06,1800,1800,0,35000,2880.0,28800.0,144000.0,6,10,120,200,-65.38,-64.0,-64.0,-64.0,930,22.5,2.1,0,0,62.0],[1792805820000,"live",1.8e-06,1800,1800,0,35000,2880.0,28800.0,144000.0,6,10,120,200,-64.71,-64.0,-64.0,-64.0,935,22.5,2.1,0,0,62.0],[1792805880000,"live",1.8e-06,1800,1800,0,35000,2880.0,28800.0,144000.0,6,10,120,200,-25.0,-64.0,-64.0,-64.0,940,22.5,2.1,0,0,62.0],[1792805940000,"live",1.8e-06,1800,1800,0,35000,2880.0,28800.0,144000.0,6,10,120,200,-5.26,-64.0,-64.0,-64.0,945,22.5,2.1,0,0,62.0]]}]}
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
# dexterm executor reference kit
|
|
2
|
+
|
|
3
|
+
dexterm holds no key and signs nothing. In real mode a strategy sends a **LIVE TRADE FIRE** signal
|
|
4
|
+
(`dexterm-trade-fire/1`) for every buy and sell. **Your own executor** acts on it: a Telegram trading bot you chose,
|
|
5
|
+
or any script.
|
|
6
|
+
|
|
7
|
+
This folder holds three small executors you can wire up in minutes, so you can see the whole path work before
|
|
8
|
+
anything can spend money:
|
|
9
|
+
|
|
10
|
+
| file | channel | how dexterm reaches it |
|
|
11
|
+
|---|---|---|
|
|
12
|
+
| `webhook-executor.mjs` | webhook | `dexterm autotrade signal channels --webhook http://127.0.0.1:8787/signal` |
|
|
13
|
+
| `signal-cmd-executor.mjs` | command hook | `dexterm autotrade signal channels --signal-cmd '["/abs/node","/abs/signal-cmd-executor.mjs","--account","main"]'` |
|
|
14
|
+
| `jsonl-tail-executor.mjs` | JSONL stream | `dexterm autotrade signal channels --jsonl on` (add `--jsonl-signed on` for HMAC lines) |
|
|
15
|
+
|
|
16
|
+
Each one handles every signal the same way:
|
|
17
|
+
|
|
18
|
+
1. It verifies the HMAC, when you give it the secret file. Without `--secret-file` it acts on unsigned bodies (it says `HMAC NOT checked` when it starts); before you put a real trade into `act()`, run it with `--secret-file` and `--require-hmac`.
|
|
19
|
+
2. It checks the account id.
|
|
20
|
+
3. It dedupes by nonce. Delivery is at-least-once, so a repeat is normal, and the seen set survives a restart.
|
|
21
|
+
4. It ignores anything past `expiresAt` (the TTL).
|
|
22
|
+
5. It writes a receipt to dexterm's `autotrade/real/receipts.jsonl` and a heartbeat to `autotrade/real/executor.jsonl`.
|
|
23
|
+
|
|
24
|
+
**All of them are DRY RUN.** `act()` in `kit.mjs` only logs what it WOULD do, and the receipt says so:
|
|
25
|
+
status `rejected`, reason `dry-run: would BUY …`. There is no wallet code, no key and no chain call anywhere in this
|
|
26
|
+
kit. Trading for real means replacing `act()` with your own code, or handing the order to your own bot. That is your
|
|
27
|
+
code and your wallet, never dexterm's.
|
|
28
|
+
|
|
29
|
+
## Five minutes, end to end (paper money only)
|
|
30
|
+
|
|
31
|
+
```sh
|
|
32
|
+
# 1. a secret for the HMAC (written to a 0600 file, stored in your keychain, never printed)
|
|
33
|
+
dexterm autotrade signal secret generate --out ~/.dexterm-exec.secret
|
|
34
|
+
|
|
35
|
+
# 2. start the kit's webhook executor (dry run) in another terminal
|
|
36
|
+
node webhook-executor.mjs --account main --secret-file ~/.dexterm-exec.secret
|
|
37
|
+
|
|
38
|
+
# 3. point dexterm at it, then prove the round trip
|
|
39
|
+
dexterm autotrade signal channels --webhook http://127.0.0.1:8787/signal
|
|
40
|
+
dexterm autotrade signal test # per channel: delivered, latency, the kit's receipt
|
|
41
|
+
dexterm autotrade executor status # alive · last heartbeat · last receipt · lag
|
|
42
|
+
```
|
|
43
|
+
|
|
44
|
+
`signal test` sends a signal marked `test: true` that names no mint, so there is nothing in it to trade. The kit
|
|
45
|
+
receipts it as `rejected` (`test signal: received, never traded`).
|
|
46
|
+
|
|
47
|
+
## Heartbeats and the silence pause
|
|
48
|
+
|
|
49
|
+
dexterm counts a heartbeat, a receipt, or an ack on the webhook or command hook as a sign of life. When it hears
|
|
50
|
+
nothing for longer than your `executorSilenceMin` limit (placeholder: 15 min), a real run **pauses new buy
|
|
51
|
+
signals** and tells you in the run log and on Telegram. Exits keep going out. The kit sends a heartbeat every 60 s
|
|
52
|
+
(`--heartbeat-sec`). Your own executor can append the same line, POST it to the run's loopback listener
|
|
53
|
+
(`--executor-port`), or run `dexterm autotrade executor heartbeat`:
|
|
54
|
+
|
|
55
|
+
```json
|
|
56
|
+
{"schema":"dexterm-executor-heartbeat/1","at":1761300000000,"executor":"my-bot","accountId":"main","dryRun":false,"lastNonce":42}
|
|
57
|
+
```
|
|
58
|
+
|
|
59
|
+
## Receipts
|
|
60
|
+
|
|
61
|
+
A receipt is data only. It moves a real position from `unconfirmed` to executed / rejected / failed. With a fill
|
|
62
|
+
(`priceUsd`, `sizeSol`, `tokens`, `txSig`), dexterm also measures how far the real fill was from its own paper fill:
|
|
63
|
+
slippage, latency, partial fills and rejections. That shows in `dexterm autotrade audit`, `signal status` and
|
|
64
|
+
`dexterm autotrade report`.
|
|
65
|
+
|
|
66
|
+
```json
|
|
67
|
+
{"schema":"dexterm-trade-receipt/1","signalId":"<the signal's id>","nonce":42,"accountId":"main","status":"executed","at":1761300001200,"fill":{"priceUsd":0.00123,"sizeSol":0.25,"tokens":40650,"txSig":null},"reason":null,"executor":"my-bot"}
|
|
68
|
+
```
|
|
69
|
+
|
|
70
|
+
See `telegram-bot-recipe.md` for the Telegram trading-bot setup. The bot executes, and dexterm never signs.
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
// dexterm executor reference kit: the JSONL stream tail (task-1654). DRY RUN: logs what it would do; no wallet code.
|
|
3
|
+
//
|
|
4
|
+
// node jsonl-tail-executor.mjs --account main [--stream FILE] [--secret-file FILE --require-hmac] [--once] [--poll-ms 1000]
|
|
5
|
+
//
|
|
6
|
+
// Turn the stream on in dexterm (`dexterm autotrade signal channels --jsonl on`, default file
|
|
7
|
+
// autotrade/real/signals.jsonl). With `--jsonl-signed on` each line is an HMAC envelope this tail verifies; a bare
|
|
8
|
+
// line has no signature, so --require-hmac refuses it. The read offset is saved, so a restart resumes where it was.
|
|
9
|
+
// --once reads what is there and exits (handy for a test).
|
|
10
|
+
|
|
11
|
+
import { closeSync, existsSync, openSync, readFileSync, readSync, statSync, writeFileSync } from 'node:fs';
|
|
12
|
+
import { join } from 'node:path';
|
|
13
|
+
import { SeenStore, args, dextermHome, handle, heartbeat, readSecret, realDir, unwrapLine } from './kit.mjs';
|
|
14
|
+
|
|
15
|
+
const a = args();
|
|
16
|
+
if (!a.account) { console.error('usage: node jsonl-tail-executor.mjs --account ID [--stream FILE] [--secret-file FILE] [--once]'); process.exit(2); }
|
|
17
|
+
const home = a.home || dextermHome();
|
|
18
|
+
const stream = a.stream || join(realDir(home), 'signals.jsonl');
|
|
19
|
+
const offFile = a['offset-file'] || join(realDir(home), 'kit-tail-offset.json');
|
|
20
|
+
const seen = new SeenStore(a.state || join(realDir(home), 'kit-tail-seen.json'));
|
|
21
|
+
const secret = readSecret(a['secret-file']);
|
|
22
|
+
const name = String(a.name || 'kit-jsonl-tail').slice(0, 32);
|
|
23
|
+
const log = (s) => console.log(`[${new Date().toISOString()}] ${s}`);
|
|
24
|
+
let offset = 0;
|
|
25
|
+
try { offset = Number(JSON.parse(readFileSync(offFile, 'utf8')).offset) || 0; } catch { /* from the start */ }
|
|
26
|
+
let carry = '';
|
|
27
|
+
|
|
28
|
+
function poll() {
|
|
29
|
+
if (!existsSync(stream)) return;
|
|
30
|
+
const size = statSync(stream).size;
|
|
31
|
+
if (size < offset) { offset = 0; carry = ''; }
|
|
32
|
+
if (size === offset) return;
|
|
33
|
+
const fd = openSync(stream, 'r');
|
|
34
|
+
const buf = Buffer.alloc(size - offset);
|
|
35
|
+
try { readSync(fd, buf, 0, buf.length, offset); } finally { closeSync(fd); }
|
|
36
|
+
offset = size;
|
|
37
|
+
const lines = (carry + buf.toString('utf8')).split('\n');
|
|
38
|
+
carry = lines.pop() ?? '';
|
|
39
|
+
for (const l of lines) {
|
|
40
|
+
if (!l.trim()) continue;
|
|
41
|
+
const { body, signature } = unwrapLine(l);
|
|
42
|
+
handle(body, { accountId: a.account, secret, requireHmac: !!a['require-hmac'], signature, seen, home, executor: name, log, now: Date.now() });
|
|
43
|
+
}
|
|
44
|
+
writeFileSync(offFile, JSON.stringify({ offset: offset - Buffer.byteLength(carry) }));
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
const beat = () => { try { heartbeat(home, { executor: name, accountId: a.account, lastNonce: seen.maxNonce || null }); } catch (e) { log(`heartbeat failed: ${e.message}`); } };
|
|
48
|
+
poll();
|
|
49
|
+
beat();
|
|
50
|
+
if (!a.once) {
|
|
51
|
+
log(`dexterm kit JSONL tail executor (DRY RUN) on ${stream} · account ${a.account}`);
|
|
52
|
+
const t1 = setInterval(poll, Math.max(100, Number(a['poll-ms'] ?? 1000)));
|
|
53
|
+
const t2 = setInterval(beat, Math.max(5, Number(a['heartbeat-sec'] ?? 60)) * 1000);
|
|
54
|
+
const stop = () => { clearInterval(t1); clearInterval(t2); process.exit(0); };
|
|
55
|
+
process.on('SIGINT', stop);
|
|
56
|
+
process.on('SIGTERM', stop);
|
|
57
|
+
}
|
|
@@ -0,0 +1,144 @@
|
|
|
1
|
+
// dexterm executor reference kit: the shared part (task-1654). Plain Node (22+), no dependencies, no wallet code.
|
|
2
|
+
//
|
|
3
|
+
// Every kit executor does the same five things with a LIVE TRADE FIRE signal (`dexterm-trade-fire/1`):
|
|
4
|
+
// 1. verify the HMAC (`t=<unix s>,v1=<hex sha256 of "<t>.<body>">`) when you gave it the secret file
|
|
5
|
+
// 2. check the shape, and that the signal is for YOUR account id
|
|
6
|
+
// 3. dedupe by nonce and id (delivery is at-least-once: a repeat is normal); the seen set survives a restart
|
|
7
|
+
// 4. honor the TTL: anything past `expiresAt` is ignored, never acted on late
|
|
8
|
+
// 5. write a receipt (`dexterm-trade-receipt/1`) to dexterm's receipts.jsonl, and a heartbeat now and then
|
|
9
|
+
//
|
|
10
|
+
// It is DRY RUN, always: `act()` below only logs what it WOULD do and the receipt says so (status "rejected",
|
|
11
|
+
// reason "dry-run: …"). There is no key, no wallet and no chain call in this kit. To trade for real you replace
|
|
12
|
+
// `act()` with your own executor's code (or hand the order to the Telegram trading bot you chose); dexterm never
|
|
13
|
+
// signs anything.
|
|
14
|
+
|
|
15
|
+
import { createHmac, timingSafeEqual } from 'node:crypto';
|
|
16
|
+
import { appendFileSync, existsSync, mkdirSync, readFileSync, writeFileSync, renameSync } from 'node:fs';
|
|
17
|
+
import { dirname, join } from 'node:path';
|
|
18
|
+
import { homedir } from 'node:os';
|
|
19
|
+
|
|
20
|
+
export const SIGNAL_SCHEMA = 'dexterm-trade-fire/1';
|
|
21
|
+
export const RECEIPT_SCHEMA = 'dexterm-trade-receipt/1';
|
|
22
|
+
export const HEARTBEAT_SCHEMA = 'dexterm-executor-heartbeat/1';
|
|
23
|
+
export const ENVELOPE_SCHEMA = 'dexterm-trade-fire-envelope/1';
|
|
24
|
+
const TOLERANCE_SEC = 300;
|
|
25
|
+
const MINT = /^[1-9A-HJ-NP-Za-km-z]{32,44}$/;
|
|
26
|
+
|
|
27
|
+
/** `--name value` / `--flag` argv into an object. */
|
|
28
|
+
export function args(argv = process.argv.slice(2)) {
|
|
29
|
+
const o = {};
|
|
30
|
+
for (let i = 0; i < argv.length; i++) {
|
|
31
|
+
const a = argv[i];
|
|
32
|
+
if (!a.startsWith('--')) continue;
|
|
33
|
+
const k = a.slice(2);
|
|
34
|
+
const v = argv[i + 1];
|
|
35
|
+
if (v !== undefined && !v.startsWith('--')) { o[k] = v; i++; } else o[k] = true;
|
|
36
|
+
}
|
|
37
|
+
return o;
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
/** Where dexterm keeps its files (DEXTERM_HOME, else ~/.dexterm). */
|
|
41
|
+
export const dextermHome = (env = process.env) => env.DEXTERM_HOME || join(homedir(), '.dexterm');
|
|
42
|
+
export const realDir = (home) => join(home, 'autotrade', 'real');
|
|
43
|
+
|
|
44
|
+
/** The HMAC secret from a file (`dexterm autotrade signal secret generate --out FILE`), or null. */
|
|
45
|
+
export function readSecret(file) {
|
|
46
|
+
if (!file) return null;
|
|
47
|
+
const v = readFileSync(file, 'utf8').trim();
|
|
48
|
+
return v || null;
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
export function verify(secret, header, body, nowMs = Date.now()) {
|
|
52
|
+
const m = /^t=(\d{1,12}),v1=([0-9a-f]{64})$/.exec(String(header ?? ''));
|
|
53
|
+
if (!m) return { ok: false, why: 'signature-missing' };
|
|
54
|
+
const t = Number(m[1]);
|
|
55
|
+
if (Math.abs(nowMs / 1000 - t) > TOLERANCE_SEC) return { ok: false, why: 'signature-stale' };
|
|
56
|
+
const want = createHmac('sha256', secret).update(`${t}.${body}`).digest();
|
|
57
|
+
const got = Buffer.from(m[2], 'hex');
|
|
58
|
+
return got.length === want.length && timingSafeEqual(got, want) ? { ok: true } : { ok: false, why: 'signature-bad' };
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
/** The seen nonces and ids, in a small JSON file so a restart does not act on a repeat. */
|
|
62
|
+
export class SeenStore {
|
|
63
|
+
constructor(file) { this.file = file; this.seen = new Set(); this.maxNonce = 0; try { const d = JSON.parse(readFileSync(file, 'utf8')); for (const x of d.seen ?? []) this.seen.add(x); this.maxNonce = Number(d.maxNonce) || 0; } catch { /* first run */ } }
|
|
64
|
+
has(s) { return this.seen.has(s.id) || this.seen.has(`n${s.nonce}`); }
|
|
65
|
+
add(s) {
|
|
66
|
+
this.seen.add(s.id); this.seen.add(`n${s.nonce}`); this.maxNonce = Math.max(this.maxNonce, s.nonce);
|
|
67
|
+
const keep = [...this.seen].slice(-4000);
|
|
68
|
+
mkdirSync(dirname(this.file), { recursive: true });
|
|
69
|
+
const tmp = `${this.file}.${process.pid}.tmp`;
|
|
70
|
+
writeFileSync(tmp, JSON.stringify({ seen: keep, maxNonce: this.maxNonce }));
|
|
71
|
+
renameSync(tmp, this.file);
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
/**
|
|
76
|
+
* Check one signal body. Returns { verdict, signal?, why }: verdict is act | duplicate | expired | rejected.
|
|
77
|
+
* `secret` null = no HMAC check (only when you chose not to set one).
|
|
78
|
+
*/
|
|
79
|
+
export function check(body, o) {
|
|
80
|
+
const now = o.now ?? Date.now();
|
|
81
|
+
if (o.secret) { const v = verify(o.secret, o.signature, body, now); if (!v.ok) return { verdict: 'rejected', why: v.why }; }
|
|
82
|
+
else if (o.requireHmac) return { verdict: 'rejected', why: 'signature-required' };
|
|
83
|
+
let s;
|
|
84
|
+
try { s = JSON.parse(body); } catch { return { verdict: 'rejected', why: 'not-json' }; }
|
|
85
|
+
if (!s || s.schema !== SIGNAL_SCHEMA || !['trade', 'halted', 'test'].includes(s.type) || !Number.isSafeInteger(s.nonce) || typeof s.id !== 'string') return { verdict: 'rejected', why: 'shape' };
|
|
86
|
+
if (s.paper !== false) return { verdict: 'rejected', why: 'paper-flag' };
|
|
87
|
+
if (s.accountId !== o.accountId) return { verdict: 'rejected', why: 'wrong-account', signal: s };
|
|
88
|
+
if (o.seen.has(s)) return { verdict: 'duplicate', why: 'duplicate', signal: s };
|
|
89
|
+
if (!(now <= s.expiresAt)) return { verdict: 'expired', why: 'expired', signal: s };
|
|
90
|
+
if (s.type === 'trade' && (!MINT.test(s.mint) || (s.side !== 'buy' && s.side !== 'sell'))) return { verdict: 'rejected', why: 'shape', signal: s };
|
|
91
|
+
if (s.type === 'trade' && s.nonce <= o.seen.maxNonce) return { verdict: 'rejected', why: 'nonce-replay', signal: s };
|
|
92
|
+
return { verdict: 'act', why: null, signal: s };
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
/**
|
|
96
|
+
* What the executor does with a fresh signal. DRY RUN: it only says what it WOULD do. Replace this with your own
|
|
97
|
+
* code to trade (your wallet, your bot); keep the rest of the pipeline (verify, dedupe, TTL, receipt) as it is.
|
|
98
|
+
*/
|
|
99
|
+
export function act(s) {
|
|
100
|
+
if (s.type === 'test') return { status: 'rejected', reason: 'test signal: received, never traded' };
|
|
101
|
+
if (s.type === 'halted') return { status: null, reason: `halted (${s.reason}): would cancel ${s.outstanding.length} outstanding signal(s)` };
|
|
102
|
+
const what = s.side === 'buy' ? `would BUY ${s.sizeSol} SOL of ${s.symbol} (${s.mint}) with ${s.slippageBps} bps slippage` : `would SELL ${Math.round(s.sellFraction * 1000) / 10}% of ${s.symbol} (${s.mint}): ${s.exitReason}`;
|
|
103
|
+
return { status: 'rejected', reason: `dry-run: ${what}`.slice(0, 120) };
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
/** Append a receipt line to dexterm's receipts.jsonl (the same file `dexterm autotrade receipt` writes). */
|
|
107
|
+
export function writeReceipt(home, s, r, executor, now = Date.now()) {
|
|
108
|
+
const line = { schema: RECEIPT_SCHEMA, signalId: s.id, nonce: s.nonce, accountId: s.accountId, status: r.status, at: now, fill: r.fill ?? null, reason: r.reason ?? null, executor };
|
|
109
|
+
mkdirSync(realDir(home), { recursive: true, mode: 0o700 });
|
|
110
|
+
appendFileSync(join(realDir(home), 'receipts.jsonl'), `${JSON.stringify(line)}\n`, { mode: 0o600 });
|
|
111
|
+
return line;
|
|
112
|
+
}
|
|
113
|
+
|
|
114
|
+
/** Append a heartbeat to dexterm's executor.jsonl: dexterm pauses new buys when it hears nothing for too long. */
|
|
115
|
+
export function heartbeat(home, o) {
|
|
116
|
+
const hb = { schema: HEARTBEAT_SCHEMA, at: o.now ?? Date.now(), executor: o.executor, accountId: o.accountId ?? null, dryRun: true, lastNonce: o.lastNonce ?? null, note: o.note ?? null };
|
|
117
|
+
mkdirSync(realDir(home), { recursive: true, mode: 0o700 });
|
|
118
|
+
appendFileSync(join(realDir(home), 'executor.jsonl'), `${JSON.stringify(hb)}\n`, { mode: 0o600 });
|
|
119
|
+
return hb;
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
/** The whole pipeline for one body: check, act (dry run), receipt, log line. Returns the verdict. */
|
|
123
|
+
export function handle(body, o) {
|
|
124
|
+
const c = check(body, o);
|
|
125
|
+
const s = c.signal;
|
|
126
|
+
if (c.verdict === 'act') {
|
|
127
|
+
o.seen.add(s);
|
|
128
|
+
const r = act(s);
|
|
129
|
+
if (r.status && s.type !== 'halted') writeReceipt(o.home, s, r, o.executor, o.now ?? Date.now());
|
|
130
|
+
o.log(`#${s.nonce} ${s.type}${s.type === 'trade' ? ` ${s.side}` : ''}: ${r.reason}`);
|
|
131
|
+
} else o.log(`${s ? `#${s.nonce} ` : ''}${c.verdict}: ${c.why}`);
|
|
132
|
+
return c;
|
|
133
|
+
}
|
|
134
|
+
|
|
135
|
+
/** A stream line: a bare signal, or a signed envelope (`dexterm autotrade signal channels --jsonl-signed on`). */
|
|
136
|
+
export function unwrapLine(line) {
|
|
137
|
+
try {
|
|
138
|
+
const x = JSON.parse(line);
|
|
139
|
+
if (x && x.schema === ENVELOPE_SCHEMA && typeof x.signal === 'string') return { body: x.signal, signature: x.signature ?? null };
|
|
140
|
+
} catch { /* handled by check() */ }
|
|
141
|
+
return { body: line, signature: null };
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
export const exists = existsSync;
|