---
type: study
created: 2026-08-11
updated: 2026-08-11
sensitivity: private
status: active
tags:
  - study
  - langchain
  - typescript
  - middleware
  - runtime
  - guardrails
  - hitl
topic: LangChain TypeScript Middleware、Context、Runtime、Guardrails 与 HITL
sources:
  - https://docs.langchain.com/oss/javascript/langchain/context-engineering.md
  - https://docs.langchain.com/oss/javascript/langchain/guardrails.md
  - https://docs.langchain.com/oss/javascript/langchain/human-in-the-loop.md
  - https://docs.langchain.com/oss/javascript/langchain/middleware
  - https://docs.langchain.com/oss/javascript/langchain/middleware/built-in.md
  - https://docs.langchain.com/oss/javascript/langchain/middleware/custom.md
  - https://docs.langchain.com/oss/javascript/langchain/middleware/overview.md
  - https://docs.langchain.com/oss/javascript/langchain/runtime.md
last_verified: 2026-08-11
---
# LangChain TypeScript：Middleware、Context、Runtime 与 HITL

## Context engineering 的核心

Agent 质量往往受“模型在某一步看到了什么”支配，而不只是 model 大小。应分别设计三类数据：

| 数据 | 生命周期 | 典型载体 |
|---|---|---|
| Runtime context | 单次调用稳定、通常只读 | `contextSchema` + invoke 的 `{ context }` |
| Short-term state | 同一 thread 持久、每一步演化 | agent state + checkpointer |
| Long-term memory | 跨 thread/会话共享 | store 的 namespace + key |

另有 model context：真正送入当前模型调用的 prompt、messages、tools 与 schemas。Middleware 的价值就是在适当生命周期读取数据，并只把本步需要的信息投影到 model context。

## Runtime：依赖注入，不是全局变量袋

工具和 middleware 可通过 runtime 读取：

- `context`：用户/租户、数据库句柄、feature flags 等调用级依赖；
- `state`：当前 thread 的 checkpointed 数据；
- `store`：长期记忆；
- `streamWriter`：自定义进度；
- `executionInfo`：thread ID、run ID 等执行身份；
- `serverInfo`：LangGraph Server 上的 assistant、authenticated user 等服务端信息。

`serverInfo` 在本地非 Agent Server 环境为 `null`。`executionInfo`/`serverInfo` 要求 **`deepagents >= 1.9.0` 或 `@langchain/langgraph >= 1.2.8`**。认证逻辑必须处理“字段不存在”和“本地运行”两条分支，不能从 prompt 中的 user ID 推断身份。

TypeScript 的 `contextSchema` 若包含必填字段，`agent.invoke` 会在编译期要求传入；这能减少漏参，但外部请求仍需运行时校验。

## Middleware 生命周期与顺序

Node-style hooks：

- `beforeAgent` / `afterAgent`：整个 run 前后；
- `beforeModel` / `afterModel`：每次 model call 前后。

Wrap hooks：

- `wrapModelCall(request, handler)`：模型选择、prompt、tools、retry/fallback、响应处理；
- `wrapToolCall(request, handler)`：鉴权、参数处理、timeout、重试、错误转换、审计。

多 middleware 的顺序是：before hooks 按数组正序，after hooks 逆序；wrap 形成洋葱模型，第一个 middleware 位于最外层。顺序会改变语义，例如 PII redaction 应先于日志；timeout 与 retry 的内外关系决定“每次重试超时”还是“整个操作总超时”。应把顺序作为测试契约。

Node hook 返回 state update；wrap hook 要更新 state 时返回 `Command`。`StateSchema` 可以用 `ReducedValue` 描述合并；以下划线开头的私有字段不会出现在最终 agent 结果中，但仍可能存在运行内存/trace，不能当加密机制。

`canJumpTo` 允许 middleware 跳到 model、tools 或 end。Jump 是控制流能力，应避免在多个 middleware 中隐式竞争。

## 自定义 middleware 的选择

简单、无配置逻辑可直接使用 hook factory；需要共享状态、复杂配置、多个 hooks 或可复用包时用 `createMiddleware`。典型生产场景：

- 动态 system prompt / model routing；
- 按租户过滤 tools；
- model/tool retry、fallback、circuit breaker；
- 预算、调用次数和 token 限制；
- 输入/输出审核与 PII 处理；
- trace tags、业务指标和自定义 stream projection。

Middleware 注册 stream transformer 要求 **`langchain@1.4.3+`**。Transformer 应是可组合、顺序明确、支持取消的异步管道。

## 预置 middleware 地图

| 类别 | 能力 | 边界 |
|---|---|---|
| Context | summarization、context editing | 压缩有损；阈值依赖 model profile 或显式 token 配置 |
| Human control | HITL | 必须 checkpointer + thread；恢复需原 checkpoint |
| Budgets | model/tool call limit、to-do list | 需要定义 run/thread 计数语义 |
| Reliability | model fallback、model/tool retry、tool error | 有限重试；副作用工具必须幂等 |
| Safety | PII detection/redaction/block、guardrails | 规则与模型审核互补；日志链路也要脱敏 |
| Tool selection | LLM tool selector、provider tool search/emulator | 额外模型调用或 provider 依赖可能增加成本 |
| Deep-agent harness | filesystem、subagent | 来自 `deepagents`；backend、sandbox、持久性和权限另行设计 |

“production-ready”表示实现可配置，不表示默认配置自动满足业务合规、SLA 和安全要求。

## Guardrails：确定性规则优先

Guardrail 可作用于输入、模型前后、工具前后：

- 规则型检查适合权限、允许列表、金额/路径限制、schema、正则 PII；
- 模型型审核适合语义风险，但有延迟、费用和误判；
- 高风险副作用最终由工具服务端再鉴权，middleware 不是唯一防线。

处理策略可以 block、redact/mask、替换安全回复、抛出错误或 interrupt。必须明确用户可见错误、内部审计、重试和恢复路径，避免 redaction 后数据仍从 trace/异常/自定义事件泄漏。

## HITL 的状态机

`humanInTheLoopMiddleware` 按 `interruptOn` 对工具配置审批。每个工具可允许：

- `allowAccept`：批准原动作；
- `allowEdit`：修改参数后执行；
- `allowRespond`：不执行工具，直接提供反馈。

必要条件：checkpointer、稳定 `thread_id`、持久保存 interrupt/checkpoint、恢复时使用 `Command({ resume: ... })`。同一 turn 有多个被暂停工具时，每个 action 都要对应一项 decision，顺序和数量必须一致。

安全边界：

- `edit` 后必须重新 schema 校验和鉴权；
- 审批 UI 只能把服务端返回的允许动作展示给有权 reviewer；
- 执行恢复可能重复到达，副作用需要幂等 key；
- checkpoint/store 要有租户隔离、保留期和审计；
- timeout/拒绝/无人审批必须有终态。

**重要 JS 差异：条件式 `when`/conditional interrupt 当前仅 Python 支持。** TypeScript 页面虽混入 `interrupt_on`、v2 Python 风格说明，JS 实现应使用实际 `interruptOn` 与上述 allow 选项，不要宣称具备 Python-only 条件策略。

## 路由与文档边界

`/oss/javascript/langchain/middleware` 是可点击别名，当前 308 到 `/middleware/overview`，所以 sources 同时记录别名和正文；它不代表额外的 middleware 语义。文档数处混入 Python 参数名/代码块，属于模板复用缺陷，不能作为 TypeScript API 契约。

## 逐页覆盖

| 页面 | 学习结论 |
|---|---|
| Context engineering | runtime context、state、store 与 model context 的生命周期和读写方式。 |
| Middleware overview | agent/model/tool hooks、控制流、顺序与常见用途。 |
| Built-in middleware | summary、HITL、limits、fallback/retry、PII、todo、tool selection、filesystem、subagent。 |
| Custom middleware | hook/createMiddleware、StateSchema、Command、stream transformer 与 context typing。 |
| Runtime | context/state/store/stream writer、executionInfo/serverInfo 及版本要求。 |
| Guardrails | PII、规则/模型检查、block/redact/HITL 和分层安全。 |
| Human-in-the-loop | interrupt policy、accept/edit/respond、checkpoint 和恢复协议；conditional JS 缺口。 |

## 延伸

- [[05-TypeScript-MCP-Multi-Agent-Retrieval-and-Memory]]
- [[07-TypeScript-Production-Testing-and-Migration]]
- [Python 对照](../Python/04-Middleware-Context-and-Runtime.md)

