【问题标题】:How to digitally Sign data using p8 form private key in PHP and Verify it using Public key如何在 PHP 中使用 p8 表单私钥对数据进行数字签名并使用公钥对其进行验证
【发布时间】:2021-03-04 07:34:36
【问题描述】:

我使用 Java 创建了一个 P8 格式的私钥和签名数据,并尝试使用 PHP 中的公钥验证它失败了。

我使用 openssl 命令创建了 p8 文件

openssl pkcs8 -topk8 -inform PEM -outform DER -in myprivate.in.key -out myprivate.in.key.p8 -nocrypt

并使用

签署了一个Json数据
public byte[] sign(String data, String privateKeyFilePath) throws InvalidKeyException, NoSuchAlgorithmException, InvalidKeySpecException, IOException, SignatureException {
        byte[] returnVal = null;

            Signature signature = Signature.getInstance(RSA_SHA_256);
            PrivateKey privateKey = getPrivateKey(privateKeyFilePath);
            signature.initSign(privateKey);
            signature.update(data.getBytes());
            returnVal = signature.sign();

        return returnVal;
    }

但是当我尝试使用 openssl 命令在 PHP 中使用公共证书验证它时,它失败了

$cert_path = file_get_contents(storage_path('certificates/my_in.cer'));
        $pub_key = openssl_get_publickey($cert_path);
        $keyData = openssl_pkey_get_details($pub_key);
        $pub_key = $keyData['key'];

        // $verify = openssl_x509_verify()
        $verify = openssl_verify($dataSigned, $signatureDecoded, $pub_key, 'sha256WithRSAEncryption');

我做错了什么,还有一种方法可以在 php 中使用 p8 密钥对数据进行签名!

【问题讨论】:

    标签: php openssl


    【解决方案1】:

    按照这个过程,一切正常。也许对你有用?

    使用 openssl 生成密钥:

    # Generate PK
    openssl genpkey -algorithm RSA \
        -pkeyopt rsa_keygen_bits:2048 \
        -pkeyopt rsa_keygen_pubexp:65537 | \
      openssl pkcs8 -topk8 -nocrypt -outform der > rsa-2048-private-key.p8
    
    # Convert your PKCS#8 file to a plain private key
    openssl pkcs8 -nocrypt -in rsa-2048-private-key.p8 -inform DER -out rsa-2048-private-key.pem
    
    # Generate pub key
    openssl rsa -in rsa-2048-private-key.pem -pubout -out rsa-2048-public-key.pem
    

    测试pkey并签名数据(index.php):

    <?php
    
    $privateKeyFile="file://".__DIR__.DIRECTORY_SEPARATOR."rsa-2048-private-key.pem";
    $publicKeyFile="file://".__DIR__.DIRECTORY_SEPARATOR."rsa-2048-public-key.pem";
    
    // Data to sign
    $data = 'Hello world!';
    
    // Test on get private key
    $pkeyid = openssl_pkey_get_private($privateKeyFile);
    
    if ($pkeyid === false) {
        var_dump(openssl_error_string());
    }else{
        var_dump($pkeyid);
    }
    
    // Sign data
    openssl_sign($data, $signature, $pkeyid);
    
    // Free memory
    openssl_free_key($pkeyid);
    
    // Read pub key
    $pubkeyid = openssl_pkey_get_public($publicKeyFile);
    
    // Test if sign is ok
    $ok = openssl_verify($data, $signature, $pubkeyid);
    if ($ok == 1) {
        echo "Sign OK";
    } elseif ($ok == 0) {
        echo "Sign NOK";
    } else {
        echo "Sign check error";
    }
    // Free memory
    openssl_free_key($pubkeyid);
    

    php -S localhost:8000,http://localhost:8000,返回:

    resource(2) of type (OpenSSL key) Sign OK
    

    【讨论】:

      猜你喜欢
      • 2014-01-13
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2022-08-06
      • 2019-07-02
      • 1970-01-01
      • 1970-01-01
      • 2018-11-26
      相关资源
      最近更新 更多