首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >编解码SHA256WITHECDSA - nodeJS

编解码SHA256WITHECDSA - nodeJS
EN

Stack Overflow用户
提问于 2022-01-10 16:30:07
回答 1查看 241关注 0票数 0

我正试图用SHA256withECDSA解码/编码一个签名。我有一个运行良好的Java代码:

代码语言:javascript
运行
复制
public void verify() throws Exception {
    Signature ecdsaVerify = Signature.getInstance("SHA256withECDSA"));
    EncodedKeySpec publicKeySpec = new X509EncodedKeySpec(Base64.getDecoder().decode("your public key goes here"));
    KeyFactory keyFactory = KeyFactory.getInstance("EC");
    PublicKey publicKey = keyFactory.generatePublic(publicKeySpec);
    ecdsaVerify.initVerify(publicKey);

    ecdsaVerify.update("All the webhook field values (only the values) concatenated together using a semicolon ;".getBytes("UTF-8"));
    boolean result = ecdsaVerify.verify(Base64.getDecoder().decode("Signature to verify")); //Must return true
} 

但我需要nodejs的这个解决方案。当我在nodejs中创建一个base64缓冲区时,它将得到与Java代码不同的结果。目前我使用的是密码‘s& jwa npm。

编辑:

这是我的nodejs代码:

代码语言:javascript
运行
复制
var jwa = require("jwa");

const verifySignature = () => {
let public_key = Buffer.from("public key here", "base64");
let signature = Buffer.from("Signature_here", "base64");
let payload = "data here seperated by semicolon";
let ecdsa = jwa("ES256");
let verify = ecdsa.verify(payload, signature, public_key);
}
verifySignature();
EN

回答 1

Stack Overflow用户

发布于 2022-01-10 19:48:43

JWA实现了在JOSE中使用的算法,特别是对于ECDSA,它使用了在P1363中定义的签名格式(又名编码),它只包含连接在一起的固定长度R和S;参见https://datatracker.ietf.org/doc/html/rfc7518#section-3.4的步骤2和3。这不是大多数其他标准所使用的格式,尤其是Java,Java是由两个整数值组成的ASN.1 DER编码序列,它们都是带有标记和长度前缀的可变长度(all)。

您根本不需要JWA;内置的'crypto‘具有您需要的功能:

代码语言:javascript
运行
复制
import java.security.KeyFactory;
import java.security.Signature;
import java.security.spec.X509EncodedKeySpec;
import java.util.Base64;

public class SO70655734 {
  public static void main (String[] args) throws Exception {
    String data = "some;test;data";
    String pubkey = "MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEyOFORyCVCxX+W4QZevzH6skTbp2lVDtRLV0+7ypHjX26wFtSWSe4MTI0GZjIKDOAIT8KpbqH8HXI6Wo5S6/6hg==";
    String sig = "MEQCICDLwztlKOXmQLuDJ0Hh96gGAT2/wsm2ymw3CDxSDnB3AiAK7eR8+C6g/zw5TmXUX0K/pV5kjIJTCieIkQXzH30WYA==";

    Signature ecdsa = Signature.getInstance("SHA256withECDSA");
    ecdsa.initVerify(KeyFactory.getInstance("EC").generatePublic(
      new X509EncodedKeySpec(Base64.getDecoder().decode(pubkey)) ));
    ecdsa.update(data.getBytes("UTF-8")); // or StandardCharsets.UTF_8 
    System.out.println(ecdsa.verify(Base64.getDecoder().decode(sig)));
  }
}
-> true

const crypto = require('crypto');

const data = "some;test;data";
const pubkey = "-----BEGIN PUBLIC KEY-----\n"
  + "MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEyOFORyCVCxX+W4QZevzH6skTbp2lVDtRLV0+7ypHjX26wFtSWSe4MTI0GZjIKDOAIT8KpbqH8HXI6Wo5S6/6hg==\n"
  + "-----END PUBLIC KEY-----\n";
const sig = "MEQCICDLwztlKOXmQLuDJ0Hh96gGAT2/wsm2ymw3CDxSDnB3AiAK7eR8+C6g/zw5TmXUX0K/pV5kjIJTCieIkQXzH30WYA==";

var ecdsa = crypto.createVerify('SHA256');
ecdsa.update(data,'utf8');
console.log( ecdsa.verify(pubkey, sig,'base64') );
-> true

注意: nodejs的最新版本可以采用DER格式的公键(没有添加开始/结束行,而是将base64转换为二进制),但是我最方便的测试系统只有8.10.0,所以我采用了更兼容的老方法。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/70655734

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档