82 KiB
# Bytelyst Trading Platform - Holistic Engineering + Trading Audit
Date: 2026-02-15
Scope: bytelyst-trading-bot-service + bytelyst-trading-dashboard-web
Method: static code review, build/lint checks, lifecycle-path trace (orders -> positions -> history)
Related Docs
- Product runtime flow and execution logic:
docs/PRODUCT_FLOW_TRADING_LOGIC.md
Target Operating Model (Required)
- Auto trading must execute per profile based on profile strategy rules + profile risk config.
- Each profile must be handled identically under the same orchestration model.
- Trade monitor must enforce stop loss / take profit correctly for each open trade.
- Every trade lifecycle must be traceable by
trade_idper profile across:- Active Orders
- Open Positions
- Trade History
- Dashboard must stay synchronized with backend runtime state and profile configuration.
Current Validation Snapshot (2026-02-15)
- Bot build:
PASS(npm run build) - Dashboard typecheck:
PASS(npx tsc -b) - Dashboard lint:
PASS(npm run lint) - Dashboard production build:
FAILin this environment (spawn EPERMwhile loadingvite.config.ts) - Bot regression suite:
PASS(node --loader ts-node/esm scripts/testTradeExecutorLifecycle.ts,scripts/testLifecycleRegressions.ts,scripts/testOrderStatusSyncRegressions.ts,src/scripts/verifyWebsocketContract.ts)
Progress Snapshot (Recent)
- Virtual profile position ledger recovery shipped (bot):
- Profile ownership and reconciliation hardening shipped (bot):
- Lifecycle trade-id and SL/TP fallback visibility improvements shipped (dashboard):
- Bot-side SL/TP sync fallback +
trade_idnormalization shipped: - TP zero-guard activation fix shipped (bot):
- Partial-exit lifecycle and OrderSync partial-fill handling shipped (bot):
- Profile-scoped same-symbol entry parity shipped (bot):
- Runtime risk limit enforcement shipped (maxDailyLossUsd + maxConsecutiveLosses):
- Strategy param compatibility + entry-trigger params + AI confidence normalization shipped:
- Strategy config schema normalization shipped (bot read-path + dashboard write/read-path):
- Deterministic trade-id policy shipped for bot-originated lifecycle IDs:
- Legacy
trade_idbackfill tooling shipped (dry-run + apply modes): - Lifecycle reconciliation report tooling shipped (
orders -> positions -> historyper profile): - Profile-specific symbol signal/rule aggregation shipped (bot + dashboard):
- Dashboard lifecycle trace ledger + mismatch diagnostics shipped:
- DB lifecycle integrity constraints + rollout plan shipped:
- Websocket bot-state contract verifier shipped (payload shape + lifecycle consistency checks):
- Lifecycle regression suite shipped (zero-TP guard, partial-exit reduction, stale reconciliation, order-sync stale paths):
- CI smoke gate for dashboard production build shipped:
- JWT issuer/audience claim hardening shipped (env-driven validation on access-token verify path):
- Exchange/API flap failure-injection regression shipped (bot):
- Auth threat model + executable RLS policy verification shipped:
- Dashboard lint debt cleanup + enforced lint gate shipped:
- Secret hygiene CI gate + rotation/history-purge runbooks shipped:
- AI resilience shipped: fail-open AI rule + deterministic local chat fallback + AI health endpoint:
Critical Findings (P0)
- Take-profit guard can activate incorrectly when
takeProfitis0
- Risk: unintended trailing-guard activation and premature exits.
- Evidence:
bytelyst-trading-bot-service/src/services/tradeMonitor.ts:117bytelyst-trading-bot-service/src/services/tradeMonitor.ts:118
- Partial exit fills are treated as full lifecycle completion
- Risk: bot marks trade closed while residual exchange position remains open.
- Evidence:
bytelyst-trading-bot-service/src/services/TradeExecutor.ts:414bytelyst-trading-bot-service/src/services/TradeExecutor.ts:442bytelyst-trading-bot-service/src/services/TradeExecutor.ts:461bytelyst-trading-bot-service/src/index.ts:69bytelyst-trading-bot-service/src/index.ts:76
- Per-profile identity model is still constrained by account-level symbol lock in auto-entry
- Risk: profiles on shared account are not handled identically; second profile is blocked if net position exists for symbol.
- Evidence:
bytelyst-trading-bot-service/src/services/AutoTrader.ts:110bytelyst-trading-bot-service/src/services/AutoTrader.ts:112
High Findings (P1)
- Profile rule parameter contract mismatch for session config
- Risk: some saved profile configs do not apply as intended.
- Evidence:
bytelyst-trading-bot-service/src/strategies/rules/SessionRule.ts:18expectsparams.sessions- default profile schemas/examples commonly use
allowedSessions
- Entry trigger rule ignores profile parameters
- Risk: strategy config UI implies control that runtime does not execute.
- Evidence:
bytelyst-trading-bot-service/src/strategies/rules/EntryTriggerRule.ts:11
- AI confidence threshold scale mismatch (0-1 vs 0-100)
- Risk: AI rule can pass too easily for some profile configs.
- Evidence:
bytelyst-trading-dashboard-web/src/components/TradeProfileManager.tsx:62(minConfidence: 0.7)bytelyst-trading-bot-service/src/strategies/rules/AIAnalysisRule.ts:54(compares against 0-100 confidence)
- AI prompt hardcodes BTC/USD in generic rule
- Risk: reduced quality for non-BTC symbols.
- Evidence:
bytelyst-trading-bot-service/src/strategies/rules/AIAnalysisRule.ts:83
- Risk limits from profile config are only partially enforced
- Risk:
maxDailyLossUsdandmaxConsecutiveLossesare configured but not enforced in execution path. - Evidence:
- configured in UI/schema but no enforcement path in
AutoTrader/ runtime guards except max open trades. bytelyst-trading-bot-service/src/services/AutoTrader.ts:94
- configured in UI/schema but no enforcement path in
- Mixed-side virtual ledger collapses to dominant side
- Risk: hidden state inconsistency when both sides exist due data anomalies.
- Evidence:
bytelyst-trading-bot-service/src/services/SupabaseService.ts:610
- Symbol-level dashboard signal shows first profile result only
- Risk: dashboard can misrepresent profile-specific strategy states.
- Evidence:
bytelyst-trading-bot-service/src/index.ts:382bytelyst-trading-bot-service/src/index.ts:400bytelyst-trading-bot-service/src/index.ts:444
Medium Findings (P2)
- Dashboard quality gate still failing (43 lint errors, 5 warnings)
- Risk: reduced maintainability and higher regression probability.
- Bot package test command still not wired
- Risk: script-based regression suite exists, but
npm testis still not standardized. - Evidence:
bytelyst-trading-bot-service/package.json("test": "echo \"Error: no test specified\" && exit 1")
- Vite build environment instability (
spawn EPERM)
- Risk: release pipeline confidence gap for frontend bundle.
- Remaining type hygiene issues (
any,@ts-ignore)
- Risk: unsafe refactors and runtime regressions.
- Evidence:
bytelyst-trading-dashboard-web/src/tabs/EntriesTab.tsx:82
Security and Compliance Residuals
- Rotate credentials and enforce secret hygiene policy.
- Secret hygiene enforcement + rotation runbook shipped:
- Purge secret-bearing history before production release.
- Purge runbook shipped:
- Add explicit RLS policy test suite for core tables.
Phased Remediation Roadmap
Phase 0 - Lifecycle Safety Hotfixes (Immediate)
- Guard TP logic with explicit positive threshold check before target evaluation.
- Treat
partially_filledexits as partial reduction, not full trade finalization. - Update order-sync callback to avoid full finalize on partial exits.
- Add regression tests for: zero-TP position, partial exit fill, stale reconciliation.
- Normalize trade-id payload propagation (
trade_id/tradeId) across bot/dashboard.
Phase 1 - Per-Profile Strategy and Risk Parity
- Replace account-level symbol pre-check with profile-aware exposure policy (virtual sub-positioning model).
- Enforce
maxDailyLossUsdandmaxConsecutiveLossesin runtime guard path. - Unify and validate rule param schema (
sessionsvsallowedSessions, confidence units). - Implement profile parameter support in
EntryTriggerRule. - Add strict schema validation for
strategy_configat write/read time. - Add profile-level execution direction control (
entryMode:both|long_only) and enforce long-only entry guard.
Phase 2 - Trade Lifecycle Determinism
- Require deterministic
trade_idgeneration for all bot-originated orders. - Add DB constraint strategy and migration plan for lifecycle integrity (
profile_id + trade_idindexing, null handling policy). - Add deterministic backfill tool for legacy rows missing
trade_id. - Add lifecycle reconciliation report (
orders -> positions -> history) per profile.
Phase 3 - Dashboard/Backend Synchronization
- Render profile-specific signal/rule state (remove first-profile shortcut for shared symbols).
- Add lifecycle trace view grouping by
trade_idwith explicit ENTRY/EXIT chain. - Show mismatch diagnostics when position exists without matching entry order.
- Add websocket contract tests for payload shape and lifecycle consistency.
Phase 4 - Quality Gates and Reliability
- Burn down dashboard lint debt to zero and enforce in CI.
- Add bot unit/integration tests (TradeExecutor, TradeMonitor, OrderStatusSyncService, profile fan-out).
- Add smoke tests for dashboard runtime build in CI environment matching deployment.
- Add failure-injection tests for exchange/API flaps and stale orders.
- Add AI degradation controls and observability (
AI_FAIL_OPEN,/api/ai/health, chat local fallback).
Phase 5 - Security Hardening
- Complete key rotation and remove plaintext secrets from tracked artifacts.
- Execute repo history purge plan before production cut.
- Harden JWT validation policy (issuer/audience checks) and formalize auth threat model.
- Issuer/audience validation shipped:
- Threat model shipped:
Prioritized Task List (Execution Order)
Trading Correctness First
- P0.1 TP zero-guard bug fix + tests
- P0.2 Partial-fill lifecycle correctness fix + tests
- P0.3 OrderSync partial-fill handling fix
Profile Parity
- P1.1 Remove account-level symbol lock behavior for profile-isolated strategy flow
- P1.2 Enforce profile riskLimits (
maxDailyLossUsd,maxConsecutiveLosses) - P1.3 Normalize strategy param contract and validation
- P1.4 Add profile-level long-only entry mode (
strategy_config.execution.entryMode)
Lifecycle Traceability
- P2.1 Deterministic trade-id policy for all order states
- P2.2 Legacy backfill and reconciliation tooling
- P2.3 Dashboard lifecycle ledger by
trade_id
Platform Quality
- P3.1 Dashboard lint/type debt to zero
- P3.2 Bot automated test suite bootstrap
- P3.3 CI release gates (bot + dashboard)
Definition of Done (Release Gate)
- Every profile executes strategy/risk deterministically under the same runtime model.
- SL/TP monitoring behaves correctly for BUY/SELL and zero-risk-field edge cases.
- Partial fills (entry and exit) are represented accurately in orders, positions, and history.
- Every active order, open position, and history row is traceable via a deterministic
trade_id. - Dashboard state is consistent with backend reconciliation without profile leakage.
- Build/type/lint/test gates pass in CI.
- Security residuals (secrets/RLS/auth hardening) are closed for production release.
Appended Questions (Non-Blocking)
- Should multi-profile on the same broker account support simultaneous same-symbol exposure (virtual sub-positions), or enforce one-symbol-per-account policy?
Decision: Implemented virtual sub-positions simultaneous same-symbol exposure. - For partial exit fills, do you want immediate quantity reduction with continued monitoring, or full close retry loop before state mutation?
Decision: Implemented immediate quantity reduction with continued monitoring. - Do you want strict rejection of profile configs that use legacy param keys (
allowedSessions, confidence in 0-1), or auto-migration on read?
Decision: Implemented auto-migration/compatibility on runtime read path.
Incremental Fix Log (2026-02-15)
-
Overview win-rate window controls shipped (24H/7D/30D/All) with profile-scoped and global win-rate metrics in selected time range.
-
Overview UX refinement shipped: removed
P&L Capital Usedfrom status bar to avoid user confusion; keptP&L Durationfor contextual clarity. -
Overview P&L context extension shipped (P&L duration window + P&L capital used with realized/open breakdown next to Net P&L):
-
Unified P&L ledger parity shipped across Overview, Audit Logs, and Strategy Clusters (single deduped history aggregation path + realized-vs-net labeling clarity):
-
Overview/History P&L parity fix shipped (Overview now uses the same merged + exact-event deduped lifecycle ledger as Audit Logs for realized and per-profile net P&L):
-
Audit Logs (History tab) integrity fix shipped (exact-event dedupe key prevents partial-exit row collapse by shared trade_id; safer timestamp and side normalization):
-
Pending EXIT ghost-order lifecycle fix shipped (serialized order-write path + stale
pending_newEXIT auto-resolution when lifecycle is already closed): -
Lifecycle trace dashboard hardening shipped (profile+trade scoped grouping, deterministic ENTRY/EXIT inference, stale-status merge guards, trace-level entry capital used, explicit state reasons):
-
Order sync not-found exception reconciliation shipped (stale pending_new orders with closed trade_id lifecycle are auto-resolved to canceled, including legacy rows without action):
-
Dashboard capital/overview accuracy update shipped (numeric-safe realized/net P&L aggregation, per-profile win rate + net P&L in Capital Scope, runtime profile state labeling):
-
Overview runtime-state UX clarity shipped for zero-utilization running profiles (monitoring vs signal-active-waiting-entry vs cooldown vs in-position):
-
Bot trade_history source-column fallback hardening shipped (legacy-schema safe insert path):
-
Manual entry capital guard shipped (scale-to-remaining capital with wait-for-release behavior):
-
Dashboard capital panel baseline shipped (allocated/used/remaining profile breakdown):
-
Dashboard history lifecycle cleanup, capital-used, and loss-highlighting shipped:
-
Trade lifecycle parity hardening shipped (legacy
action=nullENTRY fallback + canonical history reconciliation tool + targeted live chain cleanup): -
Reconciliation report signal cleanup shipped (formula mismatch diagnostics now ignore quarantined lifecycle rows already neutralized for audit safety):
-
Alpaca reconciliation carry-in baseline shipped (paged Alpaca fetch, pre-window position bootstrap, flat-vs-carry dual metrics, auto primary-mode fallback when Supabase pre-window coverage is insufficient):
Incremental Fix Log (2026-02-16)
- Profile-symbol scoped runtime sync hardening shipped (bootstrap sync, profile hot-reload resync, reconcile loop symbol scope, dynamic monitored-symbol loop wiring):
bytelyst-trading-bot-service/src/index.ts
- Legacy virtual-position reconstruction hardened for rows missing both
actionandtrade_id(deterministic ENTRY/EXIT inference + synthetic trade-id handling):bytelyst-trading-bot-service/src/services/SupabaseService.ts
- Dedicated-profile symbol mismatch recovery hardened (
USD/USDTcandidate lookup for virtual-position sync):bytelyst-trading-bot-service/src/services/TradeExecutor.ts
- Stale
pending_newEXIT cleanup hardened for legacy rows withouttrade_id(profile+symbol virtual lifecycle flat check -> auto-cancel):bytelyst-trading-bot-service/src/services/OrderStatusSyncService.tsbytelyst-trading-bot-service/scripts/testOrderStatusSyncRegressions.ts
- Startup pending-order recovery hardened to auto-resolve closed EXIT-like stale rows before dashboard broadcast:
bytelyst-trading-bot-service/src/services/TradeExecutor.ts
- Position merge architecture hardened to preserve stable per-trade lifecycle visibility (owner+profile+trade keyed merge instead of collapsing all same-symbol positions):
bytelyst-trading-bot-service/src/services/apiServer.ts
- Profile symbol parsing hardened for array/string compatibility in entry gating:
bytelyst-trading-bot-service/src/services/AutoTrader.ts
Coverage Status (2026-02-16)
- Bot service (
npm run coverage:full):- Statements:
24.65%(1875/7606) - Branches:
41.20%(178/432) - Functions:
35.66%(56/157) - Lines:
24.65%(1875/7606)
- Statements:
- Dashboard (
npm run coverage:full):- Statements:
5.65%(106/1874) - Branches:
6.09%(128/2101) - Functions:
3.35%(16/477) - Lines:
5.48%(93/1697)
- Statements:
Open Enterprise Gaps (Pending)
- True same-profile same-symbol concurrent trade support is still structurally limited by
TradeExecutorin-memoryMap<symbol, PositionState>.- Impact: multiple active lifecycles on one symbol inside one profile cannot be represented independently in runtime state.
- Coverage is still far from 100% in both repos; current suites are regression-focused, not exhaustive component/service coverage.
- Live Alpaca-vs-Supabase reconciliation is still script-driven, not continuously enforced as a scheduled runtime guard.
- Legacy data quality can still introduce ambiguous lifecycle chains until historical rows are fully backfilled (
trade_id,action) and constrained at DB level.
2026-02-16 Commit References
- Lifecycle/profile sync hardening implementation batch:
- Roadmap + product-flow documentation update:
Gap Closure Update (2026-02-16, Cycle 2)
-
Same-profile same-symbol concurrent lifecycle support implemented in runtime state model.
- TradeExecutor now stores active positions by trade identity (symbol + trade_id) instead of one-position-per-symbol collapse.
- AutoTrader can manage/exit multiple active lifecycles per symbol and supports controlled pyramiding (
strategy_config.execution.allowPyramiding, default enabled). - TradeMonitor now enforces SL/TP/trailing and exchange-missing finalization per trade lifecycle (trade_id aware).
-
Runtime parity guard implemented (continuous scheduled check, not script-only).
- Reconciliation loop now compares recent profile orders against exchange order statuses and auto-corrects safe terminal mismatches.
- Runtime health now tracks
parityMismatchCount.
-
Legacy lifecycle recovery further hardened for per-trade reconstruction.
- Added profile/symbol/trade_id scoped virtual open-position reconstruction (
getVirtualOpenPositionForTrade). - Dedicated profile sync now reconstructs multiple open slices per symbol when multiple trade_ids remain open.
- Added profile/symbol/trade_id scoped virtual open-position reconstruction (
-
Manual square-off updated to close all active sub-positions for a symbol (trade_id aware), not just one selected row.
-
Coverage remains below enterprise target.
- Bot (
npm run coverage:full): Statements24.60%, Branches41.72%, Functions36.09%, Lines24.60%. - Dashboard (
npm run coverage:full): Statements5.65%, Branches6.09%, Functions3.35%, Lines5.48%.
- Bot (
Residual Open Gap
- Expand automated tests toward enterprise target coverage (module-level + integration-level) across both repos.
Cycle 2 Commit Link
- Multi-lifecycle runtime + parity guard implementation:
Gap Closure Update (2026-02-16, Cycle 3)
-
Fixed dedicated-profile sync gap that could drop valid local lifecycle positions when exchange remained open but virtual reconstruction was temporarily empty.
- TradeExecutor.syncPositions now retains existing local symbol lifecycles when exchange position exists and virtual lookup returns empty.
- Local symbol state is only cleared when exchange is flat and no virtual lifecycle remains.
-
Improved dashboard state freshness for lifecycle transitions.
- TradeExecutor.openPosition now pushes updated active positions immediately after confirmed entry fill.
- TradeExecutor.finalizeTrade now pushes updated active positions immediately after local lifecycle removal.
-
Added regression coverage for the above lifecycle-sync protections.
- Extended scripts/testTradeExecutorLifecycle.ts to assert:
- immediate position snapshot propagation after filled entry
- local lifecycle retention on exchange-open plus virtual-empty sync window
- Extended scripts/testTradeExecutorLifecycle.ts to assert:
Residual Open Gap
- Coverage remains below enterprise target across full repository scope.
Cycle 3 Commit Link
- Lifecycle retention plus immediate position push plus regression tests:
Gap Closure Update (2026-02-16, Cycle 4)
-
Hardened order persistence to be idempotent on order_id so duplicate lifecycle rows are not inserted on retries.
- Existing order rows are merged/updated, and terminal statuses are not downgraded by late pending writes.
-
Hardened stale-order detection and reconciliation cadence to reduce stale pending_new artifacts.
- Added configurable runtime controls: ORDER_SYNC_INTERVAL_MS, STALE_ORDER_THRESHOLD_MINUTES.
- Expanded stale-pending scope to include pending_new, pending, accepted, and new.
-
Added regression guardrail for order persistence and stale status scope.
- New suite: scripts/testSupabaseOrderPersistenceRegressions.ts.
- Included in regression/coverage execution paths.
-
Dashboard lifecycle table hardening shipped.
- Bot positions are deduped by profile_id plus trade_id before rendering.
- Pending EXIT rows are normalized to closed when lifecycle is already closed in history for the same trade_id scope.
-
Coverage progress (full-scope baseline run on 2026-02-16).
- Bot (npm run coverage:full): Statements 28.29%, Branches 40.59%, Functions 41.04%, Lines 28.29%.
- Dashboard (npm run coverage:full): Statements 5.58%, Branches 5.98%, Functions 3.34%, Lines 5.40%.
Residual Open Gap
- Full enterprise target coverage is still pending; broad module/component test expansion is still required across both repos.
Cycle 4 Commit Links
- Bot lifecycle dedupe plus stale sync cadence plus persistence regression:
- Dashboard lifecycle table stabilization:
Gap Closure Update (2026-02-16, Cycle 5)
- Expanded dashboard enterprise coverage across tabs/components/hooks with deterministic runtime-safe tests.
- Added coverage suites for:
AppOverviewTab,PositionsTab,SignalsTab,EntriesTab,SettingsTab,AdminTab,HistoryTab,ConfigTabAuthContext,TradeProfileManagerconfig normalization,PriceChart,AlertFeed,MarketTicker, market-opportunity widgets,EntryForm,SymbolCarduseWebSocket,supabaseClient,constmodule
- Added coverage suites for:
- Added deterministic lifecycle-branch assertions in dashboard tab coverage:
- Lifecycle states:
OPEN,PARTIAL_EXIT,CLOSED,ORPHAN_EXIT,EXIT_PENDING - Stale pending-order banner behavior and mismatch diagnostics rendering
- Lifecycle states:
- Kept strategy-config normalization logic testable by exporting
normalizeStrategyConfigand validating legacy compatibility paths. - Re-ran quality gates for both repos after coverage expansion:
- Dashboard:
npm run check-> PASS - Dashboard:
npm run coverage:full-> PASS - Bot:
npm run check-> PASS - Bot:
npm run coverage:full-> PASS
- Dashboard:
Coverage Status (2026-02-16, Post Cycle 5)
- Bot service (
npm run coverage:full):- Statements:
28.19%(2278/8080) - Branches:
40.73%(233/572) - Functions:
40.46%(70/173) - Lines:
28.19%(2278/8080)
- Statements:
- Dashboard (
npm run coverage:full):- Statements:
42.46%(806/1898) - Branches:
34.71%(743/2140) - Functions:
33.26%(159/478) - Lines:
44.25%(762/1722)
- Statements:
Residual Open Gap
- Enterprise coverage target is not yet complete for both repos; remaining work is deeper branch-path and service-level integration coverage expansion.
- Existing workspace still contains unrelated pending file changes; only targeted coverage/test files were committed in this cycle.
Cycle 5 Commit Links
- Dashboard coverage expansion suite:
Coverage Status (2026-02-16, Latest Refresh)
- Re-ran broad coverage snapshots (
npm run coverage:full) for both repos and updated the dedicated report:docs/COVERAGE_BEFORE_AFTER_2026-02-16.md
- Re-ran enforced 80% gate coverage (
npm run coverage) for both repos.
Broad Coverage (Latest)
- Bot service (
npm run coverage:full):- Statements:
55.68%(4499/8080) - Branches:
55.76%(629/1128) - Functions:
64.51%(160/248) - Lines:
55.68%(4499/8080)
- Statements:
- Dashboard (
npm run coverage:full):- Statements:
90.53%(1760/1944) - Branches:
75.61%(1619/2141) - Functions:
88.24%(443/502) - Lines:
92.11%(1624/1763)
- Statements:
Gate Coverage (Latest)
- Bot service (
npm run coverage):- Statements:
97.87%(92/94) - Branches:
93.02%(40/43) - Functions:
92.30%(12/13) - Lines:
97.87%(92/94)
- Statements:
- Dashboard (
npm run coverage):- Statements:
99.06%(106/107) - Branches:
94.16%(129/137) - Functions:
100%(16/16) - Lines:
98.93%(93/94)
- Statements:
Focus Coverage
- Dashboard
PositionsTab(src/tabs/PositionsTab.tsx):- Statements:
98.61%(498/505) - Branches:
78.86%(500/634) - Functions:
100%(112/112) - Lines:
100%(459/459)
- Statements:
Gap Closure Update (2026-02-16, Cycle 6)
- Fixed runtime duplicate position/order artifacts by introducing canonical snapshot merge logic in backend state updates.
- Positions are merged by stable
trade_idfirst; fallback merges are owner+symbol+side scoped. - Orders are merged by
order_idwith terminal-status precedence to prevent stale status downgrade.
- Positions are merged by stable
- Fixed lifecycle linkage and aggregate math drift in dashboard history/overview.
- Trade-history aggregation now runs by lifecycle (
profile_id + trade_id) instead of raw row count. - Duplicate lifecycle events with reason formatting differences are normalized and collapsed.
- Win rate and realized P&L now reflect lifecycle outcomes, not duplicated sync rows.
- Trade-history aggregation now runs by lifecycle (
- Fixed profile/trade distinction drift in open positions view.
- Runtime position dedupe now prefers
trade_idkeyed identity and preserves richer profile metadata. - Overview capital utilization and unrealized P&L now compute from deduped runtime positions.
- Runtime position dedupe now prefers
- Added/updated regression coverage for merge and lifecycle aggregation paths.
- Re-ran quality gates and coverage baselines across both repos after fixes.
Coverage Status (Cycle 6 Snapshot)
- Full scope (
npm run coverage:full):- Bot service: Statements
57.05%(4738/8304), Branches55.24%(685/1240), Functions66.53%(175/263), Lines57.05%(4738/8304) - Dashboard: Statements
90.72%(1809/1994), Branches75.40%(1662/2204), Functions88.38%(449/508), Lines92.37%(1673/1811)
- Bot service: Statements
- Gate scope (
npm run coverage):- Bot service: Statements
97.87%, Branches93.02%, Functions92.30%, Lines97.87% - Dashboard: Statements
97.70%, Branches88.75%, Functions94.44%, Lines100%
- Bot service: Statements
Root Cause (Closed)
- Primary architecture gap was non-canonical merge and aggregation.
- Runtime sources were merged without lifecycle-first identity guarantees.
- Dashboard aggregate paths mixed row-level and lifecycle-level counting.
- Primary coding bug was metadata-poor row overwrite during dedupe, which dropped profile context and inflated/fragmented position and P&L views.
Remaining Enterprise Gaps
- 100% full-repo coverage target is not yet reached; current full-scope coverage is materially improved but not complete.
- Add continuous reconciliation alerting for lifecycle chain anomalies (
orphan_exit,unclassified) at API and UI health surfaces.
Cycle 6 Commit Links
- Bot runtime merge hardening + regression suite:
- Dashboard lifecycle aggregation + runtime dedupe hardening: