PineForge Codegen

ทางการ

เซิร์ฟเวอร์ MCP ในเครื่อง: AI เขียน PineScript v6, เอ็นจิ้นที่รวมอยู่จะแปลงเป็น C++ และทดสอบย้อนหลังกับข้อมูล Binance — ไม่ต้องใช้คีย์ API, ทำงานในเครื่องทั้งหมด

GitHub
8
ลองใช้ MCP นี้ผู้สนับสนุน

คุณทำอะไรได้บ้างด้วย PineForge Codegen MCP?

  • Transpile PineScript to C++ — ขอให้ผู้ช่วยแปลงซอร์ส Pine v6 เป็นหน่วยการแปลภาษา C++ โดยใช้ transpile_pine เพื่อตรวจสอบหรือประมวลผลเพิ่มเติม
  • Run single backtests — ให้ผู้ช่วยทำ backtest กลยุทธ์ Pine v6 กับไฟล์ CSV ของ OHLCV ผ่าน backtest_pine พร้อมพารามิเตอร์เสริม inputs, overrides และ runtime
  • Sweep strategy parameters — ใช้ backtest_pine_grid เพื่อรันกริดคาร์ทีเซียนของชุดค่าผสม inputs × overrides และรับผลลัพธ์ที่จัดอันดับพร้อมการตั้งค่าที่ดีที่สุด
  • Grade TradingView parity — ขอให้ผู้ช่วยเปรียบเทียบผลส่งออกจาก TradingView Strategy Tester กับการรันสคริปต์เดียวกันของ PineForge แบบทีละเทรด โดยใช้ check_tradingview_parity
  • Fetch Binance market data — ให้ผู้ช่วยดึงข้อมูล OHLCV klines จาก API สาธารณะของ Binance ไปเป็น CSV ที่พร้อมสำหรับ backtest ผ่าน fetch_binance_ohlcv พร้อมการแบ่งหน้าอัตโนมัติสำหรับคำขอขนาดใหญ่
  • Check Pine v6 feature support — ขอให้ผู้ช่วยตรวจสอบว่า identifier หรือ namespace ของ Pine เฉพาะรองรับหรือไม่ โดยใช้ check_pine_feature ก่อนเขียนหรือพอร์ตกลยุทธ์

เอกสาร

@pineforge/backtest-mcp

เซิร์ฟเวอร์ MCP แบบสแตนด์อโลนผ่าน stdio: เอเจนต์ AI เขียน PineScript v6 และ อิมเมจ pineforge-release ที่มาพร้อมกันจะแปลงเป็น C++ และทดสอบย้อนหลังกับ ไฟล์ OHLCV CSV (ไฟล์ของคุณเอง หรือไฟล์ที่ดึงมาจาก API สาธารณะของ Binance) — ทั้งหมดในคอนเทนเนอร์เดียว แบบในโพรเซส ทำงานในเครื่องทั้งหมด — อิมเมจมาพร้อมกับ ทรานสไพเลอร์ pineforge-codegen ดังนั้น Pine → C++ → การทดสอบย้อนหลังจึงทำงานโดยไม่ต้องใช้ Docker daemon ของโฮสต์ ไม่ต้องใช้ API key ซอร์สโค้ดกลยุทธ์และไฟล์ CSV ของคุณไม่เคยออกจากเครื่อง มีเพียงเครื่องมือ Binance และ check_tradingview_parity เมื่อคุณไม่ส่งแท่งข้อมูล จะทำคำขอออกไปยังภายนอก (เฉพาะ endpoint สาธารณะ)

pineforge-backtest-mcp MCP server

demo

เครื่องมือ

ชื่อทำงานบนวัตถุประสงค์
transpile_pineในโพรเซสPine v6 → หน่วยการแปลงเป็น C++ (เฉพาะการทรานสไพล์)
list_engine_paramsในเครื่อง (ไม่มี I/O)รายการตัวเลือก overrides + runtime ทั้งหมดที่การทดสอบย้อนหลังรองรับ
backtest_pineในโพรเซสทดสอบย้อนหลังครั้งเดียวของซอร์ส Pine กับไฟล์ OHLCV CSV
backtest_pine_gridในโพรเซสสแกนแบบคาร์ทีเซียนของ inputs × overrides: ทรานสไพล์ครั้งเดียว แล้วคอมไพล์และทดสอบย้อนหลังหนึ่งครั้งต่อชุดค่าผสม
check_tradingview_parityในโพรเซส (เฉพาะ Binance public API หากไม่มีแท่งข้อมูลของคุณ)ให้คะแนนการส่งออก Strategy Tester ของ TradingView เทียบกับการรันสคริปต์เดียวกันของ PineForge ทีละเทรด
fetch_binance_ohlcvBinance public APIเขียนไฟล์ CSV ที่พร้อมทดสอบย้อนหลังจาก klines สปอตหรือ USDT-perp ของ Binance
binance_symbolsBinance public APIแสดงรายการ / กรองสัญลักษณ์ Binance (แคชในโพรเซส 5 นาที)
list_coverage_topicsในเครื่อง (ไม่มี I/O)หัวข้อความครอบคลุม Pine v6 ทั้งหมดพร้อมสถานะหนึ่งบรรทัด + สรุป
check_pine_featureในเครื่อง (ไม่มี I/O)ตรวจสอบว่า Pine identifier/namespace รองรับใน PineForge หรือไม่
get_coverage_topicในเครื่อง (ไม่มี I/O)รายละเอียดเต็ม + รายการ supported/partial/via_transpiler/unsupported สำหรับหนึ่งหัวข้อ
engine_infoในเครื่อง (ไม่มี I/O)เฉพาะ Docker image: โหมด, แฟล็กที่ฝังไว้ และเวอร์ชัน pineforge-release ที่มาพร้อมกัน (เช่น 1.0.0)

ตารางคือรายการเครื่องมือของ Docker image (11 เครื่องมือ) แพ็กเกจ npm ให้บริการสิบรายการแรก รวมถึง pull_engine_image (docker pull อิมเมจเอนจิน) และ check_engine_image แทน engine_info (12 เครื่องมือ)

ใน tools/list ทุกเครื่องมือยังมีชื่อและคำอธิบายประกอบ MCP สี่รายการ (src/tool-meta.ts) แบบอ่านอย่างเดียว: การค้นหาและ check_tradingview_parity (มัน ทำงานในไดเรกทอรีชั่วคราวที่มันลบทิ้ง) และใน Docker image transpile_pine ไม่ใช่อ่านอย่างเดียว: backtest_pine และ backtest_pine_grid (รายงาน ที่ใหญ่เกินกว่าจะส่งคืนจะถูกเขียนลงไฟล์), fetch_binance_ohlcv (เขียน CSV ของมัน) และเครื่องมืออิมเมจสองรายการ; ในแพ็กเกจ npm ยังรวม transpile_pine ด้วย เนื่องจาก ที่นั่นมันและการทดสอบย้อนหลังรับ image ที่ Docker ดึงเมื่อไม่มี แบบทำลายล้าง: เครื่องมือที่เขียนไฟล์ที่พาธที่คุณระบุ เนื่องจากมันแทนที่ไฟล์ ที่มีอยู่แล้ว แบบเปิดโลกกว้าง: เครื่องมือที่เข้าถึง Binance public API หรือ รีจิสทรีอิมเมจ

การติดตั้ง

ทำงานเป็นคอนเทนเนอร์แบบสแตนด์อโลนผ่าน stdio — เอนจินมาพร้อมกัน ในโพรเซส ไม่ต้องใช้ Docker daemon ของโฮสต์ ไม่ต้องใช้ API key เมานต์โฟลเดอร์ที่เก็บไฟล์ CSV ของคุณที่ /work:

docker run --rm -i -v "$PWD:/work" ghcr.io/pineforge-4pass/pineforge-backtest-mcp:latest

ข้อกำหนดเดียว: Docker และเครือข่ายขาออกสำหรับเครื่องมือดึงข้อมูล Binance เชื่อมต่อกับ MCP client ของคุณด้านล่าง

  • ใช้พาธ /work/... แบบสัมบูรณ์ ในอาร์กิวเมนต์เครื่องมือ (ohlcv_csv_path, output_path, report_path) ไดเรกทอรีทำงานของเซิร์ฟเวอร์ภายใน คอนเทนเนอร์คือ /app ไม่ใช่เมานต์ ดังนั้นพาธสัมพัทธ์เช่น ./btc.csv ชี้เข้าไปในคอนเทนเนอร์และจะหายไปเมื่อมันออก (--rm)
  • บน Linux เพิ่ม --user "$(id -u):$(id -g)" เพื่อให้ไฟล์ที่เซิร์ฟเวอร์เขียนไปยัง /work มีความเป็นเจ้าของตามคุณ
  • ต้องใช้ -i; ห้ามเพิ่ม -t — TTY จะทำให้สตรีม stdio JSON-RPC เสียหาย

:latest ของอิมเมจและ latest ของ npm มักจะมาพร้อมเวอร์ชันเสถียรเสมอ pineforge-release พรีรีลีส (เช่น 1.0.0-rc.1) จะสร้างพรีรีลีสของเซิร์ฟเวอร์นี้ (X.Y.Z-alpha.N, -beta.N หรือ -rc.N): อิมเมจ :vX.Y.Z-rc.N ที่สร้าง FROM พรีรีลีส pineforge-release นั้น และ npm @pineforge/backtest-mcp@next ซึ่ง เหมือนการติดตั้ง npm ทั่วไป จะรันอิมเมจเอนจินที่ระบุโดย PINEFORGE_IMAGE (ค่าเริ่มต้น ghcr.io/pineforge-4pass/pineforge-release:latest เอนจินเสถียร) พรีรีลีส ไม่แสดงอยู่ใน MCP Registry รุ่นแรก 0.9.32-rc.1 บน pineforge-release 1.0.0-rc.1 เผยแพร่เมื่อ 2026-09-30 (อิมเมจ :v0.9.32-rc.1, npm next)

npm / npx

npx -y @pineforge/backtest-mcp

ต้องใช้ Node ≥ 20 และ Docker daemon ที่รันอยู่: การทรานสไพล์และการทดสอบย้อนหลังแต่ละครั้งคือ docker run --rm --network=none ของอิมเมจเอนจิน (PINEFORGE_IMAGE, ค่าเริ่มต้น ghcr.io/pineforge-4pass/pineforge-release:latest) docker pull ก่อน: การดึงของเซิร์ฟเวอร์เอง (โดยนัยในการเรียกครั้งแรก หรือ pull_engine_image) จะถูกตัด หลังจาก PINEFORGE_DOCKER_TIMEOUT_MS (120 วินาทีโดยค่าเริ่มต้น) พาธสัมพัทธ์กับ ไดเรกทอรีทำงานของเซิร์ฟเวอร์ และโดยค่าเริ่มต้นจำกัดอยู่ภายในนั้น (ดู ขอบเขตระบบไฟล์)

ทางเลือกแบบโฮสต์ (ไม่ต้องติดตั้ง)

ต้องการลองเร็วที่สุดโดยไม่ต้องใช้ Docker และไม่ต้องใช้ API key? วาง endpoint Streamable HTTP ลงใน MCP client ใดก็ได้:

https://mcp.pineforge.dev/mcp

ข้อแลกเปลี่ยนกับ repo นี้: เซิร์ฟเวอร์แบบโฮสต์มีการจำกัดการใช้งาน (100 การรัน backtest_pine ต่อสัปดาห์ต่อ IP บวกกับขีดจำกัดอัตราที่ขอบ) และทำงานกับ OHLCV ที่มันจัดการเอง — คริปโตเท่านั้น เ دردเจ็ดเวนิว (Binance, Bybit และ OKX สปอตและ USDT-perp; Coinbase สปอต) ย้อนหลัง 365 วัน แท่งล่าสุดล่าช้าจากเวลาจริงประมาณหนึ่งชั่วโมง เครื่องมือ 11 รายการของมัน ต่างจากเซิร์ฟเวอร์นี้: ไม่มี transpile_pine, ไม่มี backtest_pine_grid, และมัน รับ symbol / interval / venue แทนพาธ CSV repo ในเครื่องนี้ ไม่จำกัดการใช้งาน รันออฟไลน์ และให้คุณนำ CSV ของคุณเองและรันการสแกนแบบกริด ได้ ซอร์สของบริการแบบโฮสต์เป็นแบบส่วนตัว

การกำหนดค่า client

เมานต์ไดเรกทอรีที่ /work; ชี้ fetch_binance_ohlcv / backtest_pine ไปที่ พาธสัมบูรณ์ภายใต้มัน (/work/btc.csv) (ต้องใช้ -i; ห้ามเพิ่ม -t — TTY จะทำให้สตรีม stdio JSON-RPC เสียหาย)

Claude Desktop

แก้ไข ~/Library/Application Support/Claude/claude_desktop_config.json (macOS) หรือ %APPDATA%\Claude\claude_desktop_config.json (Windows) และใช้พาธโฮสต์สัมบูรณ์ สำหรับเมานต์:

{
  "mcpServers": {
    "pineforge-backtest": {
      "command": "docker",
      "args": [
        "run", "--rm", "-i",
        "-v", "/absolute/path/to/your/data:/work",
        "ghcr.io/pineforge-4pass/pineforge-backtest-mcp:latest"
      ]
    }
  }
}

Cursor

.cursor/mcp.json ในโปรเจกต์ (หรือ ~/.cursor/mcp.json สำหรับทุกโปรเจกต์) Cursor ขยาย ${workspaceFolder}:

{
  "mcpServers": {
    "pineforge-backtest": {
      "command": "docker",
      "args": [
        "run", "--rm", "-i",
        "-v", "${workspaceFolder}:/work",
        "ghcr.io/pineforge-4pass/pineforge-backtest-mcp:latest"
      ]
    }
  }
}

Claude Code CLI

claude mcp add pineforge-backtest \
  -- docker run --rm -i -v "$PWD:/work" ghcr.io/pineforge-4pass/pineforge-backtest-mcp:latest

สำหรับเอเจนต์ AI — ใช้ผ่าน MCP

ช่องว่างความสามารถที่สิ่งนี้ปิด โมเดลภาษาไม่สามารถทดสอบย้อนหลังกลยุทธ์ PineScript v6 ได้อย่างแม่นยำโดยใช้เหตุผลเกี่ยวกับมัน ความหมายแบบอนุกรมของ PineScript ลำดับการเติมภายในแท่ง กฎการมองไปข้างหน้า และตรรกะคำสั่ง/ตำแหน่ง strategy.* ไม่สามารถสร้างขึ้นใหม่จากการประมาณได้ ดังนั้นโมเดลที่จำลองการทดสอบย้อนหลังในหัว — หรือเขียนเองใน Python (backtrader/vectorbt) — จะหลอนเทรดและ P&L และไม่สามารถรับประกันความเท่าเทียมกับ TradingView ได้ PineForge รันเอนจิน C++ เชิงกำหนดที่แท้จริงแทน โดยให้คะแนนทีละเทรดเทียบกับรายการเทรดของ TradingView เอง ที่เอนจิน 35db01c8 (2026-09-29; เอนจิน 1.0.0 รวมคอมมิตนั้นและไม่เปลี่ยนคะแนน): 7,989 การทดสอบที่ให้คะแนน 7,905 ดีเยี่ยม (98.95%) และ 84 ดี (1.05%) ไม่มีต่ำกว่าดี บวกอีก 17 การทดสอบที่แยกออกเนื่องจากข้อบกพร่องฝั่ง TradingView แยกต่างหาก ประตูความเท่าเทียมของเอนจินเองตรวจสอบคลังข้อมูลเปิด pineforge-corpus ซึ่งใครก็ตามสามารถทำซ้ำได้: 312 กลยุทธ์อ้างอิง 311 ดีเยี่ยมและ 1 การทดสอบที่ประกาศ expected_tier: anomaly ใน inputs.json ของมัน (รายงานเป็น anomaly ไม่ใช่ความล้มเหลว) ดีเยี่ยม หมายถึงจำนวนเทรดเท่ากัน อย่างน้อย 99% ของเทรด TradingView ตรงกัน ราคาเข้าและออกภายใน 0.01% และ P&L ต่อเทรดภายใน 1% ที่เปอร์เซ็นไทล์ที่ 90 (สคริปต์ trailing-stop ใช้โปรไฟล์การออก/P&L ที่ผ่อนปรนกว่า); ดี คือกรอบที่ผ่อนคลาย — ทั้งสองถูกกำหนดใน README ของคลังข้อมูลใน "เกณฑ์ความเท่าเทียม"

การทดสอบย้อนหลัง PineScript เป็นข้อมูลภายนอกที่คำนวณ ไม่ใช่ความรู้ที่เสถียร — มันขึ้นอยู่กับซอร์สกลยุทธ์ของผู้ใช้และ OHLCV ของพวกเขา และมันต้องทำซ้ำได้ นั่นคือการเรียกเครื่องมือ ไม่ใช่งานการเรียกคืน

เมื่อเครื่องมือเหล่านี้เหมาะสม backtest_pine (หรือ backtest_pine_grid สำหรับการสแกนพารามิเตอร์) ครอบคลุมกรณีที่ผู้ใช้ให้กลยุทธ์ PineScript v6 และต้องการทดสอบย้อนหลัง ประเมิน ตรวจสอบว่าทำกำไรได้หรือไม่ นับจำนวนเทรด คำนวณ P&L หรือทำซ้ำผลลัพธ์ TradingView บน OHLCV ที่ระบุ transpile_pine ครอบคลุมการแปลง Pine → C++ เท่านั้น check_tradingview_parity ครอบคลุมกรณีที่ผู้ใช้มีรายการเทรดของ TradingView สำหรับกลยุทธ์และต้องการทราบว่า PineForge ทำซ้ำได้หรือไม่ ทีละเทรด fetch_binance_ohlcv ครอบคลุมกรณีที่ผู้ใช้ระบุสัญลักษณ์/กรอบเวลาแต่ไม่ได้ให้ไฟล์ข้อมูล เครื่องมือเหล่านี้ไม่ใช่สำหรับอธิบายแนวคิดว่ากลยุทธ์ทำอะไร แก้ไขไวยากรณ์ Pine หรือให้คำแนะนำการเทรดหรือการเงิน

ข้อจำกัดที่ซื่อสัตย์ ออฟไลน์; PineScript v6 เท่านั้น; ต้องใช้ Docker; PineForge นำชุดย่อยของ Pine v6 ไปใช้ (ดู เครื่องมือความครอบคลุม) การทดสอบย้อนหลังวัดพฤติกรรมทางประวัติศาสตร์ของกลยุทธ์ — ไม่ใช่การคาดการณ์ผลตอบแทนในอนาคตและไม่ใช่คำแนะนำการลงทุน การทดสอบย้อนหลังแบบไร้เดียงสาหรือประมาณมักจะกล่าวเกินจริงถึงกำไร (สลิปเพจและค่าคอมมิชชันที่ไม่จำลอง สมมติฐานการเติมที่ราคาปิด อคติการมองไปข้างหน้า); คุณค่าที่นี่คือการรันที่กำหนดและตรวจสอบความเท่าเทียม เพื่อให้ผู้ใช้สามารถตรวจสอบกลยุทธ์ก่อนเสี่ยงเงินทุน

list_engine_params — ค้นพบตัวเลือก

แคตตาล็อกฟรี ในเครื่อง ไม่มี I/O ของทุกคีย์ที่ backtest_pine / backtest_pine_grid รองรับ แบ่งเป็นสองกลุ่ม:

  • strategy_overrides — ฟิลด์ส่วนหัว strategy(...) จำนวน 9 รายการที่รันไทม์ อ่านผ่าน PINEFORGE_OVERRIDES: initial_capital, pyramiding, slippage, commission_value, commission_type (percent / cash_per_order / cash_per_contract), default_qty_value, default_qty_type (fixed / percent_of_equity / cash), process_orders_on_close, close_entries_rule (ANY / FIFO)
  • runtime_args — อาร์กิวเมนต์ของ run_backtest_full (ไม่ใช่ส่วนหนึ่งของส่วนหัว strategy() ): input_tf, script_tf, bar_magnifier, magnifier_samples, magnifier_dist (uniform / cosine / triangle / endpoints / front_loaded / back_loaded)

แต่ละรายการคือ {key, type, enum?, description} เรียกสิ่งนี้ก่อนเพื่อเรียนรู้ว่า เอนจินยอมรับอะไรก่อนที่จะประกอบคำขอ backtest_pine

ตัวอย่าง backtest_pine

{
  "source": "//@version=6\nstrategy(\"sma cross\")\n...",
  "ohlcv_csv_path": "/work/btcusdt_15m_7d.csv",

  // Optional: override Pine input.*() values without touching the source.
  // Keys = the second arg of input.*(...) (e.g. "Fast Length").
  "inputs":    { "Fast Length": 8, "Slow Length": 21 },

  // Optional: override strategy(...) header fields. Each key is typed —
  // call list_engine_params for the catalog.
  "overrides": {
    "initial_capital":    100000,
    "default_qty_type":   "percent_of_equity",
    "default_qty_value":  10,
    "commission_type":    "percent",
    "commission_value":   0.04,
    "slippage":           2,
    "pyramiding":         0,
    "process_orders_on_close": true,
    "close_entries_rule": "ANY"
  },

  // Optional: engine runtime args (NOT strategy() header). Use script_tf
  // to aggregate the input CSV into a coarser strategy timeframe — the
  // engine REJECTS script_tf finer than input_tf, and the tool call then
  // fails (isError; "engine backtest failure (exit 4)" in the Docker image).
  "runtime": {
    "input_tf":          "15",
    "script_tf":         "60",
    "bar_magnifier":     true,
    "magnifier_samples": 8,
    "magnifier_dist":    "endpoints"
  },

  // Optional: where to write the full JSON report if it is too large to
  // return inline (see below). In Docker use an absolute path under /work.
  "report_path": "/work/report.json"
}

inputs ถูกส่งต่อเป็นตัวแปรสภาพแวดล้อม PINEFORGE_INPUTS ให้เอนจิน overrides เป็น PINEFORGE_OVERRIDES และแต่ละฟิลด์ runtime เป็น ตัวแปรสภาพแวดล้อม PINEFORGE_INPUT_TF / PINEFORGE_SCRIPT_TF / PINEFORGE_BAR_MAGNIFIER / PINEFORGE_MAGNIFIER_SAMPLES / PINEFORGE_MAGNIFIER_DIST แยกกัน ว่าง / ไม่ได้ตั้งค่า → ค่าเริ่มต้นจาก strategy.pine โดย input_tf ถูกตรวจจับอัตโนมัติจาก ช่องว่างระหว่างสองแถว CSV แรก

ส่งคืน JSON รายงานของอิมเมจ pineforge-release แบบสแตนด์อโลน (engine, input, summary, trades, metrics, equity_curve, fingerprint, applied_inputs, applied_overrides, applied_runtime, diagnostics, elapsed_seconds) บวก บล็อก _meta แบบอินไลน์เมื่อมันซีเรียลไลซ์ได้ไม่เกิน 200,000 ไบต์:

{
  "engine": "pineforge",
  "summary": { "total_trades": 49, "net_pnl": -190.85, ... },
  "applied_inputs":    { "Fast Length": "8", "Slow Length": "21" },
  "applied_overrides": { "default_qty_value": "5" },
  "trades": [ ... ],
  "equity_curve": [ ... ],
  "elapsed_seconds": 0.0042,
  "_meta": { "strategy_cpp_bytes": 5079, "image": "local" }   // npm/npx: the engine image name
}

การรันที่ยาวนาน (3,000 แท่งรายชั่วโมงก็เพียงพอ) ไม่พอดีกับผลลัพธ์เครื่องมือ MCP จากนั้น รายงานเต็มจะถูกเขียนไปยัง report_path — ค่าเริ่มต้น pineforge-backtest-<timestamp>.json ในไดเรกทอรีทำงานของเซิร์ฟเวอร์ — และเครื่องมือส่งคืนผลลัพธ์ขนาดกะทัดรัดแทน:

{
  "summary": { ... }, "applied_inputs": { ... }, "applied_overrides": { ... },
  "elapsed_seconds": 0.0008, "total_trades": 73,
  "report_path": "...", "report_path_in_container": "/work/report.json",
  "truncated": true, "note": "...", "_meta": { ... }
}

ในอิมเมจ Docker ให้ส่ง report_path แบบ absolute path ภายใต้ /work เสมอ ไฟล์จะได้ไปอยู่ในโฟลเดอร์ที่คุณ mount ไว้ หากไม่ระบุ รายงานจะถูกเขียนไว้ใต้ /app ภายในคอนเทนเนอร์ และจะหายไปพร้อมกับคอนเทนเนอร์นั้น (report_path และข้อความ note ถูกคำนวณโดยอ้างอิงกับ working directory ของคอนเทนเนอร์ ดังนั้นให้เชื่อถือไฟล์ที่คุณพบในโฟลเดอร์ที่ mount ไว้ มากกว่าสตริงเหล่านั้น) ขีดจำกัดแบบ inline คือ PINEFORGE_MAX_INLINE_BYTES

เพื่อให้ได้ host path แบบ absolute ที่ถูกต้องกลับมาใน report_path ให้รันเซิร์ฟเวอร์โดยใช้ /work เป็น working directory และระบุฝั่ง host ของ mount ใน PINEFORGE_HOST_WORKDIR entrypoint ของอิมเมจเป็น path ที่สัมพันธ์กับ /app ดังนั้นจึงต้องระบุ --entrypoint อย่างชัดเจน จากนั้น tool paths แบบสัมพันธ์จะ resolve ภายใน mount ด้วย:

docker run --rm -i -v "$PWD:/work" -w /work -e PINEFORGE_HOST_WORKDIR="$PWD" \
  --entrypoint node ghcr.io/pineforge-4pass/pineforge-backtest-mcp:latest /app/dist/index.local.js

ด้วย docker run แบบธรรมดาของ Install (working directory คือ /app) PINEFORGE_HOST_WORKDIR ยังคงทำให้ report_path เป็น absolute แต่ผิด: มันถูกต่อเข้ากับ path ของรายงานที่สัมพันธ์กับ /app

backtest_pine_grid — การกวาดพารามิเตอร์ (parameter sweep)

แปลงซอร์ส Pine เพียงครั้งเดียว (ในเครื่อง, ในคอนเทนเนอร์) จากนั้นคอมไพล์และรัน C++ นั้นสำหรับทุกชุดค่าผสมในผลคูณคาร์ทีเซียนของ inputs × overrides: ทุกชุดค่าผสมคือการ build g++ ใหม่ของ translation unit เดียวกัน จากนั้นจึงทำ backtest ของมัน คืนค่ารายการจัดอันดับพร้อมกับรายการสูงสุดภายใต้ best

{
  "source": "//@version=6\nstrategy(\"macd\")\n...",
  "ohlcv_csv_path": "/work/btcusdt_15m_7d.csv",

  // Each axis is {key: list-of-values}. All combinations are tried.
  "inputs": {
    "Fast Length": [8, 12, 19],
    "Slow Length": [21, 26, 39]
  },
  "overrides": {
    "default_qty_value": [1, 5],
    "commission_value":  [0.04]
  },

  // Optional knobs:
  "fixed_inputs":     { "Source": "close" },   // applied to every combo
  "fixed_overrides":  {},                      // typed strategy() overrides
  "runtime":          { "input_tf": "15",      // engine runtime args, fixed
                        "script_tf": "60" },   // across the sweep
  "max_combinations": 64,                      // default 64, at most 1024; a bigger grid is an error
  "concurrency":      2,                       // parallel runs: default 1, at most 8
  "include_trades":   false,                   // default false: omit per-trade lists
  "sort_by":          "net_pnl",               // net_pnl (default) | win_rate_pct | max_drawdown | total_trades
  "report_path":      "/work/grid.json"        // where an oversized sweep is written
}

ผลลัพธ์มี total_combinations, succeeded, failed, sort_by, best และ results (การรันที่สำเร็จจัดอันดับตาม sort_by จากมากไปน้อย จากนั้นจึงเป็นรายการที่ล้มเหลว) การกวาดที่ใหญ่เกินกว่าจะคืนค่าแบบ inline จะถูกเขียนไปยัง report_path และ tool จะคืนค่า best ซึ่งคือ 10 อันดับแรกใน top_results, results_truncated และ report_path

check_tradingview_parity — ให้คะแนนผลลัพธ์ TradingView ของคุณ

ส่งสคริปต์ Pine v6 และไฟล์ส่งออก Strategy Tester ของ TradingView เองสำหรับสคริปต์นั้น มันจะรันสคริปต์บนตลาดและช่วงเวลาเดียวกัน และให้คะแนนรายการเทรดสองรายการทีละเทรดด้วย grader ที่อยู่เบื้องหลังตัวเลข parity ที่เผยแพร่ของ PineForge: scripts/verify_corpus.py ของ pineforge-engine v1.0.1 (sha256 de84d5150ac0a29b67906f1f8b6fe1f1f13ac66ed36be88ea2bc63d7280ed298) รันผ่าน harness ของ corpus gate เอง (scripts/run_strategy.py) ทั้งสองถูก vendor ไว้โดยไม่เปลี่ยนแปลงภายใต้ parity/vendor/ ตรวจสอบกับ pineforge-corpus แบบเปิดที่ a35c7c4: ภายในอิมเมจ Docker นี้ แกนการให้คะแนนจะคืนค่า tier ที่เผยแพร่สำหรับโพรบทั้งหมด 309 รายการที่ corpus gate ให้คะแนน และตัว tool เอง เมื่อเรียกผ่าน stdio ด้วยเฉพาะอินพุตด้านล่าง จะคืนค่าให้สำหรับตัวอย่างแบบ stratified จำนวน 30 รายการ

{
  "pine": "//@version=6\nstrategy(\"my strategy\")\n...",
  // The "List of trades" CSV as TradingView exports it, or the Strategy Tester
  // XLSX report base64-encoded (it starts with UEsDB).
  "tradingview_trades": "Trade number,Type,Date and time,Signal,Price USDT,...",
  "symbol": "BINANCE:ETHUSDT.P",          // TradingView ticker
  "timeframe": "15",                      // TradingView resolution: 1, 5, 15, 60, 240, 1D, ...
  "range_start": "2025-04-01T00:00:00Z",  // first bar TradingView computed (UTC unless an offset is given)
  "chart_timezone": "Asia/Taipei",        // the timezone TradingView printed the trade times in

  // Optional:
  "range_end": "2025-10-01T00:00:00Z",    // default: the export's last row
  "inputs": { "Fast Length": 8 },         // TradingView's Inputs tab, as in backtest_pine
  "strategy_overrides": { "commission_value": 0.04 },  // TradingView's Properties tab (list_engine_params)
  "runtime": { "bar_magnifier": true },   // list_engine_params runtime args
  "max_mismatches": 10,                   // mismatching trades to list: default 10, at most 50
  "ohlcv_csv_path": "/work/eth_15m.csv"   // or "ohlcv_csv": "<CSV text>": your own bars
}
inputหมายเหตุ
pineซอร์ส Pine v6, สูงสุด 256 KiB
tradingview_tradesข้อความ CSV "List of trades" (คอลัมน์ Trade number, Type, Date and time, คอลัมน์ Price) หรือรายงาน XLSX เป็น base64
symbolticker ของ TradingView; จำเป็นเว้นแต่ XLSX ระบุไว้หรือคุณส่ง bars
timeframeresolution ของ TradingView; จำเป็นเว้นแต่ XLSX ระบุไว้
range_startวันที่หรือ datetime แบบ ISO 8601 ของแท่งแรกของ backtest; จำเป็นเว้นแต่ XLSX ระบุไว้
range_endไม่บังคับ; ค่าเริ่มต้น: แถวสุดท้ายของไฟล์ส่งออก (ผลลัพธ์จะบอกไว้)
chart_timezoneชื่อโซนเวลาแบบ IANA ที่เวลาเทรดถูกพิมพ์ไว้ (รูปแบบออฟเซ็ตแบบ UTC+8 ก็ยอมรับ); จำเป็นเว้นแต่ไฟล์ส่งออกระบุไว้; การตั้งค่า "Exchange" ของ TradingView จะไม่ถูกเดา
inputs, strategy_overrides, runtimeไม่บังคับ, คีย์เดียวกันกับ backtest_pine
max_mismatchesไม่บังคับ, ค่าเริ่มต้น 10, สูงสุด 50
ohlcv_csv / ohlcv_csv_pathbars ของคุณ เพื่อให้ตลาดใดก็ได้ทำงาน: timestamp,open,high,low,close,volume (epoch ms) หรือ chart export ของ TradingView แบบ time,open,high,low,close,Volume (epoch seconds หรือ ISO 8601); path เป็นไปตาม กฎ backtest_pine
magnifier_ohlcv_csv / magnifier_ohlcv_csv_pathbars 1 นาทีแบบไม่บังคับสำหรับ bar magnifier ที่ประกาศไว้ ครอบคลุมตั้งแต่ open ของแท่งแรกจนถึง close ของแท่งสุดท้าย; รูปแบบ ขีดจำกัด และกฎ path เดียวกับ ohlcv_csv / ohlcv_csv_path

ขีดจำกัด (ถูกปฏิเสธด้วยข้อผิดพลาดธรรมดาเมื่อเกิน):

อะไรขีดจำกัด
pine262,144 ไบต์ (256 KiB) ของ UTF-8
tradingview_trades33,554,432 อักขระ (32 × 1024²) ตามที่ส่ง; รายการเทรดที่ grader อ่าน (CSV หรือรายการที่สร้างใหม่จาก XLSX) สูงสุด 32 MiB ของ UTF-8 และ 400,000 แถว
รายงาน XLSXแต่ละส่วนที่ decompress แล้วสูงสุด 64 MiB, ทุกส่วนรวมกันสูงสุด 128 MiB; ชีตหนึ่งสูงสุด 400,000 แถวและ 256 คอลัมน์; ชีตที่อ่าน (List of trades และ Properties) รวมกันสูงสุด 8,000,000 เซลล์ นับเซลล์ว่างภายในแต่ละแถวด้วย; สูงสุด 2,000,000 shared strings
ohlcv_csv67,108,864 อักขระ (64 × 1024²)
ohlcv_csv_pathไม่มีขีดจำกัดขนาด (chart export ของ TradingView ถูกแปลงในหน่วยความจำ)
การดึง Binanceรวม 100,000 chart และ magnifier bars
เวลารันPINEFORGE_PARITY_TIMEOUT_MS, ค่าเริ่มต้น 600,000 ms สำหรับ transpile, compile, backtest และ grading รวมกัน

ไม่มีโควตาและไม่มีกรอบประวัติที่นี่: ช่วงถูกจำกัดโดย bars ที่คุณส่งเท่านั้น หรือโดยการดึง Binance 100,000 bars

Bars. ohlcv_csv / ohlcv_csv_path ของคุณเมื่อระบุ มิฉะนั้น BINANCE:<SYMBOL> จะถูกดึงเป็น Binance spot klines และ BINANCE:<SYMBOL>.P เป็น USDT-M perpetual klines จาก API สาธารณะ สูงสุด 100,000 bars สัญลักษณ์อื่นใดที่ไม่มี bars จะเป็นข้อผิดพลาดที่ขอให้ส่ง bars สคริปต์ที่ประกาศ use_bar_magnifier = true จะดึง bars 1 นาทีจนถึง close ของแท่งสุดท้ายด้วย นับในขีดจำกัดเดียวกัน เมื่อ chart เป็นแบบที่ harness ขยาย (หยาบกว่า 1 นาที, สูงสุด 1 วัน) และ runtime.bar_magnifier ไม่ใช่ false ด้วย bars ของคุณเอง คุณสามารถส่ง magnifier_ohlcv_csv / magnifier_ohlcv_csv_path แบบไม่บังคับ; หากสคริปต์ประกาศ magnifier แต่รันโดยไม่มี ผลลัพธ์จะเตือนว่า fills ภายในแท่งอาจแตกต่างจากของ TradingView

รายงาน XLSX. ชีต "List of trades" ถูกอ่านเหมือนกับ CSV (วันที่แบบ Excel กลายเป็น YYYY-MM-DD HH:MM) ชีต "Properties" ให้สัญลักษณ์ timeframe ช่วงวันที่ เงินทุนเริ่มต้น ขนาดคำสั่ง pyramiding ค่าคอมมิชชัน slippage และตัวเลือก fill ที่ระบุ; คุณสามารถส่งการตั้งค่าเดียวกันอย่างชัดเจน แต่ค่าที่ขัดแย้งกับไฟล์ส่งออกจะเป็นข้อผิดพลาดที่ระบุทั้งสองค่า Strategy inputs ที่ระบุในไฟล์ส่งออกจะถูกรายงาน ไม่ถูกนำไปใช้: ส่ง inputs สำหรับค่าใดก็ตามที่คุณเปลี่ยน TradingView ไม่ได้บันทึกโครงสร้างนี้ ดังนั้นชื่อชีตและคีย์จึงถูกจับคู่แบบหลวม ๆ และคีย์ที่ไม่รู้จักจะถูกละเว้น

ผลลัพธ์. บล็อกข้อความธรรมดาและข้อมูลเดียวกันเป็น JSON (structuredContent): tier และความหมาย การตรวจสอบทุกครั้งพร้อมค่าและเกณฑ์ จำนวนเทรดที่ตรงกันและจำนวนที่เป็น TradingView-only หรือ PineForge-only ความไม่ตรงกันแรกแบบเคียงข้างกันพร้อมคำใบ้เมื่อข้อมูลแสดง (ขอบหน้าต่าง, ตำแหน่งที่เปิดอยู่ที่ปลายช่วง, ขนาด, ค่าคอมมิชชันหรือ slippage, โซนเวลา), การตรวจสอบโซนเวลา, หน้าต่าง และเวอร์ชัน engine, codegen และ grader เทรดจะจับคู่เมื่อมีทิศทางเดียวกัน, เข้าภายในหนึ่งชั่วโมง และราคาเข้าภายใน $3 หากเทรดที่ตรงกันส่วนใหญ่อยู่ที่ออฟเซ็ตที่ไม่เป็นศูนย์เดียวกัน หรือโซนเวลาอื่นตรงกับเทรดมากกว่าอย่างชัดเจน ผลลัพธ์จะบอกไว้; tier ยังคงเป็นโซนเวลาที่คุณระบุ

Tiers ตามที่ verify_corpus.py v1.0.1 ให้คะแนน Count Δ คือ |TradingView − PineForge| / max(TradingView, PineForge) เทรด; ค่า p90 คือเปอร์เซ็นไทล์ที่ 90 ของความแตกต่างสัมพัทธ์ต่อเทรดเหนือเทรดที่ตรงกัน; coverage คือเทรดที่ตรงกันต่อเทรดที่ปิดทั้งหมดของ TradingView

tierกฎ
excellentจำนวนเทรดเท่ากัน; coverage ≥ 99 % หรือมีเทรดไม่ตรงกันอย่างมาก 1 รายการ; ราคาเข้า p90 < 0.01 %; ราคาออก p90 < 0.01 % (โปรไฟล์ production: < 0.05 %); P&L p90 < 1 % (โปรไฟล์ production: < 100 %); เมื่อ TradingView แสดงหลายรายการที่เวลาและราคาเดียวกัน PineForge มีจำนวนเท่ากัน
strongcoverage ≥ 95 % หรือมีเทรดไม่ตรงกันอย่างมาก 1 รายการ; count Δ < 6 %; ราคาเข้า p90 < 0.1 %; ราคาออก p90 < 0.5 %; P&L p90 < 100 %
moderatecoverage ≥ 75 % และอย่างน้อย 90 % ของเทรด TradingView ตรงกัน
weakมีเทรดตรงกันอย่างน้อยหนึ่งรายการ
minimalไม่มีเทรดตรงกัน

โปรไฟล์ production ใช้เมื่อสคริปต์ตั้งค่า trail_points, trail_offset หรือ trail_price บน strategy.exit; สคริปต์อื่นทุกตัวถูกให้คะแนนด้วยโปรไฟล์ที่เข้มงวด วิธีการ: https://pineforge.dev/en/methodology/

การเก็บรักษา. ทุกอย่างรันบนเครื่องของคุณ; ข้อมูลตลาดถูกดึงจาก Binance เฉพาะเมื่อคุณไม่ส่ง bars สคริปต์และรายการเทรด และ bars ที่ต้องแปลงหรือดึง ไปยังโฟลเดอร์ชั่วคราวที่ถูกลบเมื่อการตรวจสอบสิ้นสุด ด้วย npm/npx การตรวจสอบรันในอิมเมจ engine (docker run --network=none, แกน grading และ bars ของคุณถูก mount แบบอ่านอย่างเดียว)

fetch_binance_ohlcv — ดึงข้อมูลตลาด

เขียน CSV ที่พร้อมสำหรับ backtest (ส่วนหัว timestamp,open,high,low,close,volume, timestamp = เวลาเปิดใน UNIX ms UTC) จาก endpoints สาธารณะของ Binance ไม่ต้องใช้การรับรองความถูกต้อง คำขอ > 1000 bars ถูกแบ่งหน้าโดยอัตโนมัติ output_path ปฏิบัติตามกฎเดียวกันกับ ohlcv_csv_path: ใน Docker ให้ใช้ absolute path ภายใต้ /work; ด้วย npx จะต้องอยู่ใน working directory เว้นแต่ PINEFORGE_ALLOW_ANYWHERE=1

{
  "symbol":      "BTCUSDT",
  "interval":    "15m",          // 1s (spot only), 1m, 3m, 5m, 15m, 30m, 1h, 2h, 4h, 6h, 8h, 12h, 1d, 3d, 1w, 1M
  "market":      "spot",         // default; or "usdt_perp" for USDT-margined perpetual futures
  "limit":       672,            // total bars: default 1000, at most 100000; > 1000 paginates
  "output_path": "/work/btcusdt_15m_7d.csv"
  // Optional: "start_time" / "end_time" in UNIX ms UTC.
}

binance_symbols — ค้นพบ / ตรวจสอบสัญลักษณ์

คืนค่ารายการสัญลักษณ์ที่พร้อมใช้งานบน API สาธารณะของ Binance สำหรับการดึง OHLCV แคช 5 นาทีในกระบวนการ ใช้เพื่อตรวจสอบสัญลักษณ์ก่อนเรียก fetch_binance_ohlcv

{
  "market":        "usdt_perp",   // required: "spot" or "usdt_perp"
  "query":         "BTC",         // case-insensitive substring match
  "quote_asset":   "USDT",
  "base_asset":    "BTC",
  "status":        "TRADING",
  "contract_type": "PERPETUAL",   // futures-only filter
  "limit":         50             // default 200, at most 2000
}

เครื่องมือความครอบคลุม (Coverage tools)

PineForge ใช้ ชุดย่อย ของ Pine v6 ดังนั้นโปรดตรวจสอบก่อนเขียนหรือพอร์ตกลยุทธ์:

  • list_coverage_topics — ทุกหัวข้อความครอบคลุมพร้อมสถานะ (supported, partial, unsupported, via_transpiler) และบทสรุป พร้อมคำอธิบายสัญลักษณ์
  • get_coverage_topic { "topic": "ta" } — รายการ supported / partial / via_transpiler / unsupported เต็มรูปแบบสำหรับหนึ่ง id หัวข้อ (ตัวอย่างเช่น ta, strategy_orders, request_security)
  • check_pine_feature { "feature": "ta.supertrend" } — หนึ่ง identifier หรือ namespace: supported / partial / unsupported / via_transpiler / not_found พร้อมหมายเหตุที่อ้างอิงรายการในแคตตาล็อก Plots, tables และ alerts (plot, bgcolor, table, alert) ถูกยอมรับและไม่มีผล; ออบเจกต์ line, box และ label เป็นข้อมูลที่กลยุทธ์สามารถอ่านกลับได้

ทุกสถานะอธิบายสิ่งที่ backtest ผ่านเซิร์ฟเวอร์นี้สามารถทำได้ เซิร์ฟเวอร์ไม่ได้ติดตั้ง bars ของสัญลักษณ์อื่น ข้อมูลคำขอที่บันทึก หรือซอร์สไลบรารี Pine ดังนั้นเมื่อ engine รองรับมากกว่านั้น รายการจะบอกไว้: request.security บนสัญลักษณ์อื่น ตัวอย่างเช่น ได้รับการสนับสนุนโดย engine แต่ที่นี่ คำขอที่มีค่าถึงเทรดได้จะหยุดการรัน

ข้อมูลถูกฝังในแพ็คเกจนี้และประทับด้วยฟิลด์ coverage_version ที่ list_coverage_topics คืนค่า (engine v1.0.1 + codegen 1.0.1 (2026-10-02) ในเวอร์ชันนี้); docs/coverage.md ของ engine ที่แท็กนั้นเป็นข้อมูลอ้างอิงที่ใช้ตรวจสอบ

ขอบเขตระบบไฟล์

ด้วย npx path ของ OHLCV, เอาต์พุต และรายงานต้องอยู่ใน working directory ปัจจุบันของกระบวนการ MCP server โดยค่าเริ่มต้น การตรวจสอบรันบน path ที่ resolve แล้ว: ส่วน .. และ symbolic links ถูก resolve ก่อน ดังนั้นทั้งคู่ไม่สามารถชี้ไปนอกนั้นได้ และ symbolic link ที่ target ไม่มีอยู่จะถูกปฏิเสธ ไฟล์ข้อมูลหรือโฟลเดอร์ที่ลิงก์เข้าไปใน working directory จากภายนอกจึงถูกปฏิเสธเช่นกัน ใช้การแทนที่ด้วย:

export PINEFORGE_ALLOW_ANYWHERE=1

อิมเมจ Docker ตั้งค่า PINEFORGE_ALLOW_ANYWHERE=1 เอง (คอนเทนเนอร์คือ sandbox) ดังนั้น path ใดก็ได้ถูกยอมรับที่นั่น — ใช้ absolute /work/... paths

ตัวแปรสภาพแวดล้อมอื่น ๆ

ตัวแปรค่าเริ่มต้นวัตถุประสงค์
PINEFORGE_IMAGEghcr.io/pineforge-4pass/pineforge-release:latestเฉพาะ npm/npx: อิมเมจเอนจิน (รันไทม์ + โค้ดเจนที่รวมอยู่) ใช้สำหรับ transpile + backtest
PINEFORGE_ALLOW_ANYWHERE0 (1 ในอิมเมจ Docker)อนุญาตให้เส้นทาง OHLCV / output / report อยู่นอก cwd
PINEFORGE_DOCKER_TIMEOUT_MS120000การหยุดแบบบังคับสำหรับการรันเอนจินแต่ละครั้งและสำหรับ docker pull
PINEFORGE_MAX_INLINE_BYTES200000รายงานที่ใหญ่ที่สุดที่ส่งกลับแบบอินไลน์; รายงานที่ใหญ่กว่านั้นจะถูกเขียนไปยัง report_path
PINEFORGE_PARITY_TIMEOUT_MS600000ขีดจำกัดเวลาของการรัน check_tradingview_parity หนึ่งครั้ง (transpile, compile, backtest, grading)
PINEFORGE_HOST_WORKDIRไม่ตั้งค่าDocker: ไดเรกทอรีโฮสต์ที่เมานต์ที่ /work; เมื่อตั้งค่า report_path จะเป็นเส้นทางโฮสต์แบบสัมบูรณ์ — ถูกต้องเฉพาะเมื่อเซิร์ฟเวอร์รันด้วย /work เป็นไดเรกทอรีทำงาน (ดูท้ายตัวอย่าง backtest_pine)

ด้วย Docker ให้ส่งค่าเหล่านี้เป็น -e NAME=value

พัฒนา

npm ci
npm run build     # tsc; also writes the gitignored src/version.ts
npm test

เพื่อสร้างอิมเมจ ให้ส่งเวอร์ชัน pineforge-release ที่จะใช้สร้าง (แท็กจาก หน้า Releases ของมัน โดยไม่มี v):

docker build -f docker/Dockerfile --build-arg PINEFORGE_RELEASE_VERSION=<X.Y.Z> -t pineforge-backtest-mcp .

ใบอนุญาต

เซิร์ฟเวอร์นี้ได้รับอนุญาตภายใต้ MIT (LICENSE) อิมเมจยังรวม pineforge-engine (Apache-2.0) และตัว transpiler ของ pineforge-codegen (ซอร์สที่เปิดให้ใช้: PolyForm Noncommercial 1.0.0 พร้อมข้อยกเว้นการซื้อขายส่วนบุคคล; การใช้งานเชิงพาณิชย์หรือแบบโฮสต์ต้องมีใบอนุญาตเชิงพาณิชย์) ดู LEGAL.md