Релиз PHP 8.5 намечен на 20 ноября 2025 года. С ним мир PHP получит не только ожидаемые новые возможности и улучшения синтаксиса, но и, по традиции, ряд устаревших элементов (deprecations), или, как мы их любим называть, «депрекейтов». Эти предупреждения — это не просто уведомления; это последний звонок, сигнализирующий: определенные функции, методы или языковые конструкции будут либо удалены, либо их поведение станет более строгим в будущих версиях, скорее всего, в PHP 9.0.
Проактивная подготовка — ваш единственный способ защитить проект от внезапных сбоев, сохранить совместимость и перейти на более чистый, безопасный и высокопроизводительный код.
В этой статье я расскажу, как подготовиться к PHP 8.5, чтобы ваш код пережил эту волну «депрекейтов»:
«Депрекейты» в PHP 8.5, Которые Нужно Знать
Ниже представлен перечень наиболее значимых устареваний, собранный на основе официальных предложений RFC и журналов изменений PHP. Начинайте аудит кодовой базы с этих пунктов.
1. Приведение типов: только канонический вид
Использование полных форм для приведения скалярных типов теперь генерирует предупреждение:
- Устаревает:
integer
,double
,boolean
,binary
. - Используем: Только краткие, канонические формы:
int
,float
,bool
,string
.
2. Прощай, старая сериализация
Магические методы __sleep()
и __wakeup()
объявляются устаревшими. Если вы храните сериализованные объекты в сессиях, кеше или БД, это ваш самый большой приоритет.
- Замена: Переходите на
__serialize()
и__unserialize()
.
3. Выполнение команд через обратные кавычки (`
)
Синтаксис, использующий обратные кавычки для вызова внешних команд, объявляется устаревшим.
- Замена: Пишите явно:
shell_exec()
.
4. null
как ключ в array_key_exists()
Передача null
в качестве ключа (offset) в array_key_exists()
устарела.
- Правило: Всегда передавайте ключ валидного типа (строка или число). Для проверки наличия используйте
isset()
.
5. Функции ручной очистки ресурсов
PHP становится умнее и сам управляет ресурсами. Функции для ручного закрытия ресурсов, которые теперь представлены объектами и управляются деструкторами, становятся избыточными и устаревшими. Это касается:
finfo_close()
xml_parser_free()
curl_close()
иcurl_share_close()
imagedestroy()
6. Повторное объявление констант
Определение константы с одним и тем же именем более одного раза будет вызывать предупреждение. Константы должны быть уникальны.
7. Устаревшие INI-директивы
Удалите следующие директивы из ваших php.ini
или .user.ini
, если они там есть:
report_memleaks
register_argc_argv
(в SAPI для HTTP)disable_classes
8. Работа с null
в функциях для директорий
Передача null
в качестве дескриптора директории в стандартные функции, такие как readdir()
, rewinddir()
, closedir()
, теперь устарела.
9. Константы MHASH_*
Старые константы MHASH_*
для хеширования устаревают.
- Замена: Используйте современные и безопасные API:
hash()
или функцииopenssl
.
10. Требования к обработчикам вывода (Output Handlers)
Ваши кастомные обработчики буфера вывода должны быть «чистыми»:
- Возврат: Они должны всегда возвращать строковое значение.
- Вывод: Прямой вывод данных (через
echo
илиprint
) внутри обработчика устаревает.
11. Ограничения на класс Directory
Прямое создание экземпляра (new Directory()
), добавление динамических свойств, клонирование и сериализация объектов Directory
устаревает.
- Замена: Используйте функцию
dir($path)
.
Что Потенциально Выйдет из Строя? (Болевые Точки)
Предупреждения об устаревании не всегда фатальны, но они — мины замедленного действия. Поломка произойдет, если:
- Вы настроили строгий
error_reporting
, где «депрекейты» = фатальная ошибка. - Ваш проект должен быть совместим с PHP 9.0, где эти функции будут удалены.
- Ваши старые сторонние библиотеки или фреймворки не обновлялись годами.
Наиболее уязвимые места:
- Сериализация: Если ваша логика сохранения состояния объектов полагается на
__sleep()
/__wakeup()
. - Legacy-код: Любой старый код, где встречаются неканонические приведения типов (
(double) $val
). - Shell-скрипты: Код, использующий обратные кавычки для вызова команд. Эту практику часто пропускают при аудите.
- Устаревшие алгоритмы: Использование констант
MHASH_*
для хеширования. - Кастомный Output Buffering: Сложная логика в обработчиках вывода, которая зависит от возврата нестроковых данных или прямого вывода.
Стратегии Замены: Чистим Код и Готовимся к Будущему
Для каждого устаревшего элемента есть четкий путь к модернизации.
1. Сериализация
- Решение: Перепишите методы на
__serialize()
и__unserialize()
. Если нужно читать старые данные, разработайте адаптер для поддержки обоих форматов.
2. Приведение типов
- Решение: Глобальный Поиск и Замена по кодовой базе. Переходите на
int
,float
,bool
,string
.
3. Выполнение команд
- Решение: Замените команда на явный
shell_exec('команда')
. Это делает код понятнее и безопаснее.
4. Ключи массивов
- Решение: Убедитесь, что вы всегда передаете валидный ключ. Если ключ может быть
null
, используйтеisset()
для проверки наличия.
5. Константы
- Решение: Определяйте каждую константу только один раз. Используйте пространства имен для логической организации констант и избежания коллизий.
6. Очистка ресурсов
- Решение: Удалите все ручные вызовы
finfo_close()
,curl_close()
,imagedestroy()
и т.д. Доверьте очистку деструкторам объектов.
7. Хеширование
- Решение: Замените
MHASH_*
на современные, более безопасные функции:hash()
,hash_hmac()
,password_hash()
илиopenssl_*()
.
8. Обработчики вывода
- Решение: Модифицируйте обработчики, чтобы они гарантированно возвращали строку и не выводили данные напрямую.
9. Класс Directory
- Решение: Вместо
new Directory($path)
используйтеdir($path)
. Удалите любой код, добавляющий динамические свойства или пытающийся клонировать этот объект.
Дорожная Карта Миграции: 7 Шагов к Безопасному PHP 8.5
Чтобы обновить даже большой Legacy-проект без боли и сбоев, необходим план.
Шаг 1: Инвентаризация и Скрининг 🔎
- Сканирование: Запустите статический анализатор (PHPStan, Psalm) с уровнем, включающим
E_DEPRECATED
, чтобы получить полный список проблем. - Поиск: Проведите поиск по исходникам на наличие известных «депрекейтов» (
__sleep
,MHASH_
, обратные кавычки и т.д.).
Шаг 2: Включение Строгого Режима ⚠️
- На dev- и staging-средах установите
error_reporting
так, чтобыE_DEPRECATED
иE_WARNING
были включены. - Настройте CI, чтобы любой «депрекейт» приводил к провалу сборки.
Шаг 3: Инкрементальный Рефакторинг 🛠️
- Начните с малого: Замените неканонические приведения типов и обратные кавычки — это самый быстрый выигрыш.
- Постепенно переходите к сложным участкам: сериализация, хеширование, Output Handlers.
Шаг 4: Тестирование — Ваш Спасательный Круг ✅
- Запустите все юнит- и интеграционные тесты. Особенно проверьте логику, связанную с сериализацией и файловой системой.
- Тесты должны подтвердить, что после рефакторинга не осталось ни одного предупреждения об устаревании.
Шаг 5: Обновление Зависимостей 📦
- Проверьте и обновите все сторонние библиотеки до версий, которые официально поддерживают PHP 8.5.
Шаг 6: Деплой и Мониторинг на Staging 🚀
- Разверните очищенный код на staging-сервере с PHP 8.5.
- Активно мониторьте логи и трассировки, устраняя последние «сюрпризы».
Шаг 7: Готовность к PHP 9.0 🔮
- Поскольку устаревания в 8.5 — это почти гарантия удаления в 9.0, рассматривайте этот рефакторинг как полную подготовку к следующему мажорному релизу.
Заключение
Устаревания в PHP 8.5 многочисленны, но они направлены на то, чтобы сделать язык чище и безопаснее.
Ключевые выводы:
- Начинайте рано! Не ждите релиза, начните аудит прямо сейчас.
- Модернизируйте! Заменяйте устаревшие функции их современными аналогами (
__serialize()
,hash()
, канонические типы). - Тестируйте! Ваши тесты должны ловить любые оставшиеся «депрекейты».
Переход на PHP 8.5 — это не просто обновление, а капитальный ремонт вашего кода. С четким планом вы не только избежите поломок, но и получите более быстрый, чистый и устойчивый проект.