openssl_sign(): supplied key param cannot be coerced into a private key

PHP RSA error
openssl_sign(): supplied key param cannot be coerced into a private key 

Reason:
Local test is normal, server error
Using test data and test keys, both local and server are normal
This situation has nothing to do with the PHP and OPENSSL versions (have recompiled PHP and OPENSSL, wasting a lot of time)

Solution:
RSA keys generally have a fixed line break format. Is this caused by this situation? Try this format, the problem is solved smoothly

Private Key

$str ='Your private key (changed to a line)';
$str = chunk_split($str, 64, "\n");
$key = "-----BEGIN RSA PRIVATE KEY-----\n$str-----END RSA PRIVATE KEY-----\n";
$signature = '';
if (openssl_sign($data, $signature, $key, OPENSSL_ALGO_MD5)) {
    echo base64_encode($signature);
}

Public Key

$data ='content';
$str ='Your public key (changed to a line)';
$str = chunk_split($str, 64, "\n");
$key = "-----BEGIN PUBLIC KEY-----\n$str-----END PUBLIC KEY-----\n";
$signature = "";
if (openssl_verify(base64_decode($data), $signature, $key, OPENSSL_ALGO_MD5) == 1) {
    echo $signature;
}

Case:
http://php.net/manual/en/function.openssl-sign.php Official case.
The official public key private key format is too standard, so it needs to be modified.
Because the public key private key we got is probably one line

$data = "is really good..";
$private_key = <<<EOD
-----BEGIN RSA PRIVATE KEY-----
MIIBOgIBAAJBANDiE2+Xi/WnO+s120NiiJhNyIButVu6zxqlVzz0wy2j4kQVUC4Z
RZD80IY+4wIiX2YxKBZKGnd2TtPkcJ/ljkUCAwEAAQJAL151ZeMKHEU2c1qdRKS9
sTxCcc2pVwoAGVzRccNX16tfmCf8FjxuM3WmLdsPxYoHrwb1LFNxiNk1MXrxjH3R
6QIhAPB7edmcjH4bhMaJBztcbNE1VRCEi/bisAwiPPMq9/2nAiEA3lyc5+f6DEIJ
h1y6BWkdVULDSM+jpi1XiV/DevxuijMCIQCAEPGqHsF+4v7Jj+3HAgh9PU6otj2n
Y79nJtCYmvhoHwIgNDePaS4inApN7omp7WdXyhPZhBmulnGDYvEoGJN66d0CIHra
I2SvDkQ5CmrzkW5qPaE2oO7BSqAhRZxiYpZFb5CI
-----END RSA PRIVATE KEY-----
EOD;
$public_key = <<<EOD
-----BEGIN PUBLIC KEY-----
MFwwDQYJKoZIhvcNAQEBBQADSwAwSAJBANDiE2+Xi/WnO+s120NiiJhNyIButVu6
zxqlVzz0wy2j4kQVUC4ZRZD80IY+4wIiX2YxKBZKGnd2TtPkcJ/ljkUCAwEAAQ==
-----END PUBLIC KEY-----
EOD;

/////////////////////////////////
// The above is the official one.
// For example, the public key private key we got is one line.
// private key
////////////////////////////////

$str='MIIBOgIBAAJBANDiE2+Xi/WnO+s120NiiJhNyIButVu6zxqlVzz0wy2j4kQVUC4ZRZD80IY+4wIiX2YxKBZKGnd2TtPkcJ/ljkUCAwEAAQJAL151ZeMKHEU2c1qdRKS9sTxCcc2pVwoAGVzRccNX16tfmCf8FjxuM3WmLdsPxYoHrwb1LFNxiNk1MXrxjH3R6QIhAPB7edmcjH4bhMaJBztcbNE1VRCEi/bisAwiPPMq9/2nAiEA3lyc5+f6DEIJh1y6BWkdVULDSM+jpi1XiV/DevxuijMCIQCAEPGqHsF+4v7Jj+3HAgh9PU6otj2nY79nJtCYmvhoHwIgNDePaS4inApN7omp7WdXyhPZhBmulnGDYvEoGJN66d0CIHraI2SvDkQ5CmrzkW5qPaE2oO7BSqAhRZxiYpZFb5CI';
$str = chunk_split($str, 64, "\n");
$private_key = "-----BEGIN RSA PRIVATE KEY-----\n$str-----END RSA PRIVATE KEY-----\n";
 
//public key
$str='MFwwDQYJKoZIhvcNAQEBBQADSwAwSAJBANDiE2+Xi/WnO+s120NiiJhNyIButVu6zxqlVzz0wy2j4kQVUC4ZRZD80IY+4wIiX2YxKBZKGnd2TtPkcJ/ljkUCAwEAAQ==';
$str = chunk_split($str, 64, "\n");
$public_key = "-----BEGIN PUBLIC KEY-----\n$str-----END PUBLIC KEY-----\n";
$binary_signature = "";
openssl_sign($data, $binary_signature, $private_key, OPENSSL_ALGO_SHA1);
 
// Check signature
$ok = openssl_verify($data, $binary_signature, $public_key, OPENSSL_ALGO_SHA1);
echo "check #1: ";
if ($ok == 1) {
    echo "signature ok (as it should be)\n";
} elseif ($ok == 0) {
    echo "bad (there's something wrong)\n";
} else {
    echo "ugly, error checking signature\n";
}
 
$ok = openssl_verify('tampered'.$data, $binary_signature, $public_key, OPENSSL_ALGO_SHA1);
echo "check #2: ";
if ($ok == 1) {
    echo "ERROR: Data has been tampered, but signature is still valid! Argh!\n";
} elseif ($ok == 0) {
    echo "bad signature (as it should be, since data has beent tampered)\n";
} else {
    echo "ugly, error checking signature\n";
}

The key solution is to format your one line key into the correct form. Hope it helps you.

source: https://www.programmersought.com/article/20701473131/

1 thought on “openssl_sign(): supplied key param cannot be coerced into a private key”

Leave a Comment