Codebase Audit Report¶
Date: 2026-04-16
Scope: Full TradingDesk project (tradingview-mcp/, fatbot/, docs/)
Executive Summary¶
The TradingDesk project is well-architected for its research/educational purpose. The MCP server is the strongest component — 78 tools with good input validation, compact output, and comprehensive test coverage. The dashboard is a clean static UI ready for React migration. The broker layer is the weakest link — fragile UI automation that needs to be replaced with direct API integration.
Scores¶
| Area | Score | Notes |
|---|---|---|
| Architecture | A | Clean layer separation, indicator-first philosophy is sound |
| MCP Server | A- | 78 tools, good validation, but depends on undocumented APIs |
| Input Validation | A | Zod schemas + safeString + requireFinite |
| Test Coverage | B+ | 100+ tests, but E2E requires live TradingView |
| Dashboard | B | Functional but static mock data, no framework |
| Broker Layer | D | UI automation only, fragile, no real broker APIs |
| Documentation | A | Thorough docs, indicator contracts, tool reference |
| Security | A- | All localhost, no data exfil, but CDP is inherently powerful |
| Error Handling | B+ | Good error messages, but some tools swallow errors silently |
| Dependencies | A+ | Only 2 runtime deps, minimal attack surface |
Critical Findings¶
1. Broker Layer is UI Automation Only (HIGH)¶
File: tradingview-mcp/src/core/trading.js (~700 lines)
The entire trading layer works by clicking TradingView UI elements:
- Hardcoded CSS selectors ([data-name="trading-floating-toolbar"])
- Fixed timing delays (await sleep(500), await sleep(2000))
- DOM scraping for order/position data
- Will break on any TradingView UI update
Recommendation: Replace with direct broker API integration. See Broker Tools (Planned).
2. Undocumented TradingView API Dependency (HIGH)¶
File: tradingview-mcp/src/connection.js — KNOWN_PATHS
All data extraction depends on internal TradingView JavaScript objects:
window.TradingViewApi._activeChartWidgetWV.value()
window.TradingViewApi._chartWidgetCollection
window.TradingViewApi._replayApi
These are undocumented internal APIs that can change without notice in any TradingView update.
Mitigation already in place: tv_discover tool probes paths and reports which are alive. The RESEARCH.md acknowledges this risk.
Recommendation: Add automated path validation on startup. If critical paths are broken, fail fast with clear error messages.
3. Pine Graphics Extraction is Fragile (MEDIUM)¶
File: tradingview-mcp/src/core/data.js
Pine graphics extraction navigates internal collection objects:
s._graphics._primitivesCollection.dwglines.get('lines').get(false)._primitivesDataById
This chain of property access has no fallback. If TradingView changes the internal structure, it throws silently or returns empty data.
Recommendation: Add defensive checks at each level of the chain. Return partial data with warnings rather than empty results.
4. CDP Gives Full Page Control (MEDIUM)¶
File: tradingview-mcp/src/core/ui.js — ui_evaluate
The ui_evaluate tool executes arbitrary JavaScript in the TradingView page context. While necessary for the system to work, this is a powerful capability.
Mitigation: The tool is intended for development/debugging. Document that it should not be used in automated workflows.
Module-Level Findings¶
connection.js (287 lines)¶
- Good: Singleton pattern, auto-reconnect with exponential backoff, multi-target support
- Good:
safeString()prevents injection,requireFinite()validates numbers - Issue: Reconnect max retries (5) is hardcoded — consider making configurable
- Issue: No connection timeout on initial connect — can hang indefinitely
chart.js (~200 lines)¶
- Good: Clean separation of get/set operations
- Good:
manageIndicatorhandles both add and remove - Issue:
setSymboldoesn't verify the symbol exists before setting — could leave chart in error state
data.js (~400 lines)¶
- Good: Summary mode on OHLCV, label caps, verbose flag
- Good: Study filter for targeted extraction
- Issue:
getDepth()requires DOM panel to be open but doesn't check/open it automatically - Issue: Strategy data extraction (
getStrategyResults,getTrades,getEquity) uses long JS evaluation strings with no error boundary
pine.js (~400 lines)¶
- Good:
pine_analyzeworks offline — very useful for CI/pre-compile checks - Good:
pine_smart_compileauto-detects and reports errors - Issue:
pine_get_sourcecan return 200KB+ — no truncation option - Suggestion: Add
max_linesparam topine_get_source
replay.js (~150 lines)¶
- Good: Race condition handling (poll for
isReplayStarted && currentDate !== null) - Issue: 30-iteration poll with 250ms sleep = 7.5s max wait. Should be configurable or fail faster.
trading.js (~700 lines)¶
- Critical: Entire module is UI automation — see Finding #1
- Issue:
placeLimitOrderhas 8 sequential UI clicks with timing assumptions - Issue: Order ID extraction depends on DOM structure of Orders tab
- Issue: No order confirmation/verification after placement
- Positive: Tradovate OAuth flow exists but is incomplete
ui.js (~300 lines)¶
- Good: Multiple selector strategies (aria-label, data-name, text, class)
- Issue:
ui_evaluatehas no sandboxing — full page access - Issue:
ui_clickreturns success even if the click had no visible effect
stream.js¶
- Good: Poll-and-diff approach is pragmatic
- Issue: No backpressure — if consumer is slow, events are dropped silently
health.js¶
- Good:
discoverprobes all known paths and reports status - Good:
launchhas platform detection (Windows, macOS, Linux) - Issue:
launchstill tries TradingView Desktop — should prefer Chrome CDP per current workaround
batch.js¶
- Good: Parallel execution across symbols
- Issue: No rate limiting — rapid symbol changes can overwhelm TradingView
Dashboard Audit (fatbot/)¶
index.html (~1050 lines)¶
- Good: Clean component structure, dark theme, responsive
- Good: CSS custom properties for easy theming
- Good: Fetch error handling with status icon feedback
- Good: Symbol sanitisation on chart screenshot path
- Issue: All CSS, HTML, and JS in one file — needs extraction for React migration
- Issue: No live MCP connection — entire dashboard is static
server.js (~35 lines)¶
- Good: Minimal, does one thing
- Good: Path traversal protection (resolved path must start with __dirname)
- Good: Proper error logging with status codes (404 vs 500)
- Issue: No CORS headers (fine for localhost, but needed for cross-origin MCP calls later)
- Issue: No content security policy headers
Documentation Audit¶
Strengths¶
- Indicator Contract system is well-specified (overview.md, per-indicator specs)
- Tool reference is comprehensive (tool-reference.md)
- CLAUDE.md decision tree helps tool selection
- SECURITY.md is clear about threat model
- SETUP_GUIDE.md covers all platforms
Gaps¶
- No architecture diagram (only text descriptions)
- No changelog or version history
- No runbook for common failures (CDP connection lost, TradingView update breaks tools)
- Broker layer has no documentation (planned tools not specified until now)
Test Audit¶
Coverage¶
| Suite | Tests | Requires CDP | Status |
|---|---|---|---|
e2e.test.js |
78 | Yes | Full tool coverage |
pine_analyze.test.js |
15 | No | Offline Pine analysis |
cli.test.js |
10 | No | CLI routing |
replay.test.js |
5 | Yes | Replay state |
sanitization.test.js |
5 | No | Input validation |
Gaps¶
- No unit tests for
connection.js(reconnect logic, singleton management) - No tests for
trading.js(hard to test UI automation) - No tests for error paths (what happens when CDP disconnects mid-operation)
- No performance/load tests (what happens with 50+ rapid tool calls)
- No integration test for dashboard → MCP flow (doesn't exist yet)
Dependency Audit¶
Runtime Dependencies (2)¶
| Package | Version | Risk | Notes |
|---|---|---|---|
@modelcontextprotocol/sdk |
1.12.1 | Low | Well-maintained, Anthropic-backed |
chrome-remote-interface |
0.33.2 | Low | Stable, widely used |
Supply Chain¶
- Minimal attack surface — only 2 deps
- No build step — raw JS, no transpilation
- No lockfile — should add
package-lock.jsonto pin versions
Recommendations Priority¶
P0 (Do Now)¶
- Design broker API tools — Replace UI automation with direct API calls (spec in broker-tools.md)
- Add package-lock.json — Pin dependency versions
P1 (Soon)¶
- Add startup path validation — Check KNOWN_PATHS on connect, warn if broken
- Add defensive Pine graphics extraction — Partial data + warnings instead of silent failures
- Fix
health.launch— Default to Chrome CDP, not TradingView Desktop - Add connection timeout — Don't hang on initial CDP connect
P2 (When Building Broker Layer)¶
- Add risk controls — Position sizing, daily loss limits, max contracts
- Add order audit log — Track all broker interactions
- Add kill switch —
broker_flatten_allemergency tool
P3 (During React Migration)¶
- Extract dashboard components — Split index.html into React components
- Add CORS and CSP headers to dashboard server
- Build live MCP bridge — Replace mock JSON with real-time MCP data
P4 (Polish)¶
- Add connection.js unit tests
- Add error path tests (CDP disconnect, TradingView crash)
- Add architecture diagrams
- Add changelog