关于 canonic
canonic 为数据 Agent 构建带业务定义、关系和约束的数据上下文,帮助其按规范查询仓库。它以只读方式执行确定性 SQL,并在结果中附带定义、规则和可信度信息。
主要功能
- 01将业务指标定义编译为 SQL
- 02强制应用查询约束并检测连接扇出
- 03为结果附带可信度与新鲜度信息
- 04从数据源和文档生成可审阅上下文
- 05通过 CLI 查询、审计和评估
- 06以只读方式连接多种数据库
适用场景
- 01让 Agent 按统一口径查询业务指标
- 02发现指标变化在不同维度上的来源
- 03在 CI 中验证查询结果和断言
- 04为分析工具提供受治理的数据上下文
MCP 相关
canonic 通过按需启动的本地 MCP 服务,将查询、指标分解及上下文工具提供给 MCP 客户端;也支持 HTTP 传输和按客户端配置的 Bearer token。MCP 返回的结果包含已解析定义、触发的约束及可信度信息。
配置
本地服务的配置在各客户端中通用,复制后粘贴到客户端的 MCP 配置文件即可。
工具
本地服务需要在你的电脑上运行后才能读取工具,维护者暂未提供工具列表。
详细介绍
canonic
让 AI Agent 能正确查询数据的上下文层。
将 canonic 指向你的数据库,它就会构建 Agent 准确回答数据问题所需的上下文:定义、关系、业务含义,以及防止自信地给出错误答案的防护规则。随着数据变化,它会让上下文保持最新,而且除了读取数据外,绝不会对你的数据仓库进行任何操作。
📖 完整文档:https://docs.getcanonic.app
问题所在
直接连接到数据仓库的 AI Agent 看到的是表和列,而不是含义。它不知道 revenue 对应 orders.amount,但不包括退款;也不知道“活跃客户”有财务团队认定的特定定义。因此它只能猜测。访问架构让 Agent 能流利表达,却不代表它正确。
从针对 电商示例 的实时运行中截取的实际输出:
$ canonic sql "SELECT SUM(amount) FROM fct_orders"
┏━━━━━━━━━┓
┃ sum ┃
┡━━━━━━━━━┩
│ 4050.50 │
└─────────┘
这个总额包含两笔已退款订单($260),虽然数字格式规范、语气肯定,却高估了 6.4%。
$ canonic --json query --metrics revenue
{
"result": { "rows": [["3790.50"]] },
"compiled": {
"sql": "SELECT SUM(\"orders\".\"amount\") AS \"revenue\" FROM \"fct_orders\" AS \"orders\" WHERE \"orders\".\"status\" <> 'refunded'"
},
"metadata": {
"guardrails_fired": [{ "id": "revenue-excludes-refunds", "kind": "mandatory_filter" }]
}
}
canonic 会将“revenue”解析为其规范定义,无论是否有人提出要求,都会把防护规则编译进 SQL,并返回正确的数字及其推理过程。
canonic 既不是 BI 工具,也不是聊天界面:它是为你已有的工具(BI 仪表板、Agent、笔记本)提供正确且受治理的答案的上下文层。
canonic 的功能
- 强制执行规范定义。 Agent 按名称请求某项指标时,canonic 会将其解析为唯一约定的定义并编译 SQL。
mandatory_filter、required_dimension、restrict_source和min_trust等护栏都是契约的一部分,因此文档中注明的注意事项不会被悄然忽略。契约与护栏 - 聚合方式正确,而不只是 SQL 有效。 半可加度量(MRR 快照)、按请求的粒度重新计算的比率、去重计数、百分位数和累计总计,都有各自的编译策略;可能导致事实表行数膨胀的联接也会被捕获。存在多条有效联接路径时,你可以用
via选择一条,canonic 不会猜测。编译器 - 答案附带可信度信息。 每个结果都会附带一组元数据:解析后的定义、触发的护栏、数据新鲜度、最终与临时行,以及可信度等级(
trusted、provisional、caution)和相应原因。断言可作为 CI 的门禁条件,而经确认错误的结果会降低指标的可信度。可信度与断言 - 为什么发生了变化?
canonic decompose和 MCP 工具decompose_change会分析某项指标在两个时期之间的变化,既给出整体结果,也按成员拆分。所用方法会遵循指标类型,因此比率会拆解为可相加的结构效应和比率效应,而不是无法相加的成员差异。工具参考 - 拒绝作答并询问。 对于含糊或不安全的问题,系统会返回结构化原因(
ambiguous_join_path、guardrail_block等),供 Agent 采取相应操作,绝不会猜测作答。错误代码 - 自动构建上下文。 系统会从实时架构、dbt 清单或 Apache Ossie 模型中生成语义草案,并从 Looker 和 Metabase 的使用情况、Notion 页面及网页文档中学习。每项更改都会生成可供审核的差异(
canonic review、canonic apply),并标记偏差,同时提议移除对已不存在对象的引用。数据摄取 - 为 Agent 提供业务知识。 定义、策略和注意事项以 Markdown 页面形式保存。Agent 可以搜索这些内容,读取包含实时渲染定义的页面,并在答案中获取相关注意事项。知识层
- 内置治理功能。 支持租户范围限定、基于角色的访问控制、列掩码,以及 MCP 服务的 OAuth 2.1 / OIDC,其中包括身份断言,以支持代表用户执行操作的 Agent。多租户与访问控制
- 只读访问你的数据仓库。 支持 Postgres、Redshift、MySQL、Snowflake、Databricks、ClickHouse、SQLite 和 DuckDB(包括 CSV 和 Parquet 文件)。连接器
- 效果可衡量。 本地事件日志可供
canonic audit和canonic status使用;准确性测试工具(canonic assert、canonic eval baseline)则让“可信”变得可验证。监测与评估
工作原理
your sources canonic consumers
──────────── ─────── ─────────
warehouse schema ┐ ingest ┌──────────────────────────┐ CLI (query, sql, review)
dbt / Ossie ├─────────▶ │ semantics/ knowledge/ │ ──▶ MCP server
Looker, Metabase │ propose │ contracts/ (files in git)│ Claude Code, Cursor, Codex,
Notion, web docs ┘ → review └──────────────────────────┘ any MCP client
每个问题都会沿着一条确定的路径处理:解析指标,依据规范定义编译 SQL,应用护栏,只读执行,并附上元数据。回答时不涉及大模型。
Agent 会收到什么
来自 saas-analytics 示例中 canonic --json query --metrics gross_revenue 的真实输出(节选):
{
"result": { "columns": [{ "name": "gross_revenue", "type": "decimal" }], "rows": [["77071.00"]] },
"compiled": {
"sql": "SELECT SUM(\"fct_invoices\".\"amount\") AS \"gross_revenue\" FROM \"fct_invoices\" AS \"fct_invoices\" WHERE \"fct_invoices\".\"status\" <> 'refunded' AND \"fct_invoices\".\"is_trial\" = FALSE",
"dialect": "duckdb"
},
"metadata": {
"resolved": { "metrics": { "gross_revenue": "fct_invoices.total_amount" } },
"guardrails_fired": [
{ "id": "revenue-excludes-refunds", "kind": "mandatory_filter", "severity": "error" },
{ "id": "revenue-excludes-trials", "kind": "mandatory_filter", "severity": "error" }
],
"freshness": [{ "source": "fct_invoices", "stale": false }],
"trust_score": {
"tier": "provisional",
"reasons": ["gross_revenue: assertion unverified (pass/fail not yet persisted)"]
}
}
}
Agent 可以看到答案采用了哪个定义、哪些规则影响了 SQL,以及为什么该数值仅为 provisional,因此可以在答案中说明相关注意事项,而不是将其作为定论呈现。
三层
canonic 的上下文存在于三个已提交的界面中:git 仓库里的纯文本文件,像代码一样经过审查。
| 层 | 文件 | 回答的问题 | 维护方 |
|---|---|---|---|
| 语义 | semantics/**/*.yaml | “如何安全地查询?” | 自动维护 |
| 知识 | knowledge/**/*.md | “这对业务意味着什么?” | 自动维护 |
| 契约 | contracts/**/*.yaml | “哪个定义是规范的,答案必须遵守什么?” | 人工维护 |
影响 SQL 运行方式 → 语义。人工需要它来信任答案 → 知识。决定哪个定义具有权威性 → 契约。参见概念:三层。
快速开始
canonic 需要 Python 3.13 或更高版本(uv 会为你获取)。
uvx canonic --version # try it without installing
uv tool install canonic # persistent, global command
pip install canonic # without uv
docker pull ghcr.io/mischuh/canonic:latest # CI, headless, air-gapped
最快的方式是使用本地连接器,无需服务或网络。指定 SQLite .db 或 DuckDB .duckdb/CSV/Parquet 文件:
canonic setup

向导会为项目命名、连接数据源、按需配置 LLM、根据实时架构起草语义,然后运行实际查询,并显示答案及其新鲜度和定义。服务器型数据库或 LLM 提供商需要凭据;请在运行 canonic setup 之前将凭据设为环境变量(或使用 file: 引用),因为 canonic 绝不会将密钥直接存储在 canonic.yaml 中。
现在,你的仓库中已有一个可用的上下文层:
canonic overview # what's askable
canonic query --metrics revenue --dimensions order_date # ask it
canonic review && canonic status # review what it drafted
隔离网络环境安装和离线 wheel 包:参见安装。
连接你的 Agent(MCP)
canonic 通过本地、按需启动的 MCP 服务提供工具,并已通过 Claude Code、Cursor 和 Codex 验证:
canonic mcp start
{
"mcpServers": {
"canonic": {
"command": "uvx",
"args": ["canonic", "mcp", "start", "--project", "/path/to/canonic/examples/rental", "--suggestions"]
}
}
}
通过 GUI 启动的客户端(Claude Desktop、Cursor)不会加载你的 shell 配置文件,因此请通过配置的 env 字段传递连接凭据,而不要使用 export。
有关远程部署和企业部署(--transport http、每个客户端单独的 bearer token),请参见连接你的 Agent和工具参考。若要查看如何针对真实身份应用数据屏蔽、run_sql 控制和租户范围限制,可使用scripts/local_idp在本地 Keycloak 后运行 marketplace 示例:操作指南。
示例项目
examples/ 提供七个开箱即用的项目,每个项目都附有一份指南:
| 示例 | 后端 | 展示内容 |
|---|---|---|
| jaffle-shop | DuckDB | 将 MetricFlow 模型作为依据的 dbt 清单 |
| ecommerce | Postgres | 完整流程:防护规则、最终性、Notion 和 dbt 依据、可观测性 |
| rental | SQLite | 跨事实扇出和 NULL 处理防护规则,无需设置 |
| saas-analytics | DuckDB | 所有指标绑定类型、所有防护规则类型、最终性、断言 |
| dutch-railway | DuckDB | 地理维度链和比率指标 |
| marketplace | SQLite | 租户范围限定、基于角色的访问和列屏蔽 |
| ossie-retail | SQLite | 从 Apache Ossie 模型引导的上下文 |
| coffeehouse | DuckDB | 用 dbt MetricFlow 和 canonic 回答相同问题:计数去重、平均值、防护规则 |
你可以信赖的特性
- 只读。 canonic 永远不会修改你的数据仓库。
- 仅提议,拒绝并询问。 每项变更都是可审查的差异;对于含糊或不安全的回答,会提供结构化原因,而非猜测。
- 回答流程中不使用大模型。 查询以确定性方式编译。大模型是可选的,仅在设置期间用于起草上下文,支持四家提供方(Anthropic、OpenAI、任何兼容 OpenAI 的端点、GitHub Copilot),请参阅配置大模型。
- 本地优先,支持气隙环境。 完全在你的计算机上运行;无需将任何内容发送到网络之外。
面向开发者
uv sync # install with dev dependencies
uv run pytest tests/ -x # tests, including the golden suite
uv run ruff check . && uv run ruff format --check .
uv run mypy canonic/
- 目录布局。
canonic/是软件包(编译器、连接器、契约、数据摄取、知识、MCP 服务、信任、检测),tests/与其结构对应,examples/存放示例项目。 - 扩展点。 连接器按能力(
introspect_schema、run_read_only_sql、extract_definitions、extract_evidence)向ConnectorFactory注册;短期凭据通过CredentialProviderRegistry接入。 - 稳定契约。 服务契约有版本管理(
contract_infoMCP 工具、CONTRACT_CHANGELOG.md),而tests/golden/则锁定示例的编译后 SQL 和执行结果。 - 贡献。 Conventional Commits、黄金测试套件工作流和契约变更流程详见 CONTRIBUTING.md。
文档
- 快速入门:几分钟内获得第一个回答。
- 概念:三层架构、编译器、契约、多租户。
- CLI 参考:逐项介绍每条命令及其标志。
- MCP / Agent 集成:将 canonic 接入 Claude Code、Cursor、Codex 或任何 MCP 客户端。
- 指南:七个示例项目和数据仓库使用演练。
- 参考:错误代码和完整的
canonic.yaml配置架构。
许可证
Business Source License 1.1。可免费用于非商业、个人、评估、教育和开发用途。商业用途需要单独的许可证。授权版本将于 2030 年 7 月 17 日转换为 Apache 2.0。
评论
一个开放协议,规定了 AI 应用如何以统一方式连接外部工具与数据源。客户端负责与模型对话,MCP 服务负责提供工具、资源和提示模板,两者通过标准消息通信,同一个服务可以被不同客户端复用。