Data lake local de acciones A para agentes de IA
ashare-lake crea un data lake local de acciones A con 39 conjuntos de datos, registros de deslistadas, consultas retrospectivas y un servidor MCP para agentes.
Un data lake local de acciones A contiene el historial del mercado accionario de China continental en archivos Parquet columnares almacenados en tu propio disco. Puedes leerlos con DuckDB o Polars, en lugar de consultar un endpoint de un proveedor página por página. ashare-lake es un proyecto de código abierto que crea ese repositorio, incluye el proceso diario que lo mantiene actualizado y ofrece un servidor del Model Context Protocol para que un agente de IA pueda consultarlo. Dos decisiones de diseño justifican este artículo: conserva las emisoras deslistadas y permite consultar los fundamentales tal como estaban disponibles en una fecha pasada.
Por qué un agente de IA necesita un data lake local de acciones A
Un agente que investiga acciones chinas sin una copia local tiene dos opciones. Puede extraer datos de páginas financieras, consumir su ventana de contexto con HTML y generar cifras que nadie podrá reproducir el próximo mes. O puede consultar un proveedor que exige registro, limita el número de filas y vincula cada resultado a una cuenta.
La escala es el aspecto que más se subestima. Nuestro data warehouse conserva el tape de EE. UU. con resolución de un minuto, y una semana normal de datos se ve así:
El SQL exacto detrás de cada cifra
SELECT toDate(toTimeZone(window_start, 'America/New_York')) AS session,
formatDateTime(toDate(toTimeZone(window_start, 'America/New_York')), '%b %e') AS session_label,
uniqExact(ticker) AS tickers_count,
round(count() / 1000000, 2) AS minute_bars_millions
FROM global_markets.delayed_stocks_minute_aggs
WHERE toDate(toTimeZone(window_start, 'America/New_York')) >= toDate('2026-07-20')
AND toDate(toTimeZone(window_start, 'America/New_York')) <= toDate('2026-07-24')
GROUP BY session, session_label
ORDER BY sessionEl Jul 20, el tape generó 1.79 millones de barras de un minuto correspondientes a 11737 símbolos, y las otras cuatro sesiones del panel repiten ese patrón. Un mercado nacional, una semana y una sola resolución. Una década de barras diarias, fundamentales, composición de índices y registros de flujos de capital de otro mercado tiene la misma magnitud, y recorrerla mediante HTTP consume la ejecución de un agente.
Un lake local cambia dos aspectos a la vez. Las lecturas se convierten en un escaneo de archivos en lugar de depender de una cuota, y una consulta escrita hoy devuelve las mismas filas dentro de seis meses. Eso es lo que necesita un backtest para poder verificarse. Nuestras notas sobre habilidades de datos de mercado para agentes de IA y sobre una API SQL para datos de mercado plantean el mismo argumento para los datos de EE. UU.
Instálelo y fije una sola versión
Python 3.10 o posterior. Fije la versión: entre el 27 de julio y el 2 de agosto de 2026 se publicaron seis versiones, y una instalación sin versión fijada dentro del script de configuración de un agente cambia con el tiempo. El código está en rootSunc/ashare-lake, bajo Apache 2.0.
pip install ashare-lake==0.5.0instala la versión actual a principios de agosto de 2026.asl --versionmuestra la build instalada.asl config init --data-root /path/to/ashare-lakeescribe el archivo TOML de ejemplo incluido, con la ruta raíz de datos ya completada y sin necesidad de clonar el repositorio.--configestablece la ruta de salida;--forcesobrescribe el archivo.asl doctorejecuta sus comprobaciones sin conexión, antes de mover datos.asl servers testcomprueba los hosts upstream de cotizaciones.asl sourcescomprueba cada fuente, con un--vantagedecn,overseasolocal.
Deténgase ahí. El siguiente comando ejecuta el backfill y no debe lanzarse mientras lee.
Qué hace la carga histórica
asl init crea la estructura de directorios y completa el historial. La documentación del proyecto estima que una ejecución completa requiere varias horas de tiempo transcurrido y varios GB de espacio en disco. También necesita una conexión activa con un servidor de cotizaciones upstream de Tongdaxin; eso es lo que verifica asl servers test. asl init --profile quick cubre los tres años más recientes en minutos y conserva todos los valores que cotizaron durante ese periodo, incluidos los que posteriormente dejaron de cotizar. asl run daily es el proceso incremental posterior, asl status --datasets informa la cobertura y la actualización de cada dataset, y asl serve publica un dashboard de solo lectura en 127.0.0.1:8787.
El repositorio no incluye datos. Cada archivo Parquet se genera en tu máquina, con trazabilidad a nivel de fila que registra qué fuente produjo cada fila y cuándo se descargó.
¿Cuáles son los 39 datasets?
Están organizados por capas, desde los datos de referencia hacia afuera: 36 tablas curadas y 3 derivadas.
- Referencia: instrumentos, un calendario bursátil que cubre de 2016 a 2027 y el estado de cotización.
- Datos de mercado: barras diarias, barras de índices, barras de 1 y 5 minutos, ticks de operaciones, barras de commodities, factores de ajuste y eventos de desliste.
- Eventos corporativos: acciones corporativas, un índice de anuncios y el calendario de divulgación de resultados.
- Fundamentales y valuación: partidas de estados financieros, métricas de valuación y consenso de analistas.
- Flujos de capital: flujo de fondos, operaciones de margen, flujos y tenencias northbound, el tablero Dragon-Tiger de divulgaciones de órdenes grandes, operaciones en bloque y tenencias institucionales.
- Estructura e industrias: componentes de sectores, componentes de índices, integrantes de industrias e índices industriales.
- Macroeconomía: indicadores macroeconómicos, amplitud de mercado y un calendario económico.
- Sentimiento y rotación: puntuaciones de sentimiento, ranking de popularidad, barras sectoriales, flujo de fondos por sector, titulares de noticias y un servicio de noticias flash.
- Riesgo y cumplimiento: el calendario de liberación de acciones restringidas y eventos regulatorios.
La ubicación de un dataset indica qué considera importante el autor. Los factores de ajuste y los eventos de desliste están en la capa de datos de mercado, junto a las barras diarias, y no relegados a un apéndice. Para cualquiera que pruebe ideas con datos históricos, esa ubicación representa la mitad del proyecto que tiene mayor valor.
Cómo maneja un lago local el sesgo de supervivencia
El sesgo de supervivencia aparece cuando el universo de un estudio se construye con los nombres que siguen cotizando hoy. Toda empresa que se fusionó, pasó a ser privada o fue excluida de cotización queda fuera de forma silenciosa. Además, los nombres que desaparecen rara vez son los ganadores.
Nuestro almacén de datos puede dimensionar ese vacío para el mercado estadounidense, con la misma aritmética pero en otro alfabeto. Para cada año, toma todos los símbolos que registraron una barra de un minuto durante la segunda semana de marzo y comprueba cuáles seguían registrando operaciones en las dos últimas semanas de julio de 2026:
El SQL exacto detrás de cada cifra
WITH on_tape_now AS (
SELECT ticker
FROM global_markets.delayed_stocks_minute_aggs
WHERE toDate(toTimeZone(window_start, 'America/New_York')) >= toDate('2026-07-20')
AND toDate(toTimeZone(window_start, 'America/New_York')) <= toDate('2026-07-31')
GROUP BY ticker
),
cohort AS (
SELECT toYear(toTimeZone(window_start, 'America/New_York')) AS cohort_year,
ticker
FROM global_markets.delayed_stocks_minute_aggs
WHERE toYear(toTimeZone(window_start, 'America/New_York')) BETWEEN 2016 AND 2025
AND toMonth(toTimeZone(window_start, 'America/New_York')) = 3
AND toDayOfMonth(toTimeZone(window_start, 'America/New_York')) BETWEEN 10 AND 14
GROUP BY cohort_year, ticker
)
SELECT c.cohort_year AS year,
count() AS names_on_tape_count,
countIf(n.ticker != '') AS still_trading_count,
count() - countIf(n.ticker != '') AS gone_count,
round(100 * countIf(n.ticker != '') / count(), 1) AS still_trading_pct
FROM cohort AS c
LEFT JOIN on_tape_now AS n ON c.ticker = n.ticker
GROUP BY year
ORDER BY yearDe los 8101 símbolos que cotizaron esa semana en 2016, 50.1% seguían en el tape a finales de julio de 2026 y 4040 ya no. La cohorte de 2025 muestra 86.7%. Si se ejecuta hacia atrás, durante esos 10 años, un screen construido con las cotizaciones actuales, se pierde una proporción cada vez mayor del mercado.
La suposición más cómoda es que todos los nombres ausentes eran penny stocks. Sin embargo, ordenar por niveles la cohorte de marzo de 2021 según su volumen diario promedio en dólares de ese mes muestra otra realidad:
El SQL exacto detrás de cada cifra
WITH on_tape_now AS (
SELECT ticker
FROM global_markets.delayed_stocks_minute_aggs
WHERE toDate(toTimeZone(window_start, 'America/New_York')) >= toDate('2026-07-20')
AND toDate(toTimeZone(window_start, 'America/New_York')) <= toDate('2026-07-31')
GROUP BY ticker
),
march_2021 AS (
SELECT ticker,
sum(toFloat64(close) * toFloat64(volume))
/ uniqExact(toDate(toTimeZone(window_start, 'America/New_York'))) AS avg_daily_dollar_volume
FROM global_markets.delayed_stocks_minute_aggs
WHERE toDate(toTimeZone(window_start, 'America/New_York')) >= toDate('2021-03-01')
AND toDate(toTimeZone(window_start, 'America/New_York')) <= toDate('2021-03-31')
GROUP BY ticker
)
SELECT multiIf(d.avg_daily_dollar_volume >= 1000000000, '$1B or more',
d.avg_daily_dollar_volume >= 100000000, '$100M to $1B',
d.avg_daily_dollar_volume >= 10000000, '$10M to $100M',
d.avg_daily_dollar_volume >= 1000000, '$1M to $10M',
'under $1M') AS liquidity_bucket,
count() AS names_count,
countIf(n.ticker = '') AS gone_count,
round(100 * countIf(n.ticker = '') / count(), 1) AS gone_pct
FROM march_2021 AS d
LEFT JOIN on_tape_now AS n ON d.ticker = n.ticker
GROUP BY liquidity_bucket
ORDER BY min(d.avg_daily_dollar_volume)El nivel under $1M perdió la mayor proporción: 57.5% de 3968 nombres. El nivel con mayor actividad tampoco estuvo exento: 3.4% de los 89 símbolos que negociaban $1B or more al día en marzo de 2021 habían desaparecido a finales de julio de 2026. Las fusiones, las adquisiciones para retirar una empresa de bolsa, las quiebras y las salidas de índices terminan igual en una tabla de precios: las filas dejan de aparecer.
ashare-lake trata este asunto como un problema central. El dataset de instrumentos conserva los símbolos excluidos de cotización, en lugar de filtrar solo los que siguen activos. Una tabla delisting_events registra cómo terminó cada nombre que salió del mercado, y universe="all_a" en la API de Python resuelve un snapshot histórico que los incluye. La documentación del proyecto informa una brecha aproximada de dos veces entre un backtest que solo incluye supervivientes y otro que incorpora exclusiones de cotización durante 2016-2021. Es la imagen inversa de la trampa que describimos en nuestras notas sobre sesgo de anticipación en backtesting: un universo que conoce el futuro de forma silenciosa.
Consultas puntuales en el tiempo
load("financial_statement_items", as_of="2018-04-30") devuelve la versión más reciente de cada partida anunciada en esa fecha o antes, no el dato tal como fue reformulado posteriormente. Las barras incluyen un argumento adjust: hfq para ajustes retrospectivos, qfq normalizado dentro de la ventana de consulta, o precios sin ajustar. Un factor calibrado con cifras que el mercado todavía no había publicado no mide nada. Esa es la primera comprobación que debe hacerse en cualquier pipeline de factor alpha generado por un LLM.
Registrarlo como servidor MCP
El Model Context Protocol es la forma en que un agente incorpora herramientas. asl mcp lo utiliza mediante stdio, y el cliente inicia el proceso:
claude mcp add ashare-lake -- asl mcp --config /abs/path/to/ashare-lake.toml- Cualquier otro cliente MCP usa los mismos dos elementos:
aslcomo comando ymcp --configjunto con una ruta absoluta como argumentos. La ruta debe ser absoluta porque el cliente puede iniciar el proceso desde cualquier directorio.
Se habilitan seis herramientas, organizadas por tipo de consulta y no por conjunto de datos: describe_lake indica qué existe y cómo leerlo; resolve_symbol convierte un nombre en un código, incluidos los nombres deslistados; query_bars consulta barras; query_fundamentals consulta fundamentales con su argumento as_of; query_dataset cubre todo lo demás; y run_sql ejecuta un único SELECT de DuckDB, de solo lectura, entre varios conjuntos de datos. Un indicador --live permite que el servidor responda consultas de símbolos y barras diarias sin ajustar directamente desde la fuente ascendente, sin escribir en el lake.
Límites que conviene conocer primero
- Solo acciones A. No incluye Hong Kong, cotizaciones en EE. UU. ni ningún mercado fuera de China continental.
- Es un proyecto personal. Los issues y pull requests reciben atención según disponibilidad. La documentación indica claramente que no existe garantía de disponibilidad: los sitios de origen cambian y una IP puede quedar bloqueada, lo que detiene la ingesta hasta que alguien aplique una corrección.
- Apache 2.0 cubre el código, no los datos. Cada fuente de origen conserva sus propios términos. El mantenedor no concede ningún derecho para redistribuir o revender los archivos Parquet que genere. Lea los términos de las fuentes antes de cualquier uso comercial.
- Las fuentes consultadas no requieren una cuenta ni un token. Esa es una ventaja, pero también una fuente de fragilidad.
- La compatibilidad con Windows llegó en 0.3.0, y la versión mínima de Python pasó a 3.10 en 0.3.1.
De dónde provienen estos datos del proyecto
La versión 0.5.0, las seis fechas de lanzamiento y la versión mínima de Python provienen del historial de lanzamientos del proyecto en PyPI y del CHANGELOG, consultados el 4 de agosto de 2026. El catálogo de datasets, el comportamiento frente a exclusiones de cotización y consultas point-in-time, los flags de la CLI, la lista de herramientas MCP y la información sobre licencias y soporte provienen de la documentación del repositorio: docs/datasets/catalog.md, docs/reference/cli.md, docs/reference/mcp.md y docs/legal-and-data-sources.md. El software evoluciona más rápido que las publicaciones, así que consulte la documentación correspondiente a la versión que instale. Los dos paneles de survivorship miden símbolos de EE. UU. en nuestro propio warehouse, no cotizaciones chinas, y sirven como ilustración del mecanismo, no como medición del mercado de acciones A.
Preguntas frecuentes
¿Se necesita una API key para crear un lago de datos local de acciones A?
No con esta herramienta. Las fuentes upstream que consulta no requieren registro ni token, y el lago de datos reside en tu equipo. Cada fuente mantiene sus propios términos de uso, que deben revisarse antes de cualquier trabajo comercial.
¿Cuánto tarda la carga histórica de ashare-lake?
La documentación estima que una carga histórica completa requiere varias horas de tiempo de ejecución y varios GB de espacio en disco. También exige mantener durante todo el proceso una conexión operativa con un servidor upstream de cotizaciones. asl init --profile quick cubre los tres años más recientes en minutos y todavía incluye valores que posteriormente fueron excluidos de cotización.
¿Un lago de datos local de acciones A incluye acciones excluidas de cotización?
Este sí. Los símbolos excluidos de cotización permanecen en el dataset de instrumentos. Una tabla delisting_events registra cómo terminó cada caso, y universe="all_a" crea una instantánea histórica que los incluye. Nuestra medición propia del mercado estadounidense anterior muestra la magnitud de lo que queda fuera cuando solo se conserva un universo de supervivientes.
¿Puede un agente de IA consultar ashare-lake directamente?
Sí. asl mcp expone seis herramientas mediante el Model Context Protocol. Una de ellas permite ejecutar consultas SQL de solo lectura. Así, el agente consulta archivos Parquet locales en lugar de hacer scraping. Regístralo con claude mcp add ashare-lake -- asl mcp --config /abs/path/to/ashare-lake.toml.
¿Ashare-lake sustituye a AkShare o Baostock?
No. Se ejecuta por encima de ellas. Esas bibliotecas obtienen datos de fuentes upstream. Este proyecto almacena, versiona y concilia esos datos en archivos Parquet curados, con trazabilidad a nivel de fila y un contrato por dataset.
Cada cifra anterior corresponde a una consulta almacenada y versionada sobre datos de mercado reales. Expande cualquier panel para leer el SQL o ejecuta la misma comprobación de sesgo de supervivencia sobre tu propio universo en la terminal de Strasmore.