美文网首页
openssl JAVA 签名方法

openssl JAVA 签名方法

作者: chuan_bai | 来源:发表于2019-08-19 11:16 被阅读0次

    1.私钥不能直接被java使用(但可以被openssl使用),需要进行PKCS#8编码

    openssl pkcs8 -topk8 -in rsa_private_key.pem -out pkcs8_rsa_private_key.pem -nocrypt
    

    2.签名方法

        /**
         * rsa签名
         *
         * @param content    待签名的字符串
         * @param privateKey rsa私钥字符串
         * @param charset    字符编码
         * @return 签名结果
         * @throws Exception 签名失败则抛出异常
         */
        public String rsaSign(String content, String privateKey, String charset) throws SignatureException {
            try {
    
                PrivateKey priKey = getPrivateKeyFromPKCS8("RSA", new ByteArrayInputStream(privateKey.getBytes()));
    
                Signature signature = Signature.getInstance("SHA256withRSA");
                signature.initSign(priKey);
                if (StringUtils.isEmpty(charset)) {
                    signature.update(content.getBytes());
                } else {
                    signature.update(content.getBytes(charset));
                }
    
                byte[] signed = signature.sign();
                return new String(Base64.encodeBase64(signed));
            } catch (Exception e) {
                throw new SignatureException("RSAcontent = " + content + "; charset = " + charset, e);
            }
        }
    
    
        public PrivateKey getPrivateKeyFromPKCS8(String algorithm, InputStream ins) throws Exception {
            if (ins == null || StringUtils.isEmpty(algorithm)) {
                return null;
            }
    
            KeyFactory keyFactory = KeyFactory.getInstance(algorithm);
            byte[] encodedKey = StreamUtil.readText(ins).getBytes();
            encodedKey = Base64.decodeBase64(encodedKey);
            return keyFactory.generatePrivate(new PKCS8EncodedKeySpec(encodedKey));
        }
    
        /**
         * rsa验签
         *
         * @param content 被签名的内容
         * @param sign 签名后的结果
         * @param publicKey rsa公钥
         * @param charset 字符集
         * @return 验签结果
         * @throws SignatureException 验签失败,则抛异常
         */
        boolean doCheck(String content, String sign, String publicKey, String charset) throws SignatureException {
            try {
                PublicKey pubKey = getPublicKeyFromX509("RSA", new ByteArrayInputStream(publicKey.getBytes()));
    
                Signature signature = Signature.getInstance("SHA1WithRSA");
                signature.initVerify(pubKey);
                signature.update(getContentBytes(content, charset));
                return signature.verify(Base64.decodeBase64(sign.getBytes()));
            } catch (Exception e) {
                throw new SignatureException("RSA验证签名[content = " + content + "; charset = " + charset
                        + "; signature = " + sign + "]发生异常!", e);
            }
        }
    
        private PublicKey getPublicKeyFromX509(String algorithm, InputStream ins) throws NoSuchAlgorithmException {
            try {
                KeyFactory keyFactory = KeyFactory.getInstance(algorithm);
    
                StringWriter writer = new StringWriter();
                StreamUtil.io(new InputStreamReader(ins), writer);
                byte[] encodedKey = writer.toString().getBytes();
    
                // 先base64解码
                encodedKey = Base64.decodeBase64(encodedKey);
                return keyFactory.generatePublic(new X509EncodedKeySpec(encodedKey));
            } catch (IOException ex) {
                // 不可能发生
            } catch (InvalidKeySpecException ex) {
                // 不可能发生
            }
            return null;
        }
    
        private byte[] getContentBytes(String content, String charset) throws UnsupportedEncodingException {
            if (StringUtil.isEmpty(charset)) {
                return content.getBytes();
            }
    
            return content.getBytes(charset);
        }
    
    

    3.测试方法

        public static void main(String[] args) throws SignatureException {
            String content = "content";
            RasSign rasSign = new RasSign();
            String signResult = rasSign.rsaSign(content, "key", "UTF-8");
            System.out.println("signResult:" +signResult);
        }
    

    相关文章

      网友评论

          本文标题:openssl JAVA 签名方法

          本文链接:https://www.haomeiwen.com/subject/akarqctx.html