PHP 7.2+及8.x已彻底移除mcrypt扩展,因其自7.1起被废弃;替代方案是用openssl_encrypt等函数迁移AES-CBC加密逻辑,并注意填充、IV长度及元函数缺失问题。

phpEnv 不支持 Mcrypt 扩展,强行安装会失败或导致 PHP 崩溃。 因为 phpEnv 默认使用 PHP 7.2+ 或 8.x,而 Mcrypt 自 PHP 7.1 起被标记为废弃,7.2 起彻底移除——不是“没打包”,是源码里根本没了 mcrypt 目录。
为什么 phpEnv 下执行 pecl install mcrypt 会报错
错误通常长这样:ERROR: Package "mcrypt" does not have a release for PHP version 8.0.28 或更直接的 configure: error: mcrypt.h not found。原因很实在:
- PECL 官方早在 2019 年就归档了
mcrypt包,现在pecl.php.net/package/mcrypt返回 404 - phpEnv 编译时用的是系统级 OpenSSL 和现代构建链,压根不链接
libmcrypt库 - 即使你手动下载旧版
mcrypt-1.0.4.tgz,phpize生成的 configure 脚本也会在检测mcrypt.h时失败——头文件路径对不上,PHP 内部结构也变了
替代方案:用 OpenSSL 模拟 Mcrypt 的常见用法
Mcrypt 最常被用来做 AES-128-CBC 加密(比如 Laravel 5.2 及更早的 encrypt 辅助函数)。OpenSSL 完全能兼容,但要注意三点:
- Mcrypt 的
mcrypt_encrypt(MCRYPT_RIJNDAEL_128, $key, $data, MCRYPT_MODE_CBC, $iv)对应 OpenSSL 的openssl_encrypt($data, 'AES-128-CBC', $key, OPENSSL_RAW_DATA, $iv) - Mcrypt 默认不填充,OpenSSL 要求 PKCS#7 填充;如果原 Mcrypt 代码用了零填充(
\0),得自己补或改逻辑 - IV 长度必须严格为 16 字节(AES-CBC),Mcrypt 宽松些,OpenSSL 会直接报
iv length must be 16
示例迁移:
立即学习“PHP免费学习笔记(深入)”;
/* 旧 Mcrypt */ $td = mcrypt_module_open(MCRYPT_RIJNDAEL_128, '', MCRYPT_MODE_CBC, ''); mcrypt_generic_init($td, $key, $iv); $encrypted = mcrypt_generic($td, $data); mcrypt_generic_deinit($td); <p>/<em> 新 OpenSSL(等效) </em>/ $encrypted = openssl_encrypt($data, 'AES-128-CBC', $key, OPENSSL_RAW_DATA, $iv);
实在绕不开 Mcrypt 的旧项目怎么办
别在 phpEnv 上硬刚。可行路径只有两条:
- 降级到 phpEnv 支持的 PHP 7.0 分支(如
phpenv install 7.0.33),再用系统包管理器装php7.0-mcrypt(Ubuntu/Debian)或编译mcrypt.so(CentOS) - 改用 Homestead 或 Docker:Homestead 有预置 PHP 7.1 镜像,Docker 可基于
php:7.1-apache构建,再走传统apt-get install php7.1-mcrypt流程
注意:PHP 7.0/7.1 已停止安全更新,仅限离线开发或临时过渡,上线环境严禁使用。
真正容易被忽略的点是:有些老项目不仅调用 mcrypt_encrypt,还依赖 mcrypt_list_algorithms() 这类元函数——OpenSSL 没有对应替代,必须 mock 或删掉这些探测逻辑,否则运行时直接 fatal error。



















