canli-validation-mcp
Valida un backtest antes de confiar en él: ratio de Sharpe deflactado, sobreajuste de backtest (CSCV), evidencia en papel y comprobaciones de amplitud a través de una API gratuita, cada una devolviendo un recibo recalculable. También lee el historial financiero reportado de las empresas a partir de los archivos de la SEC. Ejecuta con npx -y canli-validation-mcp.
Documentación
canli-validation-mcp
Un servidor MCP (Protocolo de Contexto de Modelo) sobre la API de validación gratuita con clave de canlicapital.com. Proporciona a un agente de codificación nueve herramientas: emitir una clave gratuita, ejecutar los cinco validadores (Sharpe deflactado, sobreajuste CSCV, conformidad con evidencia de papel, límite de amplitud, longitud mínima de historial), recuperar un recibo almacenado, leer el estado del servicio y leer el historial financiero reportado de una empresa a partir de presentaciones ante la SEC. Cada herramienta devuelve el sobre completo de la API como texto de resultado, ya sea éxito o error, para que el agente no pueda ver un número sin las frases que lo acompañan y que indican qué es lo que ese número no establece.
Este paquete se publica en npm como canli-validation-mcp.
También está listado en el Registro oficial de MCP (io.github.arhancanli/canli-validation-mcp) y en
cursor.directory. Ejecútelo con npx, sin paso de instalación, como se muestra a continuación. Solo se necesita una copia local para desarrollar o probar este paquete en sí; consulte "Copia local" cerca del final.
Este README describe la versión en package.json. npx sin versión ejecuta la última versión de npm; npx -y canli-validation-mcp@<version> fija una versión específica.
Qué es la API (y qué no es)
El motor es el producto. El servicio procesa los números que usted envía mediante la misma aritmética de honestidad que el propio registro de papel de canlicapital.com aplica sobre sí mismo y devuelve un veredicto que cualquiera puede recalcular a partir del recibo. No acepta datos de mercado, no firma recibos, no califica una estrategia y nunca ve su fuente de datos, sus costos ni ningún lookahead en cómo se construyó una serie. Consulte docs/superpowers/specs/2026-09-05-developer-key-validation-api-design.md en el repositorio principal para ver el diseño completo.
Herramientas
| Herramienta | Llamadas | Clave requerida |
|---|---|---|
get_key | POST /api/v1/keys | no |
validate_deflated_sharpe | POST /api/v1/validate/deflated-sharpe | sí |
validate_overfitting | POST /api/v1/validate/overfitting | sí |
validate_paper_evidence | POST /api/v1/validate/paper-evidence | sí |
validate_breadth | POST /api/v1/validate/breadth | sí |
validate_track_record | POST /api/v1/validate/track-record | sí |
get_receipt | GET /api/v1/receipts/{id} | no |
service_status | GET /api/v1/validate/status | no |
company_financial_history | GET /company-data/{cik}.json (un ticker se resuelve mediante GET /api/v1/company-tickers.json) | no |
validate_deflated_sharpe acepta exactamente una de dos formas de entrada, nunca una mezcla de ambas:
- los siete campos del contrato:
observed_sharpe_annualized,observations,periods_per_year,skew,non_excess_kurtosis,effective_independent_trials,cross_trial_sharpe_sd_annualized; - o una serie de retornos más los ensayos detrás de ella:
returns,periods_per_year,effective_independent_trials,cross_trial_sharpe_sd_annualized.
El envío de campos de ambas formas, o de ninguna, se rechaza antes de que cualquier solicitud salga del proceso; consulte src/schemas.mjs.
company_financial_history es diferente de las otras herramientas: lee la referencia de empresa pública en canlicapital.com, no la API de validación. Proporcione un CIK (de 1 a 10 dígitos) para listar los historiales financieros disponibles de una empresa, o un CIK y un concepto us-gaap como Revenues para obtener las observaciones, de la más reciente a la más antigua (limit tiene un valor predeterminado de 40, máximo 200). Cada observación conserva su accession de presentación, formulario, fecha de presentación y unidad, y el resultado incluye el SHA-256 de la respuesta original de la SEC y la frase límite propia del registro: son valores contables tal como se reportaron a la SEC, no precios de mercado, retornos ni una recomendación. Las empresas y conceptos fuera de la versión actual devuelven un error con los conceptos disponibles listados.
Prompts, recursos y resultados estructurados
Los clientes que muestran prompts de MCP ofrecen dos flujos de trabajo guiados: validate_backtest (Sharpe deflactado, luego sobreajuste, luego el historial necesario, informado con lo que cada número no establece) y track_record_needed. Se pueden leer dos recursos: canli://limits, las frases límite que cada resultado lleva, y canli://sources, los documentos detrás de cada validador y cómo se verifica cada uno contra ellos. Cada resultado de herramienta lleva su sobre tanto como texto como structuredContent.
Contexto compacto (0.3.0)
Un agente paga por cada token que devuelve una herramienta, incluido el espacio en blanco que nunca lee. Desde 0.3.0 cada resultado es JSON minimizado, y un historial de empresa devuelve sus observaciones como un encabezado columns y una fila por observación, con una unidad compartida por cada fila indicada una sola vez. No se elimina ningún campo: cada frase límite, número de accession, formulario, fecha de presentación y hash de fuente sigue en el resultado, y columns + rows reconstruyen cada observación exactamente.
Medido con bench/token_cost.py en registros reales (tokenizador: tiktoken o200k_base; otros tokenizadores dan recuentos absolutos diferentes), 20 observaciones cada uno:
| Registro | 0.2.0 (con sangría) | minimizado | 0.3.0 (minimizado, columnar) |
|---|---|---|---|
| Apple, StockholdersEquity | 2,214 | 1,560 (−29.5%) | 1,060 (−52.1%) |
| Microsoft, CashAndCashEquivalentsAtCarryingValue | 2,231 | 1,574 (−29.4%) | 1,065 (−52.3%) |
Las herramientas de validación solo ganan la minimización: el sobre service_status en vivo midió 593 tokens con sangría y 475 minimizados (−19.9%); sus frases límite se conservan palabra por palabra. Estas son mediciones de estos resultados, no una afirmación sobre ningún otro servidor.
Cambio importante desde 0.2.0: history.observations ahora es {unit?, columns, rows} en lugar de un array de objetos.
Configuración
| Variable | Predeterminado | Significado |
|---|---|---|
CANLI_API_BASE | https://canlicapital.com | Dónde vive la API. Apúntela a un despliegue de vista previa para pruebas. |
CANLI_KEY | sin establecer | Una clave ya emitida desde POST /api/v1/keys. Cuando se establece, get_key no envía ninguna solicitud e informa que la clave ya está configurada; cada otra herramienta la envía como Authorization: Bearer <key>. |
CANLI_LOCAL | sin establecer | 1 o true ejecuta los cinco validadores en esta máquina (modo local privado, abajo): sin clave, sin red, sin recibo. |
Si CANLI_KEY no está establecida y el modo local está desactivado, llame a get_key una vez por sesión antes de los validadores. La clave que devuelve vive solo en la memoria de este proceso durante la vida de la sesión; no se escribe en disco.
Los fallos HTTP y los sobres de error de la API se marcan como errores de herramienta de MCP mientras se conserva el sobre JSON completo. Una validación exitosa con un veredicto negativo sigue siendo un resultado normal. Las solicitudes tienen un plazo de 30 segundos que cubre encabezados y cuerpo, rechazan redirecciones y nunca se reintentan automáticamente. Puede ocurrir un tiempo de espera después de que el servicio haya procesado una solicitud; verifique el estado del servicio antes de decidir enviar de nuevo. Los cuerpos de respuesta que no son JSON y los errores de red sin procesar se omiten de los errores de herramienta.
Instalación
Sin paso de instalación. npx obtiene el paquete publicado en la primera ejecución, por lo que cada configuración de cliente a continuación simplemente inicia npx -y canli-validation-mcp. Consulte "Copia local" cerca del final para desarrollar o probar este paquete en sí en lugar de ejecutar el publicado.
Endpoint alojado (sin instalación)
Las mismas herramientas se sirven en https://canlicapital.com/mcp mediante MCP Streamable HTTP, para clientes que se conectan a una URL en lugar de iniciar un proceso (conectores de Claude.ai, ChatGPT, servidores remotos de Cursor). Nada que instalar y sin Node.js en su máquina.
claude mcp add --transport http canli https://canlicapital.com/mcp
Sin una clave, las solicitudes se ejecutan bajo una clave anónima compartida, por lo que la cuota diaria de validación es compartida por cada llamador alojado. Para su propia cuota, emita una clave gratuita (consulte /developers) y envíela como encabezado:
claude mcp add --transport http canli https://canlicapital.com/mcp --header "Authorization: Bearer $CANLI_KEY"
El endpoint no tiene estado. En él, get_key no emite nada y dice qué clave está en uso, porque una clave emitida allí no llegaría a la siguiente solicitud. Un encabezado Authorization malformado se rechaza en lugar de reemplazarse con la clave compartida.
Claude Desktop
Agregue a claude_desktop_config.json (Configuración, Desarrollador, Editar configuración):
{
"mcpServers": {
"canli": {
"command": "npx",
"args": ["-y", "canli-validation-mcp"]
}
}
}
Reinicie Claude Desktop después. Agregue un objeto "env" con CANLI_API_BASE para apuntar esto a un despliegue de vista previa en lugar del predeterminado.
Claude Code
claude mcp add canli -- npx -y canli-validation-mcp
Ejecute claude mcp list para confirmar que está registrado y claude mcp remove canli para eliminarlo.
Modo local privado
Establezca CANLI_LOCAL=1 y los cinco validadores se ejecutan en su máquina: nada sobre la serie que usted envía se envía a canlicapital.com, no se necesita clave y no se almacena ningún recibo. El cálculo es el propio de la API, enviado byte por byte en src/local (una prueba falla si se desvía), por lo que un resultado local es igual al alojado; no nombra ningún id de recibo porque no se creó ninguno.
claude mcp add canli-local --env CANLI_LOCAL=1 -- npx -y canli-validation-mcp
get_receipt, service_status y company_financial_history aún leen desde canlicapital.com; no envían ninguna serie. En la extensión de Claude Desktop, esta es la configuración "Modo local privado".
Cliente stdio genérico
Cualquier cliente de MCP que pueda iniciar un proceso y hablar stdio funcionará. Usando el SDK oficial directamente, desde Node:
import { Client } from "@modelcontextprotocol/sdk/client/index.js";
import { StdioClientTransport } from "@modelcontextprotocol/sdk/client/stdio.js";
const transport = new StdioClientTransport({
command: "npx",
args: ["-y", "canli-validation-mcp"],
env: { ...process.env, CANLI_API_BASE: "https://canlicapital.com" },
});
const client = new Client({ name: "my-agent", version: "0.1.0" });
await client.connect(transport);
const { tools } = await client.listTools();
console.log(tools.map((t) => t.name));
const keyResult = await client.callTool({ name: "get_key", arguments: { label: "my-agent" } });
if (keyResult.isError) throw new Error("Key setup failed; inspect the error privately.");
// The session retains the issued key. Avoid printing its envelope into logs.
const result = await client.callTool({
name: "validate_deflated_sharpe",
arguments: {
returns: [0.004, -0.002, 0.007, 0.001, -0.003, 0.005, 0.002, -0.001],
periods_per_year: 252,
effective_independent_trials: 30,
cross_trial_sharpe_sd_annualized: 0.5,
},
});
console.log(result.content[0].text); // the full envelope, including limits and receipt.url
await client.close();
Qué no establece un resultado (lenguaje límite)
Cada sobre que este servidor devuelve lleva estas frases, textualmente, de la propia API (api/_lib/limits.js):
- Este veredicto trata sobre la serie exactamente como se envió. El servicio nunca vio la fuente de datos, sus costos, la supervivencia ni ningún lookahead en cómo se construyó la serie.
- Una probabilidad de Sharpe deflactado o de sobreajuste por encima o por debajo de cualquier umbral no es admisión a nada ni es un pronóstico.
- El recibo tiene hash de contenido y es reproducible desde el núcleo de código abierto que nombra. No está firmado.
- Cuotas: 1000 validaciones por clave por día UTC, 5 claves por cliente por día UTC, 1048576 bytes por solicitud, 20000 observaciones por serie, 200 variantes por matriz.
La descripción de cada herramienta también establece una de estas frases, para que un agente vea el límite antes de llamar a la herramienta, no solo después. Ninguna herramienta en este servidor elimina limits o receipt.url de una respuesta; el sobre completo es siempre el texto de resultado.
Copia local
Solo se necesita para desarrollar o probar este paquete en sí, no para ejecutar el publicado.
cd mcp
npm ci
node src/server.mjs
Apunte un cliente a la copia local en lugar de npm iniciando node /absolute/path/to/meridian/mcp/src/server.mjs en lugar de npx -y canli-validation-mcp en cualquier configuración anterior.
Pruebas
npm test
npm run test:package
Ejecuta node --test sobre test/*.test.mjs: recorridos de ida y vuelta de esquema contra el propio OpenAPI de la API y ejemplos de manifiesto, un caso de éxito, uno de sobre de error y uno de cuota 429 por herramienta con clave (un fetch falso representa a la red), una verificación de que cada descripción de herramienta lleva una frase de límites, una verificación de que esas frases no se han desviado de api/_lib/limits.js, una verificación de que ningún archivo enviado contiene una raya em, y una prueba que inicia el binario real del servidor y realiza un apretón de manos real de MCP tools/list y callTool sobre stdio contra un stub HTTP local, de modo que el cableado esté probado en lugar de asumido.
test:package crea el tarball real de npm, verifica su lista exacta de archivos y licencia, lo instala en un directorio de consumidor temporal y ejecuta la prueba stdio contra esa entrada instalada. La instalación de dependencias contacta a npm; las llamadas de herramienta usan solo el stub HTTP local. No publica un paquete ni emite una clave de API de producción.
Dependencias
Solo @modelcontextprotocol/sdk (fijada exacta) y zod (fijada exacta). No se agrega ninguna otra dependencia de tiempo de ejecución, y nada en este paquete toca el package.json, .vercelignore, api/, scripts/, js/ o public/ raíz del sitio.