mcpField
D
Debmatic Mcp

Debmatic Mcp

本地服务
github.com/claymore666其他92 天前更新

关于 Debmatic Mcp

Debmatic Mcp 将 HomeMatic CCU 的设备、房间、程序和系统变量接入 MCP 客户端,面向需要通过 AI 管理本地智能家居的用户。它直接使用 CCU 的 JSON-RPC API,无需云服务或附加组件。

主要功能

  1. 01发现设备并解析类型
  2. 02读取房间、程序和系统变量
  3. 03查询与控制设备状态
  4. 04管理 CCU 会话并转换数据值

适用场景

  1. 01查询房间温度或窗户状态
  2. 02调整供暖设定温度
  3. 03查找低电量设备
  4. 04规范设备与通道名称

MCP 相关

作为 MCP 服务向客户端提供 HomeMatic 设备、房间、程序和系统变量相关工具。支持 stdio 子进程连接,也可通过独立 HTTP 服务供客户端访问。

配置

本地服务的配置在各客户端中通用,复制后粘贴到客户端的 MCP 配置文件即可。

mcp.json · 通用配置
{
"mcpServers": {
"debmatic": {
"command": "npx",
"args": [
"-y",
"debmatic-mcp"
],
"env": {
"CCU_HOST": "<CCU_HOST>",
"CCU_PASSWORD": "<CCU_PASSWORD>",
"CCU_USER": "<CCU_USER>",
"CCU_HTTPS": "<CCU_HTTPS>",
"CCU_PORT": "<CCU_PORT>",
"CACHE_DIR": "<CACHE_DIR>",
"MCP_ALLOWED_ORIGINS": "<MCP_ALLOWED_ORIGINS>",
"MCP_ALLOWED_HOSTS": "<MCP_ALLOWED_HOSTS>"
}
}
}
}
启动命令npx -y debmatic-mcp
需要配置的环境变量
CCU_HOSTHostname or IP of your HomeMatic CCU (debmatic, CCU3, or RaspberryMatic)
CCU_PASSWORD密钥CCU admin password (same as the WebUI login)
CCU_USERCCU username
CCU_HTTPSConnect to the CCU via HTTPS (self-signed certificates supported)
CCU_PORTCCU API port (80 for HTTP, 443 for HTTPS)
CACHE_DIRDirectory for the device type cache and session persistence
MCP_ALLOWED_ORIGINSComma-separated allowlist of browser origins. Unset = no cross-origin browser access (default-deny). An allowlisted origin is reflected exactly in Access-Control-Allow-Origin (never '*'); the list also drives DNS-rebinding origin checks
MCP_ALLOWED_HOSTSExtra Host header values accepted by DNS-rebinding protection (comma-separated host:port); add your hostname when behind a proxy or container DNS name

本地服务需要在你的电脑上安装运行环境(如 Node.js 18+)。各客户端的配置文件位置不同,请参考客户端文档。

安装包
npmdebmatic-mcp1.3.0

工具

18

收录的工具列表 · 更新于 3 周前

参数类型必填说明
roomstring否按房间名称筛选(完全匹配)
functionstring否按功能组名称筛选(完全匹配)
typestring否按设备类型筛选(完全匹配,例如 'HmIP-eTRV-2')
namestring否按设备/通道名称筛选(子字符串,不区分大小写)

详细介绍

OpenSSF Best Practices OpenSSF Scorecard

ccu-mcp

通过 Claude、Cursor 或任何 MCP 客户端与你的 HomeMatic 智能家居对话。

ccu-mcp MCP 服务

ccu-mcp 连接到 CCU 内置的 JSON-RPC API,并将你的设备、房间、程序和系统变量作为 MCP 工具提供。无需附加组件,无需 XML-API,也无需云服务——只需直接连接到本地网络中的 CCU。

兼容任何 HomeMatic CCU:debmatic(运行于 Debian 上的 HomeMatic)、CCU3 或 OpenCCU(原 RaspberryMatic)——只要支持标准的 /api/homematic.cgi 端点即可。

它能做什么?

你可以向 AI 助手提出这样的问题:

  • “浴室的温度是多少?”
  • “有窗户开着吗?”
  • “把客厅暖气设为 21 度”
  • “显示所有电量低的设备”
  • “燃气表读数是多少?”
  • “哪些设备电量低,或者已经很久没有被发现?”
  • “找出所有名称与设备名称不匹配的通道”
  • “将所有设备重命名为统一的命名规范,并标注楼层(UG/OG/EG)”
  • “窗户传感器在哪个房间?”

MCP 服务负责设备发现、类型解析、会话管理和值转换——AI 只需调用工具。

前提条件

  • 网络中可访问且正在运行的 HomeMatic CCU(debmatic、CCU3 或 OpenCCU——原 RaspberryMatic)
  • CCU 管理员用户名和密码(与登录 WebUI 时使用的凭据相同)
  • Node.js 24+(用于从源代码运行或以 stdio 模式运行)或 Docker

快速开始

export CCU_HOST=your-ccu-hostname-or-ip
export CCU_PASSWORD=your-ccu-admin-password
npx ccu-mcp --stdio

如果它在 stderr 中输出 server_ready,就表示运行正常。按 Ctrl+C 停止。现在在你的 MCP 客户端中进行设置——请参见下文。

如果旁边出现 cache_save_failed … mkdir '/data',在这里可以忽略,但在实际使用中建议修复:CACHE_DIR 默认值为 /data(Docker 布局),因此在容器外部运行时,设备类型缓存和 CCU 会话不会在运行之间持久保存。将它指向一个可写位置: export CACHE_DIR="$HOME/.cache/ccu-mcp"(或在 .env / env 配置块中设置相同的键)。

希望获得引导式设置?npx ccu-mcp init 会探测你的 CCU、固定其 TLS 证书、测试登录、写入一个可直接使用的 .env 文件,并输出对应的 MCP 客户端配置——请参见命令行标志。

安装

有两种运行方式:stdio(服务作为 MCP 客户端的子进程运行)或 HTTP(服务在 Docker 中独立运行,客户端通过网络连接)。请选择一种。

选项 A:stdio(直接运行,最简单)

这是最简单的设置方式。你的 MCP 客户端(Claude Code、Cursor 等)会将服务作为子进程启动——无需 Docker、无需网络配置,也无需身份验证令牌。

对于 Claude Code,请在项目目录(或你会使用 Claude Code 的任何目录)中创建一个 .mcp.json 文件:

{
  "mcpServers": {
    "ccu-mcp": {
      "command": "npx",
      "args": ["ccu-mcp", "--stdio"],
      "env": {
        "CCU_HOST": "your-ccu-hostname-or-ip",
        "CCU_PASSWORD": "your-ccu-admin-password"
      }
    }
  }
}

将 your-ccu-hostname-or-ip 替换为你的 CCU 主机名(例如 homematic-ccu3)或 IP(例如 192.168.1.50),并将 your-ccu-admin-password 替换为你登录 CCU WebUI 时使用的密码。

重启 Claude Code。运行 /mcp 检查连接状态。你应该会在列表中看到 ccu-mcp。

或者,使用 Claude Code CLI:

claude mcp add ccu-mcp -- npx ccu-mcp --stdio
选项 B:Docker(独立 HTTP 服务)

如果你希望服务独立运行,例如运行在家用服务器上、供多个客户端访问,或者 MCP 客户端支持 HTTP 远程连接,请使用此选项。

1. 启动容器。 镜像已发布到 GHCR,支持 linux/amd64 和 linux/arm64(因此也可在 CCU 旁的 Raspberry Pi 上运行),在每种 架构上原生构建并经过证明——gh attestation verify oci://ghcr.io/claymore666/ccu-mcp:latest --repo claymore666/ccu-mcp 可证明该镜像来自此仓库的发布工作流。

docker pull ghcr.io/claymore666/ccu-mcp:latest

每次发布也会发布对应的 X.Y.Z 标签——如果你希望自行决定升级时机,可以固定使用该标签,而不是 latest。 如需从源代码构建:

git clone https://github.com/claymore666/ccu-mcp.git && cd ccu-mcp
docker build -t ghcr.io/claymore666/ccu-mcp .

然后运行:

docker run -d \
  --name ccu-mcp \
  -e CCU_HOST=your-ccu-hostname-or-ip \
  -e CCU_PASSWORD=your-ccu-admin-password \
  -e MCP_ALLOWED_HOSTS=your-server-ip:3000 \
  -v ccu-data:/data \
  -p 3000:3000 \
  ghcr.io/claymore666/ccu-mcp:latest

远程客户端必须设置 MCP_ALLOWED_HOSTS。 服务的 DNS 重绑定防护会拒绝任何 Host 标头不在允许列表中的请求——默认情况下,仅允许 MCP 端口上的 localhost/127.0.0.1/[::1]。请将客户端用于访问服务的所有名称/IP 添加到列表中(以逗号分隔,格式为 host:port)。如果未设置,本地健康检查可以正常运行, 但所有远程 MCP 请求都会收到 403 Invalid Host header。

2. 获取身份验证令牌。 服务首次启动时会生成一个随机的 bearer 令牌,并将其保存在容器的数据卷中。你需要使用此令牌对 MCP 客户端进行身份验证。使用以下命令获取:

docker exec ccu-mcp grep MCP_AUTH_TOKEN /data/.env

命令会输出类似 MCP_AUTH_TOKEN=e96suzi1iG0H-GPif6K2... 的内容。= 后面的部分就是你的令牌。

3. 配置 MCP 客户端。 如果客户端使用 .mcp.json,请添加 HTTP 服务:

{
  "mcpServers": {
    "ccu-mcp": {
      "url": "http://your-server-ip:3000",
      "headers": {
        "Authorization": "Bearer PASTE-YOUR-TOKEN-HERE"
      }
    }
  }
}

如需自动注入令牌(需要 jq):

TOKEN=$(docker exec ccu-mcp grep MCP_AUTH_TOKEN /data/.env | cut -d= -f2)
jq --arg t "$TOKEN" '.mcpServers["ccu-mcp"].headers.Authorization = "Bearer " + $t' .mcp.json > .mcp.json.tmp && mv .mcp.json.tmp .mcp.json

此操作只会更新 ccu-mcp 条目,不会更改 .mcp.json 中的其他服务。

4. 检查服务是否正常运行:

curl http://localhost:3000/health
基于浏览器的客户端(CORS)

默认情况下,HTTP 服务不会发送任何 CORS 标头,因此随机网页无法控制本地实例。如需让 MCP Inspector 等基于浏览器的 MCP 客户端直接连接,请将 MCP_ALLOWED_ORIGINS 设置为可信来源的逗号分隔允许列表(例如 https://app.example,http://localhost:6274)。对于 Origin 在列表中的请求,服务会将该来源的原值写入 Access-Control-Allow-Origin,绝不会使用通配符 *,因为那会让任何网站都能控制管理真实 CCU 硬件的本地实例。来自其他来源的请求不会获得 CORS 标头(浏览器会阻止该请求),并且会被服务端的 DNS 重绑定防护拒绝。无论如何都会强制执行身份验证:每个 MCP 请求都需要 bearer 令牌。

默认情况下,HTTP 传输也会启用 DNS 重绑定防护:它会拒绝 Host 标头不是配置端口上的 localhost/127.0.0.1/[::1] 的请求。如果你通过其他主机名或 IP 访问服务(反向代理、容器 DNS 名称、服务所在的局域网地址),请将这些主机添加到 MCP_ALLOWED_HOSTS,否则合法请求会收到 403。

TLS。 bearer 令牌会随请求传输,因此除回环地址以外的连接都应加密。你有两种选择:在前置反向代理(Caddy/nginx)处终止 TLS,并将服务绑定到回环地址(MCP_HOST=127.0.0.1);或者设置 MCP_TLS_CERT 和 MCP_TLS_KEY 为 PEM 证书/密钥对,由服务自行提供 HTTPS。仍然完全支持普通 HTTP,并且它依旧是零配置默认选项;但如果服务通过非回环地址绑定并以未加密的 HTTP 传输令牌,启动时会记录警告。设置 MCP_ALLOW_PLAINTEXT=true 即表示确认知悉这一点,并可关闭该警告。

令牌轮换与过期。 默认情况下,bearer 令牌永不过期。你可以组合使用两项可选控制措施,在不让客户端断开连接的情况下轮换令牌:

  • 自动生成的令牌 — 设置 MCP_AUTH_TOKEN_TTL_DAYS(允许小数天)为生成的令牌指定有效期。服务会在令牌即将过期前在运行时自动轮换(无需重启;如果服务停机期间令牌已过期,也会在启动时轮换),并将新令牌打印到 stderr,同时让刚被替换的令牌在 MCP_AUTH_TOKEN_GRACE_HOURS 指定的时长内(默认为 24 小时)仍可通过验证,以便正在进行请求的客户端平稳切换。若要提前轮换,请删除 $CACHE_DIR/.env(或只删除其中的 MCP_AUTH_TOKEN 行)并重启。
  • 显式设置的令牌 — 如果你自行设置 MCP_AUTH_TOKEN,令牌有效期由你负责(TTL 不适用)。若要轮换,请将新令牌写入 MCP_AUTH_TOKEN,将旧令牌移至 MCP_AUTH_TOKEN_PREVIOUS,然后重启;重叠期间两个令牌都可使用。等所有客户端都使用新令牌后,删除 MCP_AUTH_TOKEN_PREVIOUS 并重启。对所有当前有效的令牌,比较过程始终采用时序安全方式。

暴力破解防护(fail2ban)。 自动生成的令牌具有 256 位随机性,因此无法通过猜测破解。如果你自行设置 MCP_AUTH_TOKEN,请确保令牌足够长且随机(例如 openssl rand -base64 32)——短或容易猜测的令牌才需要担心暴力破解。服务不会在进程内对失败的登录尝试进行速率限制或锁定;这项工作应交给防火墙级别的工具,例如 fail2ban,由它在请求到达服务之前封禁来源 IP。为方便实现这一点,每个被拒绝的请求都会向 stderr 输出一行结构化日志:

{"ts":"2026-06-18T17:28:00.370Z","level":"warn","msg":"auth_failed","client":"203.0.113.7","hadToken":true}

fail2ban/ 中附带了可直接使用的 fail2ban 配置:将 filter.d/ccu-mcp.conf 复制到 /etc/fail2ban/filter.d/,并将 jail.d/ccu-mcp.local 中的 jail 复制到 /etc/fail2ban/jail.d/(默认设置为 10 分钟内失败 5 次 → 封禁 1 小时)。服务将日志写入 stderr,因此请将 fail2ban 指向你收集日志的位置——作为 unit 运行时指向 journal(backend = systemd),或在重定向 stderr/使用 docker logs 时指向文件;jail 文件中对两种方式都有说明。需要设置 LOG_LEVEL=warn 或更低级别(默认为 info,可以使用;error 会屏蔽该日志行)。如果服务位于反向代理之后,记录的 IP 将是代理的 IP,因此请改为对代理的访问日志运行 fail2ban。

CORS 支持最初由 @marcinn2 在其分支 marcinn2/debmatic-mcp 中实现——感谢!

HTTPS

如果你的 CCU 使用 HTTPS(自签名证书也可以),请添加以下环境变量:

CCU_HTTPS=true
CCU_PORT=443

服务会自动接受自签名证书——由于 CCU 出厂时附带自签名证书,因此默认关闭证书验证(未验证连接运行时,服务会记录警告)。若要实际验证连接并消除 MITM 风险,有以下三种选择:

  • 固定证书指纹(适用于自签名设备证书,且最简单):将证书的 SHA-256 值(十六进制,可带或不带冒号)设置为 CCU_TLS_FINGERPRINT。除非 CCU 提供的证书与该值完全一致,否则连接会被拒绝。使用以下命令读取:
    echo | openssl s_client -connect "$CCU_HOST:443" 2>/dev/null | openssl x509 -noout -fingerprint -sha256
    
  • 信任 CA/自签名 PEM:将 CCU_CA_CERT 指向证书文件,以进行标准链验证。
  • 系统信任存储:如果你的 CCU 使用公开受信任的证书,请设置 CCU_TLS_VERIFY=true。

CCU_TLS_FINGERPRINT 的优先级高于 CCU_CA_CERT,而 CCU_CA_CERT 的优先级高于 CCU_TLS_VERIFY。

ccu-mcp init 会为你完成证书固定:它会显示 CCU 提供的证书,并在你确认后将指纹写入 env 文件;ccu-mcp doctor 会在之后重新检查固定的指纹(如果证书合法轮换,还会提供更新选项)。

配置

所有配置都通过环境变量完成:

变量默认值描述
CCU_HOST必填CCU 的主机名或 IP
CCU_PASSWORD必填CCU 管理员密码。必须设置;如果设备没有密码(全新安装的 OpenCCU),可以为空
CCU_USERAdminCCU 用户名
CCU_PORT80API 端口(使用 HTTPS 时为 443)
CCU_HTTPSfalse通过 HTTPS 连接(支持自签名证书)
CCU_TLS_VERIFYfalse根据系统信任存储验证 CCU 的 TLS 证书(适用于受公共机构信任的证书)
CCU_TLS_FINGERPRINT未设置通过 SHA-256 指纹(十六进制,可带冒号)固定 CCU 的自签名叶证书。优先于其他 TLS 选项
CCU_CA_CERT未设置用于验证证书链的 CCU CA/自签名 PEM 文件路径
CCU_TIMEOUT10000CCU 请求超时时间,单位为毫秒
CCU_SCRIPT_TIMEOUT30000HM Script 执行超时时间,单位为毫秒
LOG_LEVELinfoerror、warn、info 或 debug
CACHE_DIR/data设备类型缓存和会话的存储位置
CACHE_TTL86400缓存有效期,单位为秒(24 小时)
MCP_TRANSPORThttphttp 或 stdio(--stdio CLI 标志会覆盖此设置)
MCP_PORT3000HTTP 服务端口(仅适用于 HTTP 模式)
MCP_AUTH_TOKEN自动生成HTTP 模式的 Bearer 令牌;首次启动时生成并保存到 $CACHE_DIR/.env
MCP_AUTH_TOKEN_PREVIOUS未设置先前的 Bearer 令牌,在轮换重叠期间与 MCP_AUTH_TOKEN 一同接受;移除此项并重启即可结束重叠期。仅适用于显式令牌配置
MCP_AUTH_TOKEN_TTL_DAYS未设置(永不过期)自动生成的令牌有效期,单位为天(允许小数)。服务端会在令牌到期前不久于运行时自动轮换(新令牌会通过 stderr 通知);设置 MCP_AUTH_TOKEN 时忽略此项
MCP_AUTH_TOKEN_GRACE_HOURS24自动轮换后的重叠期,单位为小时;在此期间,刚被替换的令牌仍可使用
MCP_ALLOWED_ORIGINS未设置以逗号分隔的浏览器来源允许列表。未设置 = 不允许跨源浏览器访问(默认拒绝)。允许列表中的来源会原样反映在 Access-Control-Allow-Origin 中(绝不会是 *);该列表也用于 DNS 重绑定来源检查
MCP_ALLOWED_HOSTSMCP 端口上的 localhost/127.0.0.1/[::1]DNS 重绑定保护允许的额外 Host 值(以逗号分隔的 host:port);请添加客户端用于访问服务端的每个名称/IP(代理、容器 DNS 名称、普通服务端 IP)
MCP_HOST未设置(所有接口)HTTP 监听器的绑定地址;设置为 127.0.0.1 可限制为回环地址(例如部署在 TLS 终止代理后),同时也会关闭明文传输警告
MCP_TLS_CERT / MCP_TLS_KEY未设置PEM 证书/密钥路径。设置两者即可通过原生 HTTPS 提供 MCP;不设置则使用普通 HTTP。只设置其中一项会导致配置错误
MCP_ALLOW_PLAINTEXTfalse设置为 true,表示确认通过普通 HTTP 传输 Bearer 令牌,并关闭非回环地址的明文传输警告
CCU_RATE_LIMIT_BURST20发送到 CCU 的最大突发请求数
CCU_RATE_LIMIT_RATE10CCU 持续请求速率,单位为每秒
RESOURCE_POLL_INTERVAL60MCP 资源变更通知的轮询间隔,单位为秒

如需通过一台服务端驱动多个 CCU,请用命名配置替换这些扁平的 CCU_* 变量——详见下文的多个 CCU 目标。

命令行标志
ccu-mcp init           # interactive setup: probe the CCU, pin its TLS cert,
                       #   test the login, write an env file (default ./.env)
ccu-mcp doctor         # validate an env file end-to-end: reachability,
                       #   certificate pin, login, privilege level
ccu-mcp secret [prof]  # store ONE CCU password into an env file via a local
                       #   hidden prompt — name the target when the file
                       #   defines profiles, omit it for a single CCU (used by
                       #   the LLM-guided setup below; also the rotation path)
ccu-mcp --stdio        # serve over stdin/stdout (overrides MCP_TRANSPORT)
ccu-mcp --http         # serve over HTTP (default)
ccu-mcp --env <path>   # load configuration from a dotenv file (already-set
                       #   environment variables win); also accepted by
                       #   init/doctor/secret to pick the file they
                       #   write/check/update (default ./.env)
ccu-mcp --version      # print the installed version and exit
ccu-mcp --help         # print usage and exit

ccu-mcp init 会引导你配置一个或多个 CCU 目标(多个 CCU 目标)——它会先询问你是否需要配置多个目标,然后逐一询问每个目标的名称、端点、证书固定值、凭据和两个策略标志,并询问要将哪个目标设为启用状态。它会检测每个已配置用户的权限级别是 ADMIN 还是 USER(基于脚本的工具需要 ADMIN),最后提供一段可直接粘贴的 MCP 客户端配置片段。无需预先存在配置。任何检查失败时,ccu-mcp doctor 都会以非零状态码退出,因此也适用于脚本;如果 CCU 的证书确实已轮换,请在交互模式下运行,以便选择刷新固定值。操作示例:设置多个目标。

LLM 引导式设置(设置模式)

该向导还有一个对话版:先在 MCP 客户端中注册服务,再进行配置。使用 --stdio --env <path> 启动,且配置缺失或不完整时,服务会以设置模式启动——这是一个精简的 MCP 服务,仅公开四个 setup_* 工具(setup_status、setup_probe、setup_write_profile、setup_test)以及相关说明,让 LLM 通过普通聊天引导你完成相同的探测 → 固定证书 → 测试登录 → 写入流程。

{
  "mcpServers": {
    "ccu-mcp": {
      "command": "npx",
      "args": ["ccu-mcp", "--stdio", "--env", "/path/to/.env"]
    }
  }
}

然后只需提出请求:“设置我的 CCU 连接”。有一个刻意设计的例外:密码绝不会经过模型或聊天记录。setup_write_profile 没有密码参数;助手会给你一条命令,让你在终端中运行——npx ccu-mcp secret <profile> --env /path/to/.env,或者根据你的安装方式使用等效命令——它会在本地提示输入密码(关闭回显),并且只将密码写入文件(权限模式为 0600)。请复制工具输出的命令,而不是这里的命令:该命令会指定输出它的构建版本,因此不会误用缺少此子命令的旧版安装。setup_test 报告成功后,重新连接 MCP 服务,同一条客户端配置就会以完整配置启动服务。

这里也支持多个 CCU——说明这一点(“我有一个生产环境 CCU 和一个开发环境 CCU”),助手就会针对每个目标重复执行探测 → 写入 → 密钥流程:setup_write_profile 接受一个 name(以及 protected、readonly 和 makeDefault),并更新该目标,同时保留其他目标及其已存储的密码。每个目标都需要单独运行一次 ccu-mcp secret <name>;在所有已配置目标都设置好密码之前,服务会保持在设置模式:如果中途重新连接,会再次进入设置模式,并指出仍缺少密码的目标以及完成设置所需的确切 secret 命令。真正没有密码的 CCU 不属于缺少密码——将键写入空值(CCU_<NAME>_PASSWORD=)即可明确表示这一点。

设置模式仅支持 stdio(可写入配置文件的未配置 HTTP 端点会造成不可接受的攻击面);不带 --env 直接启动仍会明确报错,而不会静默地提供设置工具。

--version 和 --help 无需配置——可用它们检查已安装的副本究竟是什么版本,例如更新后:

$ npx ccu-mcp@latest --version
1.10.0

请注意,直接运行 npx ccu-mcp 会复用缓存于 ~/.npm/_npx 的副本,而不会重新从注册表解析;如果想获取最新版本,请指定 @latest(或清除该缓存)。

如何提供这些变量(内联、.env 或 export)

必需的 CCU_HOST / CCU_PASSWORD(以及其他所有变量)都是环境变量。任选以下一种方式提供即可,只需选一种:

  • 在 .mcp.json 中内联——使用上方 选项 A 中所示的 env 块。最简单,配置齐全。

  • Shell export——如上方快速开始所示。

  • .env 文件——将密钥保留在 .mcp.json 之外。使用服务自身的 --env 标志传入(ccu-mcp init 也会写入此配置并打印相应代码片段):

    {
      "mcpServers": {
        "ccu-mcp": {
          "command": "npx",
          "args": ["ccu-mcp", "--stdio", "--env", "/path/to/.env"]
        }
      }
    }
    

    (也可以在脚本路径前使用 Node 自身的 --env-file= 标志,但如果文件尚不存在,Node 会拒绝启动,而且该标志需要 dist/index.js 的完整路径。)

    将 .env.example 复制为 .env 并填写内容(其中说明了每个变量)。Docker 用户可以通过 docker run --env-file .env 或 compose 的 env_file: 传入同一文件。确保 .env 已加入 gitignore。

多个 CCU 目标(配置档)

默认情况下,上方的 CCU_* 变量用于配置单个 CCU。如需通过一个服务访问多个 CCU(例如 生产环境 + 开发环境),请改为定义命名配置档。与其他配置一样,可通过内联、.env 或 export 设置这些变量——参见上文:

CCU_PROFILES=prod,dev
CCU_DEFAULT_PROFILE=prod           # active at startup (defaults to the first listed)

CCU_PROD_HOST=ccu.example
CCU_PROD_USER=ai
CCU_PROD_PASSWORD=...
CCU_PROD_HTTPS=true
CCU_PROD_PROTECTED=true            # writes need confirm:true

CCU_DEV_HOST=127.0.0.1
CCU_DEV_PORT=18080
CCU_DEV_USER=Admin
CCU_DEV_PASSWORD=                  # may be empty (e.g. an OpenCCU dev box)

每个配置档使用与扁平变量相同的设置,变量名前缀为 CCU_<NAME>_(名称需大写,非字母数字字符替换为 _):HOST(必需)、PASSWORD(可以为空;与扁平变量 CCU_PASSWORD 不同,也可以完全省略,此时会按空值处理)、USER、PORT、HTTPS、TIMEOUT、SCRIPT_TIMEOUT、TLS_FINGERPRINT、CA_CERT、TLS_VERIFY,以及两个策略标志:

  • CCU_<NAME>_PROTECTED=true——除非调用时传入 confirm: true,否则写入工具会拒绝执行;传入后,本次会话期间对该目标的写入操作将获准。例外:每次调用 run_script 和 delete_system_variable 时都必须传入 confirm: true,它们不会因会话解锁而获准(脚本会绕过所有类型化工具的防护;删除操作无法恢复),且确认这两项操作不会解锁会话中的其他写入操作。
  • CCU_<NAME>_READONLY=true——写入工具将直接被拒绝。

如果未设置 CCU_PROFILES,则会将扁平的 CCU_* 变量作为单个 default 配置档使用(行为不变)。运行时,list_ccu_targets 会显示各个目标,get_connection_info 会报告当前活动目标,而 use_ccu 可用于切换目标。读取工具也接受可选的 target 参数,可在单次调用中从另一个 CCU 读取数据,而无需切换目标。

配置多个目标

使用向导。 ccu-mcp init 会先询问,然后针对每个目标依次收集名称 → 端点 → 证书固定值 → 凭据 → 策略标志,最后询问哪个目标作为当前活动目标启动:

$ npx ccu-mcp init --env ~/.config/ccu-mcp/.env
ccu-mcp setup — probes your CCU, pins its TLS certificate, tests the
login, and writes the result to /home/you/.config/ccu-mcp/.env.

Set up multiple CCU targets (e.g. prod/dev)? [y/N]: y
Profile name [prod]: prod
CCU hostname or IP: ccu.example
Probing ccu.example ...
  Found the CCU API on port 443 (HTTPS).
Use HTTPS? [Y/n]: y
Port [443]: 443
The CCU presents this TLS certificate:
  Subject: ccu.example
  Issuer:  ccu.example
  Valid:   Jun 19 21:37:09 2026 GMT — Jun 16 21:37:09 2036 GMT
  SHA-256: 90:0C:4C:F2:53:22:E7:78:...:40:ED:16:95:6E:BB:B1:53
Pin this certificate's fingerprint (recommended)? [Y/n]: y
CCU user [Admin]: ai
CCU password (input hidden):
Testing login ...
  Login OK (CCU 3.87.6.20260614) — privilege level ADMIN: all tools available.
Protect this target (write tools then require confirm:true)? [y/N]: y
Make this target read-only (write tools refused entirely)? [y/N]: n
Add another CCU target? [y/N]: y
Profile name: dev
CCU hostname or IP: 192.168.1.50
Probing 192.168.1.50 ...
  Found the CCU API on port 80 (HTTP).
Use HTTPS? [Y/n]: n
Port [80]: 80
CCU user [Admin]: Admin
CCU password (input hidden):
Testing login ...
  Login OK (CCU 3.87.6.20260614) — privilege level ADMIN: all tools available.
Protect this target (write tools then require confirm:true)? [y/N]: n
Make this target read-only (write tools refused entirely)? [y/N]: n
Add another CCU target? [y/N]: n
Default target (prod/dev) [prod]: prod

Wrote /home/you/.config/ccu-mcp/.env (mode 0600).

它写入的文件采用配置文件格式,每个目标对应一个带注释的区块;向导只会重写这些键,因此文件中的其他内容(LOG_LEVEL、 CACHE_DIR、MCP_*)都会保留:

# Written by ccu-mcp setup — https://github.com/claymore666/ccu-mcp#configuration
CCU_PROFILES=prod,dev
CCU_DEFAULT_PROFILE=prod

# --- target: prod ---
CCU_PROD_HOST=ccu.example
CCU_PROD_PORT=443
CCU_PROD_HTTPS=true
CCU_PROD_USER=ai
CCU_PROD_PASSWORD="..."
CCU_PROD_TLS_FINGERPRINT=90:0C:4C:F2:53:22:E7:78:...:40:ED:16:95:6E:BB:B1:53
CCU_PROD_PROTECTED=true

# --- target: dev ---
CCU_DEV_HOST=192.168.1.50
CCU_DEV_PORT=80
CCU_DEV_HTTPS=false
CCU_DEV_USER=Admin
CCU_DEV_PASSWORD=""

在已有文件上重新运行 init 时,向导会询问是否替换这些设置;添加第三个目标意味着要重新遍历整个列表,因此若只是临时添加目标,请编辑文件(或使用 setup_write_profile,它会更新或插入单个目标),然后运行 doctor。

每个目标一个密码。 ccu-mcp secret 只会写入一个键,因此需要提供目标名称——init 会在流程中提示输入密码,但 LLM 引导的流程和之后的每次轮换都要通过 secret 完成。在配置文件上不提供名称时,它会列出所需的运行命令:

$ ccu-mcp secret --env ~/.config/ccu-mcp/.env
This file configures named targets (prod, dev) — one password each:
  node /home/you/.local/bin/ccu-mcp secret prod --env /home/you/.config/ccu-mcp/.env
  node /home/you/.local/bin/ccu-mcp secret dev --env /home/you/.config/ccu-mcp/.env

$ ccu-mcp secret prod --env ~/.config/ccu-mcp/.env
CCU password for [email protected] (input hidden):
Wrote CCU_PROD_PASSWORD to /home/you/.config/ccu-mcp/.env (mode 0600).

这些提示有意显示为 node <path>,而不是 ccu-mcp:该路径对应打印提示的构建版本,因此复制命令不会误用缺少此子命令的旧版本。secret 在扁平的单 CCU 文件中会拒绝目标名称,在配置文件中会拒绝未知目标,因此绝不会写入错误的键。

一次性验证所有内容。 doctor 会检查每个目标的配置、连通性、证书固定值、登录状态和权限级别;任一检查失败都会以非零状态码退出:

$ ccu-mcp doctor --env ~/.config/ccu-mcp/.env
ccu-mcp doctor — checking /home/you/.config/ccu-mcp/.env
  ✓ configuration loads: 2 target(s), default "prod"

Target "prod" — ccu.example:443 (HTTPS)
  ✓ CCU API reachable
  ✓ pinned TLS fingerprint matches the presented certificate
  ✓ login OK as "ai" (CCU 3.87.6.20260614) — privilege level ADMIN

Target "dev" — 192.168.1.50:80 (HTTP)
  ✓ CCU API reachable
  ✓ login OK as "Admin" (CCU 3.87.6.20260614) — privilege level ADMIN

All checks passed.

在客户端中。 一个 MCP 服务条目即可服务所有目标——目标列表由 --env 文件提供,因此添加 CCU 时无需更改客户端配置:

{
  "mcpServers": {
    "ccu-mcp": {
      "command": "npx",
      "args": ["ccu-mcp", "--stdio", "--env", "/home/you/.config/ccu-mcp/.env"]
    }
  }
}

然后在聊天中询问:“配置了哪些 CCU?”(list_ccu_targets)、“读取 dev 上客厅的温度”(单次调用时指定 target: "dev")、“切换到 dev”(use_ccu)。如上所示,设置 CCU_PROD_PROTECTED=true 后,首次对 prod 执行写入操作时会要求提供 confirm: true;确认后,该目标在本次会话的剩余时间内会解除锁定——但 run_script 和 delete_system_variable 除外,这两项每次都会询问。

配置错误

有些错误会导致服务器在启动时停止,而不是忽略它们。否则,这些错误会一直被静默忽略,直到很久以后才导致失败,因此退出是有意为之的。ccu-mcp doctor 会在不启动服务器的情况下,针对 env 文件报告同样的错误,同时执行实时检查(可达性、证书固定、登录)。有一个例外:使用 --stdio --env <path> 启动时,如果配置有误,服务器会进入设置模式(并在服务器的说明中显示错误),而不是退出,这样就可以通过对话修复配置:

消息原因及其致命性
CCU_HOST environment variable is required未配置 CCU(且未设置 CCU_PROFILES)。
CCU_PASSWORD environment variable is required该变量不存在。空值是可接受的——全新的 OpenCCU 设备没有 Admin 密码——因此这表示“尚未设置”。这会让单 CCU 设置模式服务器一直处于设置模式,直到 ccu-mcp secret 保存密码。
no password stored yet for target <name>配置文件形式的对应错误,仅限设置模式:CCU_<NAME>_PASSWORD 不存在。已加载的配置仍会将缺失的键读取为空值(保持不变,因此 OpenCCU 开发目标仍可正常工作)——但在判断设置是否完成时,不存在表示“尚未输入”,因此服务器会继续处于设置模式,并打印用于完成设置的 ccu-mcp secret <name> 命令。写入 CCU_<NAME>_PASSWORD= 可明确声明密码为空是有意为之。
CCU_DEFAULT_PROFILE is set but CCU_PROFILES is not配置文件设置遗留的内容。忽略它会让写入操作指向扁平配置中的 CCU_HOST 设备,而 env 文件却显示存在一个命名目标。
CCU_PROFILES is set but lists no profile names值为空,或仅包含逗号。
CCU_PROFILES lists "<name>" more than once配置文件名称重复。
... both map to the same env prefix CCU_<P>_* — rename one不同名称经过规范化后可能发生冲突:prod-a 和 prod.a 都会读取 CCU_PROD_A_*,因此它们会被静默地视为同一个目标。
CCU_DEFAULT_PROFILE="x" is not one of CCU_PROFILES (...)启动配置文件名称拼写错误。
profile "<name>" is missing CCU_<P>_HOST每个配置文件都必须指定主机;密码可以为空。
TLS_FINGERPRINT/CA_CERT/TLS_VERIFY is set but HTTPS is disabled验证代码路径仅适用于 HTTPS。忽略这些设置会让你误以为连接已通过验证,而凭据实际上是明文传输的。请设置 CCU_HTTPS=true(或 CCU_<NAME>_HTTPS=true),或者移除这些设置。
MCP_TLS_CERT and MCP_TLS_KEY must both be set (or both unset)只设置部分 TLS 配置无法提供 HTTPS 服务。
MCP_TRANSPORT must be "http" or "stdio"大小写敏感。像 STDIO 这样的拼写错误不得静默地选择 HTTP,导致启动 stdio 的客户端永远等待。
<VAR> must be a positive integer端口、超时、CACHE_TTL、速率限制、RESOURCE_POLL_INTERVAL。整个值必须由数字组成——CCU_TIMEOUT=30s 会被拒绝,而不是被读取为 30 毫秒;30.5 或 1e4 也会被拒绝,而不是截断处理。
<VAR> must be a positive number两项时长设置:MCP_AUTH_TOKEN_TTL_DAYS 和 MCP_AUTH_TOKEN_GRACE_HOURS,这两项设置允许使用小数值。
<VAR> must be "true" or "false"任意布尔设置(CCU_HTTPS、CCU_TLS_VERIFY、CCU_<NAME>_PROTECTED、CCU_<NAME>_READONLY、MCP_ALLOW_PLAINTEXT)。首尾空格和大小写均可;不接受 yes、1 和 on,因为将它们视为false会悄然关闭保护。
CCU_CA_CERT could not be read路径错误,或服务器用户无权读取该文件。

无需任何配置即可使用 ccu-mcp --version 和 --help,因此在排查这些问题时仍可使用它们。

工具

28 个工具,按实际用途分类:

查找 — list_devices、list_rooms、list_functions、list_interfaces、list_programs、list_system_variables、list_links、describe_device_type

读取状态 — get_value、get_values(批量)、get_paramset

更改设置 — set_value、put_paramset、set_system_variable、create_system_variable、delete_system_variable、assign_channel、unassign_channel、execute_program

检查运行状况 — get_service_messages、acknowledge_service_messages、get_rssi、get_system_info

切换目标 — list_ccu_targets、get_connection_info、use_ccu(多 CCU 配置;见上文)

其他 — help(上下文感知)、run_script(原始 HomeMatic Script,用于批量操作、重命名设备/通道、查询房间成员关系,或处理其他工具未涵盖的任何事项)

大多数工具会根据设备地址自动解析接口和值类型——你无需了解设备使用的是 BidCos-RF 还是 HmIP-RF。

资源和提示词

除了工具外,服务还会提供 MCP 资源——可浏览的 JSON 快照,客户端可以将其附加为上下文:

homematic://devices、homematic://rooms、homematic://functions、homematic://programs、homematic://sysvars、homematic://interfaces、homematic://device-types、homematic://system

服务会在后台轮询 CCU(每隔 RESOURCE_POLL_INTERVAL 秒一次),并向通过 resources/subscribe 订阅了资源的客户端发送这些资源内容发生变化时的 notifications/resources/updated 通知。

服务还附带 MCP 提示词——可从支持提示词的客户端调用的现成工作流(例如,在 Claude Code 中作为斜杠命令使用):

  • check-windows — 是否有窗户或门处于打开状态?
  • room-status — 指定房间的完整状态报告
  • set-heating — 设置房间的目标温度
  • good-night — 为夜晚做好准备
  • diagnostics — 检查设备问题
  • device-info — 设备功能和参数的详细信息

room 和 device 参数支持自动补全:支持 completion/complete 的客户端会提供此 CCU 实际拥有的房间和设备名称, 因此无需记住房间在 WebUI 中的拼写方式。

MCP 协议修订版本

服务实现了修订版本 2025-11-25,并会为较旧的客户端协商降级(2025-06-18、2025-03-26、2024-11-05 均可接受)——你 无需使用特定版本的客户端。服务会声明 tools、resources (含 subscribe)、prompts、completions 和 logging。

修订版本 2026-07-28——每个请求的协议版本、server/discover—— 尚未实现:编写本文时,此服务所基于的 TypeScript SDK 尚不支持该版本,而此服务遵循该 SDK。

工作原理

服务通过 CCU 的 JSON-RPC API(与 WebUI 使用的相同 API)进行通信。启动时,它会:

  1. 登录并缓存会话(重启后会复用)
  2. 从磁盘加载设备类型缓存(或在后台预热缓存)
  3. 通过 stdio 或 HTTP 启动 MCP 服务

设备类型架构会缓存在本地,因此 AI 无需每次都访问 CCU,即可查询有效参数、类型和值范围。

返回的值使用原生类型——21.5 而不是 "21.500000",true 而不是 "true"。

已测试的设备

此服务已在生产环境中的 debmatic 安装上进行测试,涉及以下设备:

  • HmIP-eTRV-2 / eTRV-2 I9F(散热器恒温器)
  • HmIP-STHD(带湿度功能的墙面恒温器)
  • HmIP-WTH-2(墙面恒温器)
  • HmIP-SWDO-I(门窗触点)
  • HmIP-STHO(室外温度/湿度传感器)
  • HmIP-ESI(电能/燃气表)
  • HmIP-FALMOT-C12(地暖控制器)
  • HmIP-HEATING(虚拟供暖组)
  • HmIP-WRCC2(墙面遥控器)
  • HM-PB-6-WM55(BidCos 六键遥控器)
  • RPI-RF-MOD(无线模块)

其他设备类型也应该可以使用——服务会向 CCU 查询参数说明,而不是维护静态设备数据库。

更新日志

发行说明——包括升级前需检查的行为变更 (更严格的配置验证、/health 响应结构、按会话确认写入、 重试语义)——请参阅 CHANGELOG.md。

获取帮助与参与贡献

  • 遇到故障,或有功能建议? 请提交议题: github.com/claymore666/ccu-mcp/issues
  • 有问题、需要设置帮助,或想讨论 HomeMatic? 请访问 HomeMatic 论坛——维护者在论坛上的用户名是 claymore666。
  • 发现安全问题? 请不要公开发布。有关私下报告的方式,请参阅 SECURITY.md。
  • 想提交补丁? CONTRIBUTING.md 介绍了设置方法、 目标分支、编码规范和测试政策。

所有参与者都应遵守 行为准则。

项目文档
文档内容
ROADMAP.md项目的发展方向,以及明确不会实现的内容
GOVERNANCE.md决策者、决策方式,以及已知的连续性缺口
SECURITY.md报告方式、安全要求、威胁模型
docs/architecture.md高层设计和请求流程
docs/assurance-case.md安全要求成立的原因及相关证据
CHANGELOG.md各个版本的变更内容

相关项目

  • OpenCCU — 由社区维护、无云服务的 CCU 固件,适用于 Raspberry Pi、x86/ARM 以及 CCU3/ELV-Charly 硬件(原名 RaspberryMatic;基于 OCCU 框架构建)
  • debmatic — 在 Debian、Ubuntu、Raspberry Pi OS、Armbian 上运行 HomeMatic
  • OCCU — eQ-3 原版 Open CCU SDK(上游 HomeMatic 软件);目前正逐步由社区维护的 OpenCCU 取代
  • MCP — Model Context Protocol 规范
  • ccu-ai-mcp,由 Mathias (mdzio) 开发 — 一个面向 HomeMatic 的同类 MCP 服务,采用刻意不同且优雅的方案(精简的 Go 核心搭配用户自定义的 HM-Script 工具)。请参阅他在 HomeMatic 论坛 上发布的介绍。

许可证

MIT

评论

支持 Markdown

第一次接触 MCP?

从协议是什么,到在客户端里装上第一个服务,这几条回答覆盖了大多数入门问题。

一个开放协议,规定了 AI 应用如何以统一方式连接外部工具与数据源。客户端负责与模型对话,MCP 服务负责提供工具、资源和提示模板,两者通过标准消息通信,同一个服务可以被不同客户端复用。