用 Compose 配置减少智能体部署误判
文章介绍为 Cognee 构建 Docker Compose 连接器,向智能体提供实际基础设施配置。重点针对服务主机名、端口映射、卷挂载和依赖条件被错误推断的问题。
AI 深度解读
让 AI 帮忙排查容器网络,命令看起来没毛病,却把数据库地址写成了 localhost:5432。问题可能不在模型会不会写命令,而在它根本不知道服务之间怎么连接。
作者在 Mergetober 期间参与开发了一个 Docker Compose 数据源连接器,尝试把配置送进 Cognee,让 Agent 先检索基础设施信息,再生成操作建议。方向有用,但原文展示的是预期架构和示例流程,没有给出准确率对照,也没有证明这些 API 可以直接运行。
Agent 缺的可能就是仓库里的那份配置
Claude Code、Devin、Cursor 和 GitHub Copilot 被用于排查部署故障、配置 CI/CD、管理本地多容器环境时,都可能遇到同一个问题:根据常见项目模式,补出一套并不存在的容器拓扑。
容器拓扑,就是服务之间的连接关系,以及各自的端口、挂载和启动依赖。
原文列出的错误很具体:本该访问内部地址 db:5432,却用了 localhost:5432;Compose 明明配置 6379:6379,却猜 Redis 暴露在 6380;还可能假设错误的持久化目录,或者漏掉 depends_on 中的 service_healthy 条件。
这里最需要补上的,是执行位置。命令在宿主机上运行,还是在应用容器里运行,会影响应该使用哪个地址。仅仅知道「项目用了 PostgreSQL」远远不够。
compose.yaml 或 docker-compose.yml 已经记录了这些事实,包括 postgres:16-alpine、redis:7 等镜像,构建上下文和 Dockerfile,8080:80、5432:5432 等端口绑定,以及环境变量、命名卷、绑定挂载和 app-network 等网络。
作者的主张是:把这些信息解析、组织并建立索引,需要时再取出来。每次粘贴整份 500 行的 Compose 文件也能补充上下文,但会占用上下文窗口,让相关配置更难定位。
配置应该成为 Agent 的证据,而不是留给它补全的空白。
把 YAML 放进知识图谱,难点在更新和关系保真
Cognee 是一个用于构建 AI 记忆系统的开源框架。作者希望连接器解析服务、端口、卷、网络和依赖,再交给 Cognee 摄取,形成知识图谱与向量检索,最后为 Agent 提供配置上下文。
知识图谱在这里可以理解为:除了保存「有哪些服务」,还保存「谁依赖谁」等关系。向量检索则帮助系统根据自然语言问题找出相关信息,例如「哪些服务依赖 PostgreSQL,它发布了哪些端口,配置了什么健康检查条件」。
这套流程能否有效,取决于三个细节。
第一,服务身份是否稳定。原文建议使用 docker_compose:service:{service_name} 作为标识,帮助多次导入时识别同一服务。但标识相同不等于自动去重,摄取管线还得按这个身份处理实体。
第二,旧信息能否删除。新增服务容易理解,删除服务更容易留下隐患。再次导入更新后的文件,不一定会清理既有记忆中的旧节点。即使设置 write_disposition="replace",也只有连接器和底层管线明确支持替换语义时,才可能得到预期结果。
第三,配置细节是否完整。原文用 api 服务举例:镜像为 my-org/api:v1.2.0,端口为 8000:8000,DATABASE_URL 指向 postgres://<user>:<password>@db:5432/app;它依赖健康的 db 和 cache,并挂载 ./logs:/var/log/api。
这是一份便于 Agent 阅读的服务表示,并非完整的 Compose 文件。环境变量中的凭据还应在存储或暴露给 Agent 前脱敏或排除。至于依赖关系能保留到什么程度,原文也加了前提:需要摄取管线支持。
示例串起了流程,但还不是可直接交付的方案
原文给出的预期安装命令是 pip install cognee cognee-community-connector-docker-compose,同时要求先确认连接器包是否发布、安装说明是否匹配实际实现。
目录安排很简单:infrastructure-project/ 下放置 docker-compose.yml 和 ingest_topology.py。下面这段代码展示配置如何进入检索流程,保留原文写法:
import asyncio
import cognee
from cognee_community_connector_docker_compose import (
docker_compose_source,
)
async def main():
# 第一步:加载 Docker Compose 配置
print("Loading Docker Compose configuration...")
source = docker_compose_source(
compose_path="./docker-compose.yml"
)
# 第二步:将配置摄取到 Cognee
await cognee.remember(
source,
dataset_name="infrastructure_topology",
)
# 第三步:构建知识表示
print("Processing infrastructure knowledge...")
await cognee.cognify(
dataset_name="infrastructure_topology",
)
# 第四步:检索基础设施记忆
print("Searching container architecture...")
results = await cognee.search(
"What services depend on PostgreSQL, and which ports are published?",
dataset_name="infrastructure_topology",
)
for result in results:
print(result)
if __name__ == "__main__":
asyncio.run(main())
要留意 docker_compose_source(...) 的导入路径和函数签名,以及 cognee.remember、cognee.cognify、cognee.search 的实际接口。原文没有指定 Cognee 版本,明确要求运行前对照仓库核实。
这段代码表达的顺序是:加载配置、提交数据、构建知识表示、检索相关上下文。它没有展示 Agent 如何消费结果,也没有展示检索失败或信息冲突时怎么处理。
拿到配置之后,Agent 可能建议这样的命令:
docker compose exec db pg_isready -U postgres
docker compose run --rm api python manage.py migrate
需要核对的是 db、api、用户 postgres 和迁移入口 python manage.py migrate。它们都是项目相关的示例,不能直接当成 Node 项目的操作模板。
作者列出了 PR topoteretes/cognee-community#492 和关联 issue topoteretes/cognee#6307,但正文没有交代合并状态、完整支持范围或运行测试结果。因此,能确认的是作者参与了连接器工作,不能据此认定整条链路已经验证完成。
我的判断
我认同「先拿配置,再写命令」这个方向。端口映射、容器地址和启动条件都有明确配置来源,让模型凭常识补齐,确实没有必要。
但从这个判断到「需要 Cognee」,中间还有一步取舍。
如果项目只有一份较短的 Compose 文件,让 Agent 直接读取当前配置,可能更省事。检索系统会增加解析、索引、同步和查询环节,每个环节都可能丢信息。尤其是文件已经更新、记忆尚未同步时,Agent 可能非常确信地引用旧配置。
对于反复查询基础设施关系的场景,结构化检索有吸引力。不过,原文没有把它与直接读取文件、全文搜索、粘贴配置做效果或成本对照,也没有给出幻觉率下降的数据。这里展示的是工程思路,效果仍待验证。
检索能减少猜测,不能替代对当前配置和执行环境的核验。
另外,Compose 描述的是配置。原文没有展示对实际运行状态的采集,所以不能仅凭检索结果断言服务已经启动、数据库已经健康。健康检查条件写在文件里,与此刻检查是否通过,是两件事。
能拿来做什么
- 在前端加 Node 后端的多容器项目里,让 Agent 排查连接问题前,先读取 Compose 中的服务名、端口、网络和依赖,并明确命令运行在宿主机还是容器内。
- 让 Agent 编写集成测试或数据库初始化脚本时,要求它把使用的地址、端口和服务名对应到实际配置;没有配置依据的部分应明确标注待确认。
- 如果要试做连接器,先验证新增、修改、删除服务后的检索结果,再考虑接入自动执行;不要仅凭
write_disposition="replace"就认定旧实体已经清理。 - 复现原文时,先核实包的发布状态、导入路径和 Cognee API,再检查入库内容是否包含凭据,最后用项目实际支持的命令验证检索结果。