3. 可搜索加密概述:对称可搜索加密(SSE)、非对称可搜索加密
上一章我们把盲索引的概念讲清楚了。说白了,就是把明文信息藏到一个「只有钥匙才能打开的小盒子」里,然后在盒子上贴一些暴露的标签,方便你找到它。
那问题来了——谁来做这个小盒子?谁拿着钥匙去查?这就引出了可搜索加密的两大门派:对称可搜索加密(SSE)和非对称可搜索加密(也叫公钥可搜索加密,PEKS)。
我记得刚入行那会儿,老板让我调研可搜索加密方案。我在海里翻了三天,才弄明白这两个流派的核心区别。嗯,说白了就一个问题:加密和解密的钥匙,是不是同一把。
3.1 对称可搜索加密(SSE)——单钥匙方案
对称可搜索加密,你猜对了——加密数据用一把钥匙,搜索也用同一把钥匙。典型的结构是,数据拥有者自己加密数据,构建索引,然后自己拿着钥匙去搜。
我在项目中遇到过一个小型的文档加密系统,就是用的SSE方案。逻辑很直接:
- 数据拥有者把文档分词,对每个词生成一个 密文标签(就是盲索引中的那个标签)
- 把这些标签和加密文档一起上传到云服务器
- 想搜索的时候,用同一把钥匙对关键词加密,生成一个 搜索令牌()
- 服务器收到令牌,去密文标签列表里匹配,返回匹配结果
听起来很简单,对吧?但SSE有个硬伤:钥匙分发问题。数据拥有者想给别人查询权限,就必须把钥匙交出去。交出去之后,人家不但能搜,还能解密你的文档。这就很头疼了。
给你看一段简化的SSE搜索令牌生成和查询的伪代码——注意,这里只是逻辑示意,不是正经的实现。
// 生成搜索令牌
function generateSearchToken(keyword, secretKey):
// 用伪随机函数(PRF)对关键词进行加密
= PRF(secretKey, keyword)
return
// 服务端匹配
function searchOnServer(, encryptedIndex):
for each entry in encryptedIndex:
// 比较密文标签是否匹配
if slow_equals(entry.label, ):
results.append(entry.encryptedDocId)
return results
你对这段代码可能觉得眼熟——没错,跟我上一章讲的「朴素标签索引法」很像。SSE其实就是盲索引在加密搜索领域的标准实现之一。
3.2 非对称可搜索加密(PEKS)——双钥匙方案
非对称可搜索加密就有点意思了。它用 公钥 加密数据和关键词,用 私钥 生成搜索令牌。数据拥有者可以把公钥公开,谁都可以往你的加密数据库里写入数据,但只有拿着私钥的人才能搜。
为什么会这样?你想想看,在实际应用中,往往是多用户往一个数据库里写入数据的情况——比如邮件系统,Alice、Bob、Charlie都给同一台邮件服务器发加密邮件,但只有邮件拥有者(比如你自己)才能搜。
我记得有一次帮一个医疗联盟做方案,多个实验室要给协作平台的病例库写入加密报告,但只有主治医生能搜报告内容。当时我就推荐了公钥可搜索加密。
PEKS的典型流程如下:
- 发送方:用公钥加密关键词,生成可搜索密文,随加密数据一并发送给服务器
- 接收方:用私钥生成某个关键词的搜索门限(trapdoor),发给服务器
- 服务器:运行测试算法,检查门限与已有密文是否匹配
伪代码示意一下:
// 发送方:用公钥生成可搜索密文
function PEKS_Encrypt(publicKey, keyword):
r = rand()
// 典型的双线性配对运算
out = H1( e( H2(keyword), publicKey^r ) )
return out
// 接收方:用私钥生成搜索门限
function PEKS_Trapdoor(privateKey, keyword):
return H2(keyword)^privateKey
// 服务器:测试匹配
function PEKS_Test(trapdoor, ciphertext):
// 检查是否 e(trapdoor, g_r) == ciphertext
result = H1( e(trapdoor, g_r) )
return result == ciphertext
嗯,这里要注意——非对称方案的这个「测试算法」里,服务端只能做「是与否」的测试,不能提取关键词的任何信息。这是非对称方案的一个安全特性,但也是它的性能瓶颈(配对运算太耗时了)。
3.3 对称 vs 非对称:怎么选?
我直接给你一个我在项目中一直用的决策对照表:
| 维度 | 对称可搜索加密(SSE) | 非对称可搜索加密(PEKS) |
|---|---|---|
| 加密方式 | 对称加密(单钥匙) | 公钥加密(双钥匙) |
| 查询模式 | 单用户/少数信任用户 | 多用户写入 + 单用户搜索 |
| 功能扩展 | 容易支持布尔查询、范围查询 | 功能扩展较困难,典型是等值匹配 |
| 计算开销 | 极低(哈希、对称加密) | 极高(双线性配对运算) |
| 安全性 | 可达到自适应安全 | 可达到选择关键词攻击安全 |
| 适用场景 | 个人云盘搜索、企业内部文档搜索 | 加密邮件路由、多方数据上传场景 |
3.4 一张图看懂可搜索加密的流派
下面这张图我画了一下可搜索加密的两大分支。你看一下,整体脉络就很清晰了:
从图上你也能看出来,SSE和PEKS的适用场景基本是互补关系。SSE快、省资源,但是钥匙管理有隐患;PEKS灵活、支持多用户写入,但是慢得让人抓狂。
在实际选型时,我建议你不要只看里的「通用方案」,而是要问自己三个问题:
- 谁写数据?——单用户写还是多用户写?
- 谁查数据?——只有钥匙持有者查,还是多方共享查询能力?
- 延迟敏感吗?——响应时间能不能超过100ms?
对这个问题的答案,基本就决定了你该选SSE还是PEKS,或者——其实还有第三条路,也就是混合方案,这个我们在后面的章节里会详细讲。