PHP7+中AES加密解密方法,openssl 替代 mcrypt
2022-07-28 15:20:24
186
{{single.collect_count}}

mcrypt十年过去,现在php7+中已经开始淘汰。官方给出掉提示:

mcrypt_get_block_size — 获得加密算法的分组大小WarningThis function has been DEPRECATED as of PHP 7.1.0. Relying on this function is highly discouraged.

在php7中需要openssl替代,这里需要注意的是:
在mcrypt中对加密key长度没有限制要求,传入多少长度都会参加加密,但是在openssl_encrypt中。key长度只能是16长度,>16长度后,签名结果保持不变,这里是哥坑,在替代方案测试时候容易出错,具体直接上代码对比

低于php7版本代码

class AES {public static function encrypt($input,$key) {$blockSize = mcrypt_get_block_size(MCRYPT_RIJNDAEL_128, MCRYPT_MODE_ECB);$paddedData = static::pkcs5_pad($input, $blockSize);$ivSize = mcrypt_get_iv_size(MCRYPT_RIJNDAEL_128, MCRYPT_MODE_ECB);$iv = mcrypt_create_iv($ivSize, MCRYPT_RAND);$encrypted = mcrypt_encrypt(MCRYPT_RIJNDAEL_128, $key, $paddedData, MCRYPT_MODE_ECB, $iv);return bin2hex($encrypted);}private static function pkcs5_pad ($text, $blocksize) {$pad = $blocksize - (strlen($text) % $blocksize);return $text . str_repeat(chr($pad), $pad);}public static function decrypt($sStr,$key) {$decrypted= mcrypt_decrypt(MCRYPT_RIJNDAEL_128,$key,hex2bin($sStr),MCRYPT_MODE_ECB);$dec_s = strlen($decrypted);$padding = ord($decrypted[$dec_s-1]);$decrypted = substr($decrypted, 0, -$padding);return $decrypted;}/** *url 安全的base64编码 sunlonglong */function base64url_encode($data) {return rtrim(strtr(base64_encode($data), '+/', '-_'), '=');}/** *url 安全的base64解码 sunlonglong */function base64url_decode($data) {return base64_decode(str_pad(strtr($data, '-_', '+/'), strlen($data) % 4, '=', STR_PAD_RIGHT));}}$key = 'g87y65ki6e8p93av8zjdrtfdrtgdwetd';$encrypt = AES::encrypt('123abc',$key);$decrypt = AES::decrypt($encrypt,$key);var_dump($encrypt,$decrypt);加密结果:da07f6363eb0024b4bdd264e5fd4a2f5

下面是php7以上。使用openssl加密:

class AES {/** * * @param string $string 需要加密的字符串 * @param string $key 密钥 * @return string */public static function encrypt($string, $key){// openssl_encrypt 加密不同Mcrypt,对秘钥长度要求,超出16加密结果不变$data = openssl_encrypt($string, 'AES-128-ECB', $key, OPENSSL_RAW_DATA);$data = strtolower(bin2hex($data));return $data;}/** * @param string $string 需要解密的字符串 * @param string $key 密钥 * @return string */public static function decrypt($string, $key){$decrypted = openssl_decrypt(hex2bin($string), 'AES-128-ECB', $key, OPENSSL_RAW_DATA);return $decrypted;}}$encrypt = AES::encrypt('123abc', 'g87y65ki6e8p93av8zjdrtfdrtgdwetd');$decrypt = AES::decrypt($encrypt, 'g87y65ki6e8p93av8zjdrtfdrtgdwetd');var_dump($encrypt,$decrypt);die;加密结果:8c927c42f93a83c5de763aa18e4e6c7d

虽然key长度32位,但是openssl_encrypt加密时候,key长度只使用了16长度,后面未参加签名,而mcrypt_encrypt会整个key参与加密,这样就会出现加密出来对结果不一致。造成困惑,key=g87y65ki6e8p93av8zjdrtfdrtgdwetd与key=g87y65ki6e8p93av结果都是一致对

回帖
全部回帖({{commentCount}})
{{item.user.nickname}} {{item.user.group_title}} {{item.friend_time}}
{{item.content}}
{{item.comment_content_show ? '取消' : '回复'}} 删除
回帖
{{reply.user.nickname}} {{reply.user.group_title}} {{reply.friend_time}}
{{reply.content}}
{{reply.comment_content_show ? '取消' : '回复'}} 删除
回帖
收起
没有更多啦~
{{commentLoading ? '加载中...' : '查看更多评论'}}