Hindsight Claude Code 插件变更指南:{user_id} 每用户记忆隔离与 requestTimeoutSeconds 超时覆盖
2026/9/14 16:41:33 网站建设 项目流程

Hindsight Claude Code 插件变更指南:{user_id} 每用户记忆隔离与 requestTimeoutSeconds 超时覆盖

【免费下载链接】hindsightHindsight: Agent Memory That Learns项目地址: https://gitcode.com/GitHub_Trending/hindsight2/hindsight

本文以 hindsight-integrations/claude-code/CHANGELOG.md 为骨架,解读 Hindsight 的 Claude Code 插件(长期记忆集成)两个版本的演进:0.1.0 初始发布建立的"自动召回 + 自动留存 + 会话生命周期钩子"基线,以及 Unreleased 阶段引入的{user_id}模板变量与requestTimeoutSeconds超时覆盖两项能力。读完后你将掌握:如何在retainTags/retainMetadata中做机器无关的每用户记忆隔离、如何为自托管 Hindsight 调整 per-call HTTP 超时以避免read operation timed out,以及空命名空间标签(如user:)被自动丢弃的新行为边界,并能在仓库源码与测试中逐项验证这些变更。

变更日志的基线:0.1.0 初始发布

理解 Unreleased 的两项新增,需要先看 0.1.0(2025-03-23)确立的插件形态。CHANGELOG 的 0.1.0 条目记录了完整的初始能力清单,这也是当前仓库代码仍完整保留的架构基线:

  • 初始发布:面向 Hindsight 长期记忆的 Claude Code 插件;
  • 自动召回:通过UserPromptSubmit钩子在每次用户提交提示时触发,把相关记忆以additionalContext注入;
  • 自动留存:通过异步Stop钩子在每轮响应结束后提取并存储会话转录;
  • 会话生命周期钩子SessionStart做健康检查,SessionEnd做 daemon 清理;
  • 三种连接模式:外部 API、自管理本地 daemon(uvx hindsight-embed)、已有本地服务器;
  • 动态 bank ID,粒度可配置为agentprojectsessionchanneluser
  • 渠道无关:兼容 Claude Code Channels(Telegram、Discord、Slack)与交互式会话;
  • 零 pip 依赖:纯 Python 标准库(urllibfcntlsubprocess);
  • 34 个配置项,经settings.json配置并支持环境变量覆盖;
  • LLM 自动探测:从OPENAI_API_KEYANTHROPIC_API_KEYGEMINI_API_KEYGROQ_API_KEY探测;
  • 分块留存(滑动窗口:retainEveryNTurns+retainOverlapTurns);
  • 记忆标签剥离:防止 retain 反馈循环。

这些钩子的接线在 hooks/hooks.json 中可以直接核对:SessionStart(5s 超时)→scripts/session_start.pyUserPromptSubmit(45s)→scripts/recall.pyStop(15s,async: true)→scripts/retain.pySessionEnd(10s)→scripts/session_end.py

Unreleased 新增一:{user_id}模板变量,实现每用户记忆隔离

CHANGELOG 的 Unreleased/Added 第一条写明:retainTagsretainMetadata支持{user_id}模板变量,从HINDSIGHT_USER_ID环境变量解析(未设置时为空字符串),从而"无需在settings.json中硬编码用户 id,即可实现机器无关的每用户记忆作用域"。

实现位置:retain 钩子中的模板解析

变量解析发生在 scripts/retain.py:

# Resolve template variables in tags and metadata. # Supported variables: {session_id}, {bank_id}, {timestamp}, {user_id} template_vars = { "session_id": session_id, "bank_id": bank_id, "timestamp": time.strftime("%Y-%m-%dT%H:%M:%SZ", time.gmtime()), "user_id": os.environ.get("HINDSIGHT_USER_ID", ""), }

retainTagsretainMetadata中的每个值都经过同一套_resolve_template替换,因此{user_id}与既有的{session_id}{bank_id}{timestamp}完全对等。配置侧的标准用法(见 README.md 的 Template variables 小节):

{ "retainTags": ["user:{user_id}", "session:{session_id}"] }

再把HINDSIGHT_USER_ID=<opaque-user-id>写入 shell profile(.zshrc.bashrc等),即可让所有该用户的会话记忆都打上user:<id>标签,供后续按标签召回/过滤。

与动态 bank 粒度的配合

从源码结构看,{user_id}与动态 bank ID 机制共享同一来源:scripts/lib/bank.py 在dynamicBankGranularity包含user段时,同样读取HINDSIGHT_USER_ID,未设置时回落为anonymous。因此环境变量有两条落点:一条是"bank 维度隔离"(bank ID 拼接为...::user段),一条是"标签维度隔离"(user:{user_id}标签),二者可独立或组合使用。

配套测试

test/tests/test_hooks.py 中有三个直接对应本条变更的用例:

  • test_retain_tag_resolves_user_id_when_env_set:设置HINDSIGHT_USER_ID=alice后,["user:{user_id}", "session:{session_id}"]解析为["user:alice", "session:sess-user-test"]
  • test_retain_tag_dropped_when_user_id_env_unset:未设置环境变量时,user:{user_id}解析为user:后被丢弃,其余标签照常发送;
  • 全标签被丢弃时,item中不再出现tags字段(retain.py将 tags 置为None,而HindsightClient.retain仅在 tags 为真值时才写入请求体)。

Unreleased 新增二:requestTimeoutSeconds覆盖 per-call HTTP 超时

CHANGELOG 的第二条 Added 说明:新增requestTimeoutSeconds配置(环境变量HINDSIGHT_REQUEST_TIMEOUT_SECONDS),用于覆盖 recall(10s)、retain(15s)与 knowledge MCP 工具所使用的 per-call HTTP 超时;默认null保持现有行为。其动机是:自托管 Hindsight 在争用(如并行 recall)时可能合法地耗时超过 10s,此时客户端不应在服务端实际成功完成的情况下向用户暴露read operation timed out。该条同时注明健康检查不受影响、仍为 5s,并修复了 issue #1575。

配置解析:settings.json 与环境变量

在 scripts/lib/config.py 中,requestTimeoutSeconds位于DEFAULTS连接配置分组,默认None;并在ENV_OVERRIDES中注册为:

"HINDSIGHT_REQUEST_TIMEOUT_SECONDS": ("requestTimeoutSeconds", int),

配置加载遵循固定优先级(见load_config文档字符串,config.py):内置默认值 → 插件自带settings.json→ 用户配置~/.hindsight/claude-code.json→ 环境变量覆盖。即settings.json里写"requestTimeoutSeconds": 30,或export HINDSIGHT_REQUEST_TIMEOUT_SECONDS=30,两者皆可。

超时覆盖的生效路径

客户端实现见 scripts/lib/client.py:

def _resolve_timeout(self, timeout: int) -> int: """Return the override if configured, otherwise the caller's timeout.""" return self.request_timeout_override if self.request_timeout_override is not None else timeout

每个调用点保留自己的语义化默认超时——recall()默认timeout=10(client.py)、retain()默认timeout=15(client.py)——而request()统一先经_resolve_timeout替换。这与 CHANGELOG 中"默认 null 保持现状,一旦配置则 recall/retain/MCP 全部被覆盖"的描述严格一致。

三个构造HindsightClient的入口都传入了同一个覆盖值:

  • scripts/recall.py:request_timeout_override=config.get("requestTimeoutSeconds")
  • scripts/retain.py:同上;
  • scripts/mcp_server.py:knowledge MCP 工具的客户端同样传入,因此 CHANGELOG 所称"knowledge MCP 工具"也在覆盖范围内。

至于"健康检查仍为 5s",从 hooks/hooks.json 看,SessionStart钩子自身的执行超时即为 5s,且session_start.py只做服务器可达性探测,不启动 daemon,与该边界相符。

Unreleased 变更:空命名空间标签自动丢弃

CHANGELOG 的 Changed 条目规定:解析后内容为空的命名空间标签(例如HINDSIGHT_USER_ID未设置时的"user:")现在会从 retain 请求中丢弃;此前这类标签会原样发送。不含:的标签不受影响。

实现位于 scripts/retain.py:

raw_tags = config.get("retainTags", []) if raw_tags: tags = [] for original in raw_tags: resolved = _resolve_template(original) if ":" in resolved and resolved.split(":", 1)[1] == "": debug_log(config, f"Dropping tag '{original}' -> '{resolved}' (empty content after ':')") continue tags.append(resolved) if not tags: tags = None else: tags = None

判定规则可以总结为:仅当"含冒号,且冒号后为空"时丢弃;session:xxxproject(无冒号)等正常保留。丢弃过程在debug模式下会输出诊断日志(debug_logHINDSIGHT_DEBUG=true时写入 stderr,见 config.py)。

这条变更与{user_id}特性是配套的:它保证了"同一份settings.json模板在用户 id 已配置与未配置的机器上都能安全运行"——已配置时得到user:alice标签,未配置时静默降级为无该标签,而不是向服务端写入一个语义为空的user:标签污染记忆检索。

0.1.0 的其余默认配置仍为当前基线

除上述变更外,Unreleased 未改动插件的默认参数,因此 settings.json 仍是理解行为基线的最佳参照:autoRecall/autoRetain默认开启,recallBudget: "mid"recallMaxTokens: 1024recallTypes: ["observation"]recallContextTurns: 1retainMode: "full-session"retainEveryNTurns: 10retainOverlapTurns: 2retainTags默认["{session_id}"];动态 bank 默认关闭(dynamicBankId: false),启用时dynamicBankGranularity["agent", "project"];daemon 相关项apiPort: 9077embedVersion: "latest"daemonIdleTimeout: 0。环境变量覆盖清单见 config.py 的 ENV_OVERRIDES,包含HINDSIGHT_API_URLHINDSIGHT_BANK_IDHINDSIGHT_RECALL_*HINDSIGHT_DAEMON_IDLE_TIMEOUT等二十余项,其中HINDSIGHT_REQUEST_TIMEOUT_SECONDS为本次 Unreleased 新增。

适用前提与验证方式

  • 适用对象:Hindsight 的 Claude Code 插件(hindsight-integrations/claude-code),连接自托管(含uvx hindsight-embeddaemon 模式)或外部 Hindsight API 的场景;
  • requestTimeoutSeconds适用前提:仅当自托管服务端在争用下响应超过默认 10s/15s 时才需要设置;对云端/低延迟部署保持默认null即可,健康检查路径不受该配置影响;
  • {user_id}适用前提:由宿主环境(shell profile 或渠道机器人)设置HINDSIGHT_USER_ID;未设置时行为是安全降级(标签丢弃),不会报错;
  • 本地验证:可运行 hindsight-integrations/claude-code/tests/ 下的 pytest 用例(如test_hooks.pytest_config.pytest_client.py)观察模板解析、标签丢弃与超时覆盖行为;配合HINDSIGHT_DEBUG=true在 stderr 查看被丢弃标签等诊断信息。

【免费下载链接】hindsightHindsight: Agent Memory That Learns项目地址: https://gitcode.com/GitHub_Trending/hindsight2/hindsight

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询