Web Crypto API JWK 在 Python 中的用法
Web Crypto API JWK usage in Python
我正在开发一个P2P基础设施,它将拥有来自一组不同应用程序的数据,通过网络分发。这个P2P叠加层由一组Python扭曲服务器组成。
我需要为每个应用程序的每个用户保证存储数据的安全性和隐私性。因此,我使用 Web 加密 API 在 Web 应用程序的客户端生成 RSA 密钥对。RSA 密钥对也将存储在 P2P 覆盖网络中。因此,我在客户端使用用户密码的派生私钥进行密码加密。
此外,我正在使用jwk到pem模块将JWK公钥转换为PEM密钥,用于Python Cryptography库(PyCrypt或m2Crypto)。
最后,我必须保证包含这些凭据的消息以及 用户数据 ,保持其完整性。因此,在客户端,我使用用户的私钥对这些数据进行签名。
我将 ArrayBuffer 类型的数据和签名发送到服务器,以 base64 编码。
function signData(private_key, data, callback){
var dataForHash = str2ab(JSON.stringify(sortObject(data)));
computeSHA(dataForHash, "SHA-256", function(hash){
signRSA(private_key, hash, function(data){
callback(data.buffer.b64encode(), dataForHash.b64encode());
});
});
}
function computeSHA(data, mode, callback){
window.crypto.subtle.digest(
{
name: mode,
},
data
)
.then(function(hash){
callback(new Uint8Array(hash).buffer);
})
.catch(function(err){
console.error(err);
});
}
function signRSA(private_key, data, callback){
window.crypto.subtle.sign(
{
name: "RSASSA-PKCS1-v1_5",
},
private_key,
data
)
.then(function(signature){
callback(new Uint8Array(signature));
})
.catch(function(err){
console.error(err);
});
}
ArrayBuffer.prototype.b64encode = function(){
return btoa(String.fromCharCode.apply(null, new Uint8Array(this)));
};
之后,当 Python 服务器收到此 http 请求时,它会从 base64 解码数据和签名。
dataForHash = base64.b64decode(dataReceived['data'])
signature = base64.b64decode(dataReceived['signature'])
为了验证签名,需要公钥。因此:
data = utils.byteify(json.loads(dataForHash.decode("utf-16")))
pub_key = base64.b64decode(data['pub_key']) # Get PEM Public Key
(utils.byteify() 将 unicode 字符串转换为常规字符串)
验证签名:
Authentication.verifySignature(signature, dataForHash, pub_key)
方法定义:
from Crypto.Signature import PKCS1_v1_5
from Crypto.Hash import SHA256
from Crypto.PublicKey import RSA
def verifySignature(signature, data, pub_key):
key = RSA.importKey(pub_key)
h = SHA256.new(data)
verifier = PKCS1_v1_5.new(key)
return verifier.verify(h, signature)
但是,签名验证返回 False。我也尝试使用 m2crypto 库,但它返回 0。
我设法找到了问题。
尽管在 Python (PyCrypto) 中,sign 函数应该接收要签名的数据的哈希值,但使用 Web Cryptography API,sign 方法会在签名之前对接收到的数据应用哈希函数。
因此,JS 中的数据被哈希处理了两次,一次是在调用 sign 方法之前,另一次是在创建签名之前在 sign 方法中。
function signData(private_key, data, callback){
var dataForHash = str2ab(JSON.stringify(sortObject(data)));
signRSA(private_key, dataForHash, function(data){
callback(data.buffer.b64encode(), dataForHash.b64encode());
});
}
ArrayBuffer.prototype.b64encode = function(){
return btoa(String.fromCharCode.apply(null, new Uint8Array(this)));
};
String.prototype.b64decode = function(){
var binary_string = window.atob(this);
var len = binary_string.length;
var bytes = new Uint8Array(new ArrayBuffer(len));
for (var i = 0; i < len; i++) {
bytes[i] = binary_string.charCodeAt(i);
}
return bytes;
};
通过此修改,python 中的验证现在返回 True。
- 从桌面读取python文件时高亮显示代码
- python-selenium-点击上升链接
- python到“;流“;字典处理
- 什么's本地node.js服务器和python简单http服务器之间的区别
- Meteor如何运行服务器端python脚本
- 原型和用法 Javascript
- 回调函数在python代码中离线
- 将数组从ajax传递到python(Tornado)
- 为什么在python中使用异常比javascript更容易接受
- 如何让Meteor应用程序使用python脚本写入数据库
- 在IntelliJ IDEA中,如何将JS文件从“;查找用法“;使用TypeScript时的结果
- 如何访问Web2py'中python代码中的JavaScript变量;s视图
- 限制npm依赖模块's require(隔离)的用法
- 如何在python中将JavaScriptHTML渲染为HTML
- 在python中,我如何才能恢复被隐藏的元素的内容
- 用beautifulsoup-python调用onclick事件
- Python在spark中绘制地图
- 使用.format在一些HTML代码中插入文本,会出现错误(Python)
- 在selenium python中执行脚本
- Web Crypto API JWK 在 Python 中的用法