关于 tableski
tableski 是面向 AI Agent 的 MCP 服务,可将 Excel、CSV、Parquet 和 JSON 文件注册为可用 SQL 查询的表。它支持跨格式分析,并可将查询结果导出为 CSV 或 XLSX。
主要功能
- 01跨文件格式执行 SQL 查询
- 02读取 Excel、CSV、Parquet 和 JSON
- 03提供表结构与列统计工具
- 04导出 CSV 和 XLSX 查询结果
- 05为不可信 SQL 启用只读模式
适用场景
- 01联接工作簿工作表与其他文件的数据
- 02让 Agent 汇总或筛选数据集
- 03将查询结果导出供电子表格使用
MCP 相关
通过无状态 Streamable HTTP 向 MCP 客户端提供表列表、SQL 查询、结构、统计和导出工具。
配置
远程服务无需本地安装。选择你使用的客户端,复制配置或使用一键安装。
https://mcp.tableski.io/claude mcp add --transport http yarenty-tableski https://mcp.tableski.io/{"mcpServers":{"yarenty-tableski":{"type":"http","url":"https://mcp.tableski.io/"}}}在 Cursor 中打开{"servers":{"yarenty-tableski":{"type":"http","url":"https://mcp.tableski.io/"}}}在 VS Code 中打开{"mcpServers":{"yarenty-tableski":{"type":"http","url":"https://mcp.tableski.io/"}}}{"mcpServers":{"yarenty-tableski":{"serverUrl":"https://mcp.tableski.io/"}}}命令在终端中运行;JSON 粘贴到对应客户端的 MCP 配置后重启。需要授权的服务会在首次连接时提示登录。
工具
详细介绍
tableski
每个电子表格都是一张表 — tableski 以 SQL 的形式将它们提供给你的 Agent。
Excel、CSV、Parquet、JSON —— 一个企鹅家族的二进制程序,可将你的数据文件转换为 可查询的表,并通过 Model Context Protocol提供给 AI Agent。
- 单一二进制程序,无状态 Streamable HTTP —— 基于 emperor-mcp框架(符合 Emperor Profile P1 标准:分帧输出、转发凭据、无会话亲和性)。
- SQL 引擎由 Apache DataFusion提供支持。
- 在 kowalski栖息地孵化 ——
-ski是 家族名。
安装
预构建的二进制文件(macOS arm64/x86_64、Linux x86_64、Windows x86_64)可在 GitHub releases中获取:
curl -fsSL https://raw.githubusercontent.com/yarenty/tableski/main/install.sh | sh
Windows:从发布页面下载 .zip。也可以通过 cargo 安装:
cargo install tableski
连接 MCP 客户端
tableski 是一个基于无状态 Streamable HTTP 的标准 MCP 服务 —— 将任意客户端指向服务 URL 即可:
# Claude Code
claude mcp add --transport http tableski http://127.0.0.1:8080/
// Claude Desktop (claude_desktop_config.json) via mcp-remote
{ "mcpServers": { "tableski": { "command": "npx",
"args": ["mcp-remote", "http://127.0.0.1:8080/"] } } }
也可以使用原始 HTTP:向 / 发送 JSON-RPC POST 请求,并设置 Accept: application/json(见下文)。
运行
# One model for every format: --file registers by extension, table name = file stem
# (.csv .parquet .json/.ndjson/.jsonl; workbooks .xlsx/.xls/.ods = one table per sheet)
cargo run -- --file fixtures/sample.xlsx --file fixtures/sample.parquet \
--file fixtures/sample.ndjson --export-dir ./exports
# (--csv/--xlsx flags still work; name collisions get _2/_3 suffixes)
向它提问(工具:list_tables、query_sql、get_schema、column_statistics、
export_result —— 所有输出都按 Emperor Profile E8 的要求以数据帧形式呈现)。SQL 联接可跨格式进行:将 xlsx 工作表与 Parquet 文件或 NDJSON 日志联接。export_result 会将查询结果写入 .csv/.xlsx —— 仅限 --export-dir 沙盒目录内(使用相对名称,不能包含 ..;除非操作员传入该标志,否则此工具会被禁用):
curl -s -X POST http://127.0.0.1:8080/ \
-H 'Content-Type: application/json' -H 'Accept: application/json' \
-d '{"jsonrpc":"2.0","id":1,"method":"tools/call","params":{"name":"query_sql",
"arguments":{"sql":"SELECT p.name, SUM(o.amount) AS total FROM people p JOIN orders o ON p.name = o.name GROUP BY p.name ORDER BY total DESC"}}}'
# => ada 150.5, linus 99.99 — a SQL join across two sheets of one workbook
工作表名称会转换为 slug 格式的表名(People → people,2024 Orders →
t_2024_orders);如果首行看起来像标题,则会将其作为列名
(可通过 --headers auto|first-row|none 覆盖)。列类型会自动推断:整数、
浮点数、布尔值、日期(作为时间戳)和文本。
真实世界的工作簿往往杂乱无章 —— tableski 能处理各种问题:两种 Excel 日期系统
(1900 和 1904)、公式单元格(读取缓存值;#DIV/0! 之类的错误会变为 NULL)、合并单元格(左上角保留值,其余单元格为 NULL)、显示格式(始终使用原始值)、行长度不齐、仅用于格式设置的填充内容(会被裁剪)、Unicode 工作表名称,以及 --max-rows
上限(达到上限时会明确报错,而不是静默截断)。棘手工作簿语料库位于
fixtures/corpus/——每种情况都有对应的样本和测试。
新手入门?五分钟演示会将一个双工作表工作簿上传到 tableski.io 或本地 tableski,提出第一个问题,并展示如何用日常语言通过 kowalski、Claude 或 Cursor 提问。一次性尝试完整的本地流程:./scripts/demo.sh(电子表格 → 问题 → SQL 答案 →
导出的工作簿)。demo.tape 可通过 vhs将演示渲染为 GIF。
使用 kowalski,可以用日常语言提出问题,并以工作簿的形式获得答案。它的 Spreadsheet analyst 会通过 tableski 分析表格,模型会针对每个问题编写一条 SQL 查询,所有数字都来自查询引擎:

状态:CSV、Excel(xlsx/xls/ods,已针对真实世界的工作簿进行强化)、Parquet 和 NDJSON 目前均可提供服务;结果可导出为 csv/xlsx;每次发布都会提供二进制文件。即将推出。
为不可信客户端提供服务
默认情况下,tableski 会运行 DataFusion 接受的任何 SQL,这适合本地单用户设置。如果服务可被你无法控制的 Agent 或用户访问,请添加 --untrusted-sql:
tableski --file sales.xlsx --untrusted-sql
此后只运行只读查询:SELECT、WITH、VALUES、EXPLAIN;每个请求只能包含一条语句,且只能查询已注册的表。CREATE、INSERT、UPDATE、DELETE、DROP、COPY、SET、CREATE EXTERNAL TABLE、表函数(read_csv(...)、range(...))以及对未注册表或文件路径的引用,都会在解析后的语句上被拒绝,不会执行任何操作,并返回说明原因的错误。DataFusion 自身的 DDL/DML/语句开关也会关闭,作为第二道防线。
限制
单个查询不能拖垮机器。默认值中,0 表示不限:
| 标志 | 默认值 | 限制内容 |
|---|---|---|
--max-memory-mb | 2048 | 会话的 DataFusion 内存池;超出上限的查询会失败并返回 Resources exhausted,而不是让进程持续占用内存。设置上限后会关闭磁盘溢写,因此查询会快速失败,而不是占满磁盘。 |
--query-timeout-secs | 60 | 每个查询的墙钟时间,包含规划时间。查询在专用线程池中运行,并会在 DataFusion 的下一个让出点被取消;与此同时,服务会继续响应。 |
--max-result-rows | 10000 | query_sql 结果最多返回的行数。超出时会截断结果,并以 -- result truncated ... 行结尾;export_result 会拒绝导出,而不是写入不完整文件。 |
--max-result-mb | 16 | 同上,限制 Arrow 内存大小。 |
笛卡尔积(CROSS JOIN,或没有 = 条件的连接)是唯一一种运行后无法通过超时停止的查询形式,因此 --untrusted-sql 会在执行前根据查询计划拒绝这类查询。
超时涵盖规划和执行,因此仅优化就耗时很长的语句也会被中止。内存池无法计量的内容包括标量函数(repeat、lpad 等)分配的内存。为不可信客户端运行服务时,请使用容器内存限制,tableski.io 的部署就是如此。整套测试由 tests/hostile_sql.rs 覆盖(DDL/DML、文件系统访问、标识符技巧、资源耗尽、解析器压力测试、导出路径遍历);发现新的恶意形式时,请在其中添加一行测试。
作为库使用
引擎本身是独立的 crate,即 tableski-core:将文件注册到 DataFusion SessionContext,然后通过 call_tool 运行工具,或通过任意 emperor-mcp 传输方式提供 AppState。无需 HTTP,也无需命令行。
[dependencies]
tableski-core = "0.1"
let sources: Vec<Box<dyn TableSource>> = vec![Box::new(FileSource::new().path("orders.xlsx"))];
let tables = register_sources(&ctx, &sources, &IngestOptions::default()).await?;
let state = AppState::new(Arc::new(ctx), tables);
let grid = call_tool(&state, "query_sql", json!({ "sql": "SELECT count(*) FROM orders" })).await?;
表由 TableSource 实现提供。FileSource 用于磁盘上的文件;对于流式或会刷新的数据源(如价格信息流、会被重写的文件),实现相同的 trait,并将其状态保存在自身的 DataFusion TableProvider 后面,这样每次查询都会看到规划时存在的行。tableski_core::source 的模块文档说明了相关约定;crates/tableski-core/tests/table_source.rs 是一个可追加数据源的完整示例。
对于有多个租户的服务,Quota 和 UsageMeter(每日查询次数、存储字节数、文件数、每个文件的行数)可通过 with_quota 接入相同的状态;计量器在内存中运行,使用情况的持久化由宿主负责。
对比
如实定位——不同工具解决不同问题:
| tableski | 基于 openpyxl 的 Excel MCP 服务 | Google Sheets MCP | |
|---|---|---|---|
| 基于数据提问 | SQL 引擎(DataFusion):跨工作表 和 文件格式进行联接、聚合和筛选 | 读取单元格/区域;分析逻辑交由模型在上下文中处理 | 针对实时 Sheets 进行逐次 API 调用 |
| 格式 | xlsx/xls/ods + CSV + Parquet + NDJSON,统一表模型 | xlsx(通常支持读 和写,包括格式设置/图表——tableski 不会编辑工作簿) | 仅支持 Google Sheets |
| 部署 | 单个静态二进制文件、无状态的 Streamable HTTP(Emperor Profile P1) | Python 运行时 + 依赖项 | 托管 API + OAuth |
| 输出安全性 | 每项工具结果都以数据形式封装(缓解提示词注入) | 通常为原始内容 | 通常为原始内容 |
如果需要 编辑 工作簿(样式、图表、单元格写入),可将 tableski 与面向写入的服务搭配使用;tableski 是分析和导出引擎。
贡献
参见 CONTRIBUTING.md:运行检查、保持文档同步,并为提交签署认证(DCO,git commit -s)。
许可证
可选择以下任一许可证:
- Apache License, Version 2.0(LICENSE-APACHE 或 https://www.apache.org/licenses/LICENSE-2.0)
- MIT license(LICENSE-MIT 或 https://opensource.org/licenses/MIT)
由你自行选择。
除非你明确另行声明,否则你有意提交并纳入 tableski 的任何贡献,均按上述双重许可授权,不附加任何条款或条件。
评论
一个开放协议,规定了 AI 应用如何以统一方式连接外部工具与数据源。客户端负责与模型对话,MCP 服务负责提供工具、资源和提示模板,两者通过标准消息通信,同一个服务可以被不同客户端复用。