API 总览
CoreC 核心内置一套 RESTful API 与 WebSocket 实时流接口,用于驱动管理、数据读写、配置热更新、规则控制及运行时监控。API 服务通过配置项 global.api.listen 启动;该配置项未设置(空字符串)时不启动任何 API 服务,没有默认监听地址。
基础信息
| 项目 | 说明 |
|---|---|
| 协议 | HTTP/1.1(RESTful)+ WebSocket;配置 global.api.tls-cert 与 global.api.tls-key 后启用 HTTPS(WebSocket 对应 wss://) |
| 基础地址 | http://<host>:<port>,由 global.api.listen 决定 |
| 内容类型 | application/json(绝大多数请求体与响应体);例外:GET /configs/raw 与 GET /configs/backups/{name} 返回 application/yaml,GET /metrics 返回 Prometheus 文本格式(text/plain; version=0.0.4) |
| 字符编码 | UTF-8 |
| 请求体上限 | 1 MiB(maxRequestBody,超出将返回 400 Bad Request) |
| 鉴权方式 | Bearer Token(Authorization 请求头;仅 WebSocket 升级请求例外地可用 ?token= 查询参数,见下文) |
认证
当配置项 global.api.secret 非空时,除公开端点外的所有端点均需鉴权。普通 HTTP 请求只接受 Authorization 请求头;?token= 查询参数仅对 WebSocket 升级请求开放(浏览器 WebSocket API 无法自定义 Header 的狭窄例外,避免 Token 泄露到浏览器历史、反向代理日志与 Referer 头):
curl http://localhost:9090/drivers \
-H "Authorization: Bearer corec-secret-token"wscat -c "ws://localhost:9090/tags/stream?token=corec-secret-token"Token 比较先将双方做 SHA-256 哈希再以恒定时间比较(crypto/hmac.Equal),可防止时序攻击并避免泄露 Secret 长度。
未配置 Secret
若 global.api.secret 为空,核心将拒绝启动(fail-closed)以确保安全,而非跳过鉴权公开所有端点。具体而言:
- 配置加载阶段:当
global.api.listen非空时,global.api.secret必须非空且不少于 8 个字符,否则配置加载直接失败(参见config.validate)。 - 服务启动阶段:即便绕过配置校验直接调用
ReCreateServer,空 Secret 也会令服务端打印API server refusing to start: api.secret is empty.并拒绝启动(参见hub/route/server.go)。
Secret 必须显式设置,不存在"空 Secret 即跳过鉴权、公开所有端点"的回退行为。
公开端点
以下端点无需认证,始终可访问:
| 方法 | 路径 | 说明 |
|---|---|---|
GET | / | 服务信息,返回 {"name": "corec", "version": "...", "status": "ok", "time": "...", "uptime": "..."} |
GET | /version | 版本信息,返回 {"version": "<构建版本>"}(默认 dev,经 -ldflags 注入 hub/route.Version) |
GET | /healthz/live | 存活探针,返回 {"status": "alive"}(Kubernetes liveness) |
GET | /healthz/ready | 就绪探针,检查引擎状态与数据通路(Kubernetes readiness) |
CORS
API 内置 CORS 中间件,用于支持浏览器端仪表盘跨域访问。行为取决于 global.api.allowed-origins 配置:
- 未配置
allowed-origins(默认):返回Access-Control-Allow-Origin: *,允许任意来源跨域访问,便于本地开发与快速接入仪表盘。 - 配置了
allowed-origins:仅对列表中的来源反射其Origin值,其余来源不返回 CORS 头(限制模式)。
| 响应头 | 值 |
|---|---|
Access-Control-Allow-Origin | 默认 *;或白名单中匹配的 Origin 原值 |
Access-Control-Allow-Methods | GET, POST, PUT, PATCH, OPTIONS |
Access-Control-Allow-Headers | Content-Type, Authorization |
Access-Control-Max-Age | 86400(24 小时) |
OPTIONS 预检请求直接返回 204 No Content。
生产环境建议
默认配置下 CORS 策略为 *(宽松)。生产环境建议显式配置 global.api.allowed-origins 为指定仪表盘域名,或通过反向代理(如 Nginx)进一步收紧。
错误格式
所有错误响应统一使用以下 JSON 结构,HTTP 状态码与错误语义对应:
{
"error": "unauthorized"
}状态码约定
| 状态码 | 含义 | 触发场景 |
|---|---|---|
200 OK | 请求成功 | 所有 GET 端点、POST /write 成功、POST /write/batch(含部分失败)、POST /drivers/test 与 POST /transports/{name}/test(连通与不通都是 200) |
201 Created | 资源已创建 | POST /configs/backups 手动快照成功 |
204 No Content | 操作成功,无响应体 | PUT /configs、PATCH /configs、PATCH /rules/disable、POST /configs/backups/{name}/restore、资源级 DELETE /drivers/{name}、DELETE /transports/{name}、DELETE /rules/{name}、POST /drivers/{name}/pause、POST /drivers/{name}/resume、POST /alerts/ack |
400 Bad Request | 请求格式错误 | JSON 解析失败、规则名/索引不存在、POST /write 目标驱动不存在或未连接、POST /write 与 /write/batch 缺失 type 字段、批量写空数组或超 128 条、备份名非法或备份校验失败、PATCH 配置键不合法、PUT /configs 的 path 校验失败(绝对路径/越出配置目录)等 |
401 Unauthorized | 认证失败 | Token 缺失或不匹配 |
404 Not Found | 资源不存在 | 驱动/传输名称未找到、规则名未找到、告警键不存在、配置备份不存在 |
422 Unprocessable Entity | 全部批量写失败 | POST /write/batch 请求合法但所有指令均被设备层面拒绝 |
429 Too Many Requests | 请求频率超限 | 触发速率限制中间件(global.api.rate-limit-per-sec,按客户端 IP 令牌桶,超限响应带 Retry-After: 1) |
500 Internal Server Error | 内部错误 | 写入失败、配置应用失败、资源级 DELETE 应用失败等(响应体为脱敏的 internal server error,真实原因仅记录服务端日志) |
501 Not Implemented | 能力不支持 | 引擎未实现端点依赖的可选角色接口(如 GET /write/history 需要 core.WriteAuditor、POST /rules/preview 需要 core.RulePreviewer、GET /alerts/POST /alerts/ack/WS /alerts/stream 需要 core.AlertProvider/core.AlertStreamer、驱动暂停/恢复与 GET /drivers/paused 需要暂停角色、GET /configs/audit 需要审计接线) |
503 Service Unavailable | 服务状态不满足 | 空配置启动(无配置文件路径)时访问配置/备份端点、GET /configs 无活动配置、GET /healthz/ready 引擎未就绪 |
端点索引
RESTful 端点
| 方法 | 路径 | 鉴权 | 说明 |
|---|---|---|---|
GET | / | 否 | 服务信息(名称/版本/运行时间) |
GET | /version | 否 | 版本信息 |
GET | /healthz/live | 否 | 存活探针(Kubernetes liveness) |
GET | /healthz/ready | 否 | 就绪探针(Kubernetes readiness) |
GET | /configs | 是 | 获取当前配置概要(脱敏) |
GET | /configs/raw | 是 | 获取完整配置 YAML 原文(含明文凭据与环境变量展开值,供配置中心编辑器;注意回存会材料化 ${ENV} 引用) |
PUT | /configs | 是 | 全量重载配置(变更前自动快照到服务端备份) |
PATCH | /configs | 是 | 增量更新配置 |
POST | /configs/validate | 是 | 配置 dry-run 校验(不应用) |
GET | /configs/audit | 是 | 配置变更审计轨迹(最近 500 次成功变更:何时、来自哪个调用方、改了什么) |
GET | /configs/backups | 是 | 列出服务端配置备份(新→旧,仅元数据,保留最近 10 份) |
GET | /configs/backups/{name} | 是 | 读取指定备份 YAML 原文(安全姿态同 /configs/raw) |
POST | /configs/backups | 是 | 手动创建当前磁盘配置快照 |
POST | /configs/backups/{name}/restore | 是 | 恢复指定备份(走完整校验链,不绕过校验) |
GET | /drivers | 是 | 列出所有驱动状态 |
GET | /drivers/{name} | 是 | 获取指定驱动状态 |
GET | /drivers/{name}/tags | 是 | 获取指定驱动最新标签值 |
POST | /drivers/test | 是 | 驱动连通性测试(临时实例,不落配置,5s 超时) |
DELETE | /drivers/{name} | 是 | 删除单个驱动——服务端拼接配置并走完整校验/应用/持久化链(含备份快照与审计) |
GET | /drivers/paused | 是 | 列出当前暂停采集的驱动名 |
POST | /drivers/{name}/pause | 是 | 暂停指定驱动的采集任务(不动配置;设备维修/换传感器场景) |
POST | /drivers/{name}/resume | 是 | 恢复指定驱动的采集(下一 tick 起效) |
GET | /transports | 是 | 列出所有传输状态 |
GET | /transports/{name} | 是 | 获取指定传输状态 |
POST | /transports/{name}/test | 是 | 传输连通性测试(临时实例,不落配置) |
DELETE | /transports/{name} | 是 | 删除单个传输——被规则引用时返回 400 并说明原因;同上走完整安全链 |
GET | /tags | 是 | 获取所有驱动最新标签值 |
POST | /write | 是 | 向设备写入标签值 |
POST | /write/batch | 是 | 批量写入(顺序执行、逐条结果,上限 128 条) |
GET | /write/failed | 是 | 查询死信队列中失败的写入指令 |
GET | /write/history | 是 | 查询写入审计历史(最近 1000 条写记录,含成功与失败,新→旧) |
GET | /rules | 是 | 列出所有规则统计 |
PATCH | /rules/disable | 是 | 启用/禁用指定规则(按 name 推荐,index 向后兼容) |
POST | /rules/preview | 是 | 规则试算——离线验证 match 表达式(不影响生产规则集) |
DELETE | /rules/{name} | 是 | 删除单条规则(按 name)——同上走完整安全链 |
GET | /alerts | 是 | 查询活动规则告警 + 有界生命周期历史(详见 告警 API) |
POST | /alerts/ack | 是 | 确认(Acknowledge)一条活动告警(详见 告警 API) |
GET | /stats | 是 | 获取引擎运行统计 |
GET | /metrics | 是 | Prometheus 文本格式指标 |
GET | /debug/pprof/* | 是 | pprof 性能分析端点(可配置关闭或独立端口) |
传输管理端点
GET /transports 与 GET /transports/{name} 用于查询传输(transport)运行状态,返回 TransportStatus(含 name、type、state(连接状态)、published、failed、received、last_publish、queue_size、dropped_commands)。{name} 不存在时返回 404 Not Found。当前未提供独立的传输管理文档页,相关字段以代码中 core.TransportStatus 为准。
WebSocket 端点
| 路径 | 鉴权 | 说明 |
|---|---|---|
/tags/stream | 是 | 实时数据点流(支持 ?driver= 过滤) |
/logs | 是 | 实时日志流 |
/alerts/stream | 是 | 实时告警生命周期事件流(fired/acked/cleared) |
/traffic | 是 | 实时流量统计(默认每秒推送,支持 ?interval=) |
/memory | 是 | 实时内存统计(默认每秒推送,支持 ?interval=) |
WebSocket 鉴权
WebSocket 端点同样受认证中间件保护。由于浏览器 WebSocket API 无法自定义 Header,建议通过 Query 参数传递 Token:ws://host:port/tags/stream?token=<secret>。
中间件链
所有请求依次经过以下中间件处理:
- RequestID — 生成唯一请求 ID
- Trace — W3C Trace Context 传播(解析
traceparent头,注入 trace ID 到 context) - SafeRequestLogger — 计算耗时并以 DEBUG 级别记录访问日志(受
global.log-level控制,info 及以上级别不输出;自动脱敏token查询参数,防止凭证泄露) - Recoverer — 捕获 panic,返回
500防止进程崩溃 - CORS — 跨域处理
- HTTP Metrics — 记录
corec_http_requests_total/corec_http_request_duration_seconds(直方图,见可观测性指南) - RateLimit(仅当
global.api.rate-limit-per-sec > 0时启用)— 按客户端 IP 令牌桶限速,超限返回429 Too Many Requests - Authentication(仅受保护路由,且
global.api.secret非空时启用)— Bearer Token 校验
快速验证
启动核心后,可用以下命令快速验证 API 是否可用:
# 服务信息(无需认证)
curl http://localhost:9090/
# 获取驱动列表
curl http://localhost:9090/drivers \
-H "Authorization: Bearer corec-secret-token"
# 获取引擎统计
curl http://localhost:9090/stats \
-H "Authorization: Bearer corec-secret-token"