PKCS7Signature php要如何实现?
对接第三方有个java 验签代码 ,PHP要用什么函数实现这个功能?
//加签 public static String sign(byte[] byte_明文报文, String 发送方私钥文件密码,
String 发送方私钥文件名, String 发送方cer证书文件名) {
try {
char[] keyPassword = new String(发送方私钥文件密码).toCharArray();
byte[] base64EncodedPrivatekey = FileUtil.read4file(发送方私钥文件名);
PrivateKey signerPrivatekey = CryptUtil.decryptPrivateKey(
Base64.decode(base64EncodedPrivatekey), keyPassword);
byte[] base64EncodedCert = FileUtil.read4file(发送方cer证书文件名);
X509Certificate signerCertificate = CryptUtil
.generateX509Certificate(Base64.decode(base64EncodedCert));
byte[] signature = PKCS7Signature.sign(byte_明文报文, signerPrivatekey,
signerCertificate, null, false); // 签名中不附带原文
String b64StrSignature = new String(Base64.encode(signature));
return b64StrSignature;
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
回答:
PHP 验签用openssl_pkcs7_verify ,最后一个参数832,中国银行中信都可以。
中信加签值升序要用asort($argArr, SORT_STRING)
/** * 加签
* @param string $str 字符串(sortSign($argArr))
* @param string $pre 生成文件干扰字符串UID
* @return string
*/
public static function pkcs7Sign($str, $pre = 'tmp')
{
$pre = uniqid($pre);
$pkcs12 = file_get_contents('PTNRtest.pfx');
openssl_pkcs12_read($pkcs12, $certs, 'mima');
$dataFile = RUNTIME_PATH . $pre . 'dataTxt.txt';
$myfile = fopen($dataFile, "w") or die("Unable to open file!");//将要签名的参数写入文件中
fwrite($myfile, $str);
fclose($myfile);
$signFile = RUNTIME_PATH . $pre . 'sign.txt';
openssl_pkcs7_sign($dataFile, $signFile, $certs['cert'], $certs['pkey'], null, PKCS7_DETACHED | 0x200 | 0x100);
$sign = self::smimeToSign(file_get_contents($signFile));
unlink($dataFile);
unlink($signFile);
return $sign;
}
/**
* 把S/MIME格式数据格式成签名数据
* @param string $smime S/MIME格式数据
* @return string
*/
public static function smimeToSign($smime)
{
$prefix = "||";
$smime = str_replace("\n", $prefix, trim($smime));
$tmpData = [];
preg_match_all("/\|{4}(.*)\|{4}/Ui", trim($smime), $tmpData);
if (isset($tmpData[1][1])) {
$smime = str_replace("||", "", $tmpData[1][1]);
} else {
$smime = "";
}
return $smime;
}
/**
* 加签数据值升序
* @param array $argArr 请求数据
* @return string
*/
public static function sortSign($argArr)
{
$tmp = [];
foreach ($argArr as $key => $val) {
if (in_array($key, ['SIGN_INFO'])) continue;
$tmp[] = $val;
}
asort($tmp, SORT_STRING);
return implode('', $tmp);
}
回答:
PKCS7 填充是在末尾填充 n 个字节,每个字节内容为 n 值。所以对应的解密流程是先 base64 解码,读取末尾字节得到 n 值,然后去掉末尾 n 个字节截取所得字符串。
官方函数库提供了 openssl_pkcs7_decrypt 方法,封装了解密过程,可以尝试一下。
文档:https://www.php.net/manual/zh...
4.11补充
<?phpclass A {
// RSA密钥生成 https://blog.csdn.net/weixin_37194108/article/details/103946800#:~:text=Windows%20%E4%B8%8B%20%E4%BD%BF%E7%94%A8OpenSSL%E7%94%9F%E6%88%90RSA%20%E5%85%AC%E9%92%A5%E5%92%8C%E7%A7%81%E9%92%A5%20%281%29%E4%B8%8B%E8%BD%BD%20OpenSSL%20%282%29%E6%89%93%E5%BC%80%20OpenSSL,_private_key.%20pe%20m%201024%E6%AD%A4%E6%97%B6%E5%9C%A8%20OpenSSL%20%E7%9A%84bin%E7%9B%AE%E5%BD%95%E4%B8%8B%20%E7%94%9F%E6%88%90%20%E4%BA%86%E4%B8%80%E4%B8%AArs
private $prifile = './id_rsa_private_pkcs';
private $pubfile = './id_rsa_public.pub';
private $privateKey, $publicKey;
public function __construct() {
$this->privateKey = file_get_contents($this->prifile);
$this->publicKey = file_get_contents($this->pubfile);
}
# 非对称加解密
public function encrypt($data) {
openssl_private_encrypt($data, $s, $this->privateKey);
return base64_encode($s);
}
public function decrypt($data) {
openssl_public_decrypt(base64_decode($data), $s, $this->publicKey);
return $s;
}
# 对称加解密
public function pkcs7Encrypt($data, $iv="") {
$data = $this->pkcs7Padding($data);
$s = openssl_encrypt($data, "aes-256-cbc-hmac-sha256", $this->privateKey, OPENSSL_RAW_DATA, $iv);
return base64_encode($s);
}
public function pkcs7Decrypt($data, $iv="") {
$s = base64_decode($data);
$s = openssl_decrypt($s, "aes-256-cbc-hmac-sha256", $this->privateKey, OPENSSL_RAW_DATA, $iv);
return $this->pkcs7Unpadding($s);
}
# pkcs7 填充
public function pkcs7Padding($data, $blockSize=16) {
$n = $blockSize - strlen($data) % $blockSize;
$s = $data . str_repeat(chr($n), $n);
return $s;
}
public function pkcs7Unpadding($data, $blockSize=16) {
$size = strlen($data);
if ($size < $blockSize) {
print("data len error");
return false;
}
$n = (int)($data[$size-1]);
return substr($data, 0, $size - $n);
}
};
$a = new A();
$iv = "0123456789123456";
$s = $a->pkcs7Encrypt("123", $iv);
var_dump($s);
var_dump($a->pkcs7Decrypt($s, $iv));
你的需求应该是 x509 证书相关的加解密,还没试,后面再研究一下了。
以上是 PKCS7Signature php要如何实现? 的全部内容, 来源链接: utcz.com/p/944362.html