You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

PHP加密文件无法用Java解密问题求助

问题:AES-256-CBC跨语言解密失败(PHP加密→Java解密)

加密端(PHP)代码

$key="c5ff6db1e2f1d27d294047b220516312da1b4ba899035692e893e16815fc1234";

$content = file_get_contents(filename);
$ivlen = openssl_cipher_iv_length($cipher="AES-256-CBC");
$iv = openssl_random_pseudo_bytes($ivlen);

$cipherText_raw = openssl_encrypt($this->plaintext, $cipher, 
                         $key, $options=OPENSSL_RAW_DATA, $iv);

$encode = base64_encode( $iv.$cipherText_raw );//Append IV and encode

解密端(Java)代码

String hexString = "c5ff6db1e2f1d27d294047b220516312da1b4ba899035692e893e16815fc1234";

//Using Bouncycastle (org.bouncycastle.util.encoders.Hex) for Hex to byte
SecretKeySpec secretKey=new SecretKeySpec(Hex.decode(hexString),"AES");

String content = Files.readString(Paths.get("abc.xml"), StandardCharsets.UTF_8);

byte[] arrDecode  = Base64.getDecoder().decode(content);
//Extract IV
byte[] arrIV = Arrays.copyOfRange(arrDecode,0,16);
//Extract Encrypted Content
byte[] arrEnc = Arrays.copyOfRange(arrDecode,16,arrDecode.length);

Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
cipher.init(Cipher.DECRYPT_MODE, secretKey, new IvParameterSpec(arrIV));
byte[]  xx = cipher.doFinal(arrEnc);

错误信息

javax.crypto.BadPaddingException: Given final block not properly padded. Such issues can arise if a bad key is used during decryption.

问题排查与解决方案

核心问题1:密钥处理不一致

PHP端直接将十六进制字符串作为密钥字节序列使用,而Java端将十六进制字符串解码为字节数组作为密钥,两者密钥完全不匹配:

  • PHP中$key变量是64个ASCII字符(每个十六进制字符占1字节),总长度64字节,远超AES-256要求的32字节,openssl_encrypt会自动截断为前32字节作为密钥,这和Java端解码后的32字节密钥完全不同。

修正方案:PHP端将十六进制密钥解码为字节数组:

$key = hex2bin("c5ff6db1e2f1d27d294047b220516312da1b4ba899035692e893e16815fc1234");

核心问题2:加密内容变量错误

PHP代码中读取文件内容到$content变量,但实际加密的是$this->plaintext,属于明显笔误,导致加密内容不是目标文件内容,解密自然失败。

修正方案:替换加密内容变量为$content:

$cipherText_raw = openssl_encrypt($content, $cipher, $key, $options=OPENSSL_RAW_DATA, $iv);

关于填充方式的说明

PHP的openssl_encrypt默认使用PKCS#7填充,Java中的PKCS5Padding与PKCS#7填充对于AES(16字节块大小)是等价的,无需更换为PKCS7Padding,当前Java端的填充配置是正确的。

修正上述两个问题后,Java端代码即可正常解密PHP加密的内容。

内容的提问来源于stack exchange,提问作者prashant

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.25 11:54:05