proxy通过拦截set/get实现属性级透明加解密,推荐用weakmap存储密文、白名单控制敏感字段,但仅防明文查看,不替代https和服务端加密。

Proxy 本身不直接加密或解密数据,但它可以拦截属性访问(get)和赋值(set)操作,在这些拦截中嵌入加解密逻辑,从而实现“透明”的属性级加解密代理。
用 Proxy 拦截 set 实现写入时加密
在 set 拦截中对原始值进行加密(如 AES、Base64 或简单异或),再存入目标对象。注意:需避免无限递归(不能直接给 target 赋值加密后的内容,除非 target 是普通对象且 key 不触发 getter/setter)。
- 推荐将加密后数据存在私有存储(如闭包 Map 或 Symbol 属性),而非直接覆盖原属性
- 使用成熟加密库(如 aes-js)处理二进制,浏览器环境慎用同步加密(阻塞主线程)
- 简单示例可用 Base64 + 密钥混淆(仅作示意,不用于生产敏感数据):
const key = 'my-secret';
const encrypt = (val) => btoa(unescape(encodeURIComponent(val + key)));
const decrypt = (str) => {
try {
return decodeURIComponent(escape(atob(str)).replace(new RegExp(key + '$'), ''));
} catch { return undefined; }
};
const handler = {
set(target, prop, value) {
target[`__enc_${prop}`] = encrypt(value);
return true;
},
get(target, prop) {
if (prop.startsWith('__enc_')) return target[prop];
const encKey = `__enc_${prop}`;
return target[encKey] ? decrypt(target[encKey]) : undefined;
}
};
const safeUser = new Proxy({ name: 'Alice' }, handler);
safeUser.password = '123456'; // 写入即加密
console.log(safeUser.password); // '123456'(自动解密)
区分敏感字段,按需加解密
不是所有属性都需要加密。可在 handler 中维护一个白名单(如 ['password', 'token', 'idCard']),只对指定字段启用加解密逻辑,其余属性透传。
Java JDK 25 来自 OpenJDK 官方归档,版本为 JDK 25,本条下载地址已指向官方 Windows x64 zip 安装包直链,适合调试旧项目或兼容旧版 Java 运行环境。
- 避免对函数、日期、数组等复杂类型做简单字符串加密——需序列化前判断类型,或统一转 JSON 字符串再加密
- 若字段值为 undefined / null,加密结果可能异常,建议在 encrypt/decrypt 中做空值保护
- 可结合 Reflect.set/get 保证默认行为,仅对敏感字段定制逻辑
配合 WeakMap 隐藏加密存储,避免污染目标对象
用 WeakMap 存储加密数据,既不暴露密文到目标对象上,又能随目标对象回收内存,更安全干净。
- WeakMap 的 key 必须是对象,所以 proxy 的 target 应为 object(不能是 primitive)
- 每个 proxy 实例对应一个 WeakMap,适合单对象代理;多对象可封装成工厂函数
- 示例中加密值不暴露在 target 上,外部无法通过
obj.__enc_xxx窥探
注意事项与局限性
Proxy 加解密是运行时行为,不改变原始数据结构,也不提供传输加密或存储加密保障。它本质是“访问控制层”,不是安全边界。
- 加密密钥硬编码在 JS 中,前端无法真正保密——仅防低阶明文查看,不可替代 HTTPS 和服务端加密
- 无法拦截 for...in、Object.keys() 等枚举操作,敏感字段名仍可见(除非同时用 Object.defineProperty 配合 configurable: false)
- JSON.stringify() 默认忽略 Proxy 行为,需自定义 toJSON 或使用 structuredClone(含 handler)
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南










