It is easy to sign and verify in Javascript using existing libraries. However, it is confusing if we want to generate a public-private key pair in Javascript, sign a text and then verify in Flask. I already know some differences, like the default hashing in Javascript side as against python side. However, the verification in Flask side still fails.
index.html
function send(){ promise = window.crypto.subtle.generateKey(algo, true, //whether the key is extractable (i.e. can be used in exportKey) ["sign", "verify"] //can be any combination of "sign" and "verify" ); console.log(promise) promise.then( (keys) => { priv = keys.privateKey pub = keys.publicKey console.log(pub) console.log(exportCryptoKey(pub)) const pub_key_export = exportCryptoKey(pub) return pub_key_export.then( (pub_key) => { console.log("storing keys in", pub_key) signature = window.crypto.subtle.sign(algo, priv, enc_msg); signature.then((sign) => { sgn = window.btoa(ab2str(sign)); $.post("verify", {"pub": pub_key, "data": ab2str(enc_msg), "signature": sgn}, function(data){ console.log("data", data); }) }) }) }) }
verify.py
def verifySignature(signature, data, pub_key): key = RSA.importKey(pub_key) h = SHA256.new(data.encode("utf-8")) verifier = PKCS1_v1_5.new(key) return verifier.verify(h, signature)
Advertisement
Answer
btoa(raw_binary_bytes)
will encode your payload into base64 in js, this is done to prevent issues when transmitting raw bytes.
you need to call the decode method in python with base64.b64decode(encoded_bytes)
to get the actual encrypted bytes, which you can then decrypt