DIDComm 要解决的问题
当智能体需要跨组织通信时,它们如何安全地交换消息?
传统方案:
- VPN 隧道 —— 合并网络(复杂,暴露基础设施)
- HTTPS API —— 需要双方都暴露端点(防火墙问题、TLS 管理)
- 消息代理 —— 共享 Kafka/RabbitMQ(紧耦合,单点故障)
- 邮件 —— 非端到端加密,没有身份验证保障
问题:
- 没有原生加密 —— TLS 只保护传输层,而非端到端
- 紧耦合 —— 双方必须就基础设施达成一致
- 没有身份验证 —— 很难证明”这条消息确实来自智能体 A”
- 路由复杂性 —— 智能体 A 如何找到智能体 B 的端点?
DIDComm 解决了这个问题:使用 DID 实现加密且经过身份验证的消息传递——智能体无需共享基础设施即可点对点通信。
什么是 DIDComm?
DIDComm(去中心化标识符通信) 是一种协议,用于在以 DID 标识的实体之间进行安全、私密的消息传递。
关键属性:
- 端到端加密 —— 只有发送方和接收方能读取消息
- 可验证身份 —— 你能确认消息确实来自声称的 DID
- 异步 —— 像邮件一样工作(存储转发),而不仅仅是请求/响应
- 传输无关 —— 可通过 HTTP、WebSocket、蓝牙、二维码等方式发送
- 元数据私密 —— 路由过程不会暴露消息内容
类比: DIDComm 之于智能体,就像 Signal/WhatsApp 之于人类——但它是去中心化的,无需中央服务器。
DIDComm 的工作原理
1. 发现接收方的端点
智能体 A 想给智能体 B 发送消息:
// 解析智能体 B 的 DID 以获取其服务端点
const didDocB = await resolve('did:webvh:bankB.com:agent-99')
// DID 文档中包含服务端点
const endpoint = didDocB.service.find(s => s.type === 'DIDCommMessaging').serviceEndpoint
// → "https://bankB.com/didcomm"
2. 加密消息
智能体 A 为智能体 B 加密消息:
// 消息载荷
const message = {
type: 'https://didcomm.org/trade/1.0/execute',
from: 'did:webvh:bankA.com:agent-42',
to: ['did:webvh:bankB.com:agent-99'],
body: {
symbol: 'AAPL',
quantity: 100,
price: 150.00
}
}
// 使用智能体 B 的公钥加密
const encryptedMessage = await encrypt(message, didDocB.keyAgreement)
// 现在只有智能体 B 能解密它
3. 发送消息
智能体 A 将加密消息发送到智能体 B 的端点:
await fetch(endpoint, {
method: 'POST',
headers: { 'Content-Type': 'application/didcomm-encrypted+json' },
body: JSON.stringify(encryptedMessage)
})
4. 解密消息
智能体 B 接收并解密消息:
// 智能体 B 使用自己的私钥解密
const decryptedMessage = await decrypt(encryptedMessage, privateKeyB)
console.log(decryptedMessage.from) // 'did:webvh:bankA.com:agent-42'
console.log(decryptedMessage.body) // { symbol: 'AAPL', quantity: 100, ... }
// 智能体 B 验证发送方的签名
const isAuthentic = await verify(decryptedMessage, didDocA.verificationMethod)
// → true
DIDComm 消息格式
明文消息
{
"type": "https://didcomm.org/trade/1.0/execute",
"id": "urn:uuid:abc-123",
"from": "did:webvh:bankA.com:agent-42",
"to": ["did:webvh:bankB.com:agent-99"],
"created_time": "2026-07-21T19:00:00Z",
"body": {
"symbol": "AAPL",
"quantity": 100,
"price": 150.00
}
}
加密消息(JWE)
{
"protected": "eyJhbGciOiJFQ0RILUVTK0EyNTZLVyIsImVuYyI6IkEyNTZHQ00i...",
"recipients": [{
"header": { "kid": "did:webvh:bankB.com:agent-99#key-agreement-1" },
"encrypted_key": "..."
}],
"iv": "...",
"ciphertext": "...",
"tag": "..."
}
只有智能体 B 能解密 ciphertext——即使是中间路由节点也无法读取它。
DIDComm 与传统消息传递方式对比
| 维度 | HTTPS API | 消息代理(Kafka) | DIDComm |
|---|---|---|---|
| 加密 | 仅 TLS(传输层) | 无(除非自行添加) | 端到端加密(原生) |
| 身份验证 | API 密钥/JWT | 无(除非自行添加) | DID 签名(原生) |
| 基础设施 | 双方都需暴露端点 | 需要共享代理 | 无需共享基础设施 |
| 路由 | DNS/IP 地址 | Topic/分区 | DID 解析 |
| 元数据隐私 | 请求头可见 | 请求头可见 | 加密路由 |
真实应用场景
1. 跨组织智能体通信
场景: A 银行的智能体与 B 银行的智能体进行谈判。
流程:
// 智能体 A (A 银行) 发送加密的交易提案
const proposal = {
type: 'https://didcomm.org/trade/1.0/propose',
from: 'did:webvh:bankA.com:agent-42',
to: ['did:webvh:bankB.com:agent-99'],
body: {
symbol: 'AAPL',
quantity: 100,
proposedPrice: 150.00
}
}
await didcomm.send(proposal)
// 智能体 B 接收、解密并回应
const response = {
type: 'https://didcomm.org/trade/1.0/accept',
from: 'did:webvh:bankB.com:agent-99',
to: ['did:webvh:bankA.com:agent-42'],
thid: proposal.id, // 线程 ID (链接到原始提案)
body: { accepted: true, finalPrice: 150.00 }
}
await didcomm.send(response)
核心优势: 无需 VPN,无需共享消息代理——只需加密的点对点消息传递。
2. 智能体交接(多组织工作流)
场景: 保险理赔从智能体 A(承保人)→ 智能体 B(理算员)→ 智能体 C(付款方)依次传递。
流程:
// 承保智能体交接给理算智能体
const handoff = {
type: 'https://didcomm.org/claim/1.0/handoff',
from: 'did:webvh:insurer.com:underwriter-agent',
to: ['did:webvh:insurer.com:adjuster-agent'],
body: {
claimId: 'claim-12345',
status: 'approved-for-adjustment',
attachments: [vcProofOfApproval]
}
}
await didcomm.send(handoff)
// 理算智能体处理后,交接给付款智能体
const payment = {
type: 'https://didcomm.org/claim/1.0/pay',
from: 'did:webvh:insurer.com:adjuster-agent',
to: ['did:webvh:bank.com:payment-agent'],
thid: handoff.id,
body: {
claimId: 'claim-12345',
amount: 5000,
recipient: 'patient-iban-...'
}
}
await didcomm.send(payment)
核心优势: 端到端审计追踪——每一次交接都经过身份验证、加密,并可通过线程 ID 关联。
3. 元数据私密路由
场景: 智能体 A 通过中继节点 M 向智能体 B 发送消息(智能体 B 处于防火墙后)。
流程:
1. 智能体 A 为智能体 B 加密消息
2. 智能体 A 将其包装在发往中继节点 M 的转发消息中
3. 中继节点 M 只能看到外层信封 (无法读取内层消息)
4. 中继节点 M 转发给智能体 B
5. 智能体 B 解密并读取消息
代码:
// 内层消息 (为智能体 B 加密)
const innerMessage = await encrypt(message, agentB.publicKey)
// 外层信封 (面向中继节点 M)
const forwardMessage = {
type: 'https://didcomm.org/routing/2.0/forward',
to: ['did:webvh:mediator.com'],
body: {
next: 'did:webvh:bankB.com:agent-99',
payloads: [innerMessage]
}
}
await didcomm.send(forwardMessage)
核心优势: 中继节点无需读取内容即可完成路由——保护元数据隐私。
Affinidi 技术栈中的 DIDComm
Affinidi Messaging 提供 DIDComm 基础设施:
import { DIDComm } from '@affinidi/affinidi-messaging'
// 初始化
const comm = new DIDComm({
did: 'did:webvh:yourcompany.com:agent-42',
privateKey: '...'
})
// 发送加密消息
await comm.send({
to: 'did:webvh:partner.com:agent-99',
type: 'https://example.com/protocol/1.0/message',
body: { data: 'secret payload' }
})
// 接收消息
const messages = await comm.receive()
console.log(messages[0].body) // 自动解密
Agent Gateway 在智能体之间路由 DIDComm 消息:
// Agent Gateway 充当中继节点
agentGateway.on('didcomm-message', async (envelope) => {
// 验证发送方
const senderDID = envelope.from
const authorized = await trustRegistry.query({ agent: senderDID })
if (!authorized) throw new Error('未授权的发送方')
// 转发给目标智能体
await didcomm.forward(envelope)
})
协议模式
请求—响应
// 请求
const request = {
type: 'https://example.com/protocol/1.0/request',
id: 'urn:uuid:req-123',
body: { query: 'What is the price of AAPL?' }
}
await didcomm.send(request)
// 响应 (通过 pthid 关联)
const response = {
type: 'https://example.com/protocol/1.0/response',
pthid: 'urn:uuid:req-123', // 父级线程 ID
body: { answer: '$150.00' }
}
多步骤工作流(线程)
// 步骤 1: 提案
const proposal = {
type: 'https://example.com/trade/1.0/propose',
id: 'urn:uuid:thread-1',
body: { symbol: 'AAPL', quantity: 100 }
}
// 步骤 2: 还价 (通过 thid 关联)
const counter = {
type: 'https://example.com/trade/1.0/counter',
thid: 'urn:uuid:thread-1',
body: { proposedPrice: 151.00 }
}
// 步骤 3: 接受 (通过 thid 关联)
const accept = {
type: 'https://example.com/trade/1.0/accept',
thid: 'urn:uuid:thread-1',
body: { finalPrice: 151.00 }
}
快速上手
面向开发者
发送一条 DIDComm 消息:
npm install @affinidi/affinidi-messaging
import { DIDComm } from '@affinidi/affinidi-messaging'
const comm = await DIDComm.create({
did: 'did:webvh:yourcompany.com:agent-42',
privateKey: process.env.AGENT_PRIVATE_KEY
})
await comm.send({
to: 'did:webvh:partner.com:agent-99',
type: 'https://example.com/protocol/1.0/hello',
body: { message: 'Hello from Agent 42!' }
})
面向架构师
何时应使用 DIDComm:
- ✅ 跨组织智能体通信(无需共享基础设施)
- ✅ 需要端到端加密
- ✅ 异步工作流(存储转发)
- ✅ 元数据隐私(路由过程不暴露内容)
何时不应使用:
- ❌ 高频流式传输(DIDComm 是基于消息的,而非流式传输)
- ❌ HTTPS API 更简单够用的内部系统
- ❌ 向大量接收方广播(DIDComm 是点对点的)
延伸阅读
规范:
Affinidi 文档:
相关深度解析:
相关解决方案:
- 跨组织智能体信任 —— DIDComm 支持跨边界的加密通信