Оптимизация изображений на PHP-сайте без потери управляемости
На небольших PHP-сайтах производительность часто упирается не в PHP, а в изображения. Главная страница может отдавать HTML за 100 миллисекунд, но пользователь всё равно ждёт, потому что баннер весит 4 мегабайта, карточки товаров загружают оригиналы, а изображения ниже первого экрана грузятся сразу.
Оптимизация изображений не должна превращаться в хаос из ручных копий. Лучше выстроить понятный процесс: загружаем оригинал, делаем нужные размеры, отдаём подходящий формат и кэшируем статику.
Проверить фактический вес страницы
Начать лучше с браузера. Во вкладке Network видно, какие изображения грузятся, сколько весят и блокируют ли первый экран.
Через консоль можно проверить отдельный файл:
curl -I https://example.ru/uploads/banner.jpg
du -h web/uploads/banner.jpg
Если картинка отображается в блоке 600 пикселей шириной, а фактически имеет 4000 пикселей, сервер и пользователь гоняют лишние данные.
Реальные размеры
Нельзя полагаться только на CSS-уменьшение. Браузер всё равно скачает исходный большой файл.
<img src="/uploads/photo-4000.jpg" width="600" height="400" alt="">
Лучше заранее создать размер под место отображения:
<img src="/uploads/cache/photo-600.jpg" width="600" height="400" alt="">
WebP и fallback
WebP часто заметно уменьшает вес изображений. Для простого сайта можно хранить WebP-версии рядом с исходниками и отдавать их в шаблоне.
<picture>
<source srcset="/uploads/cache/photo-600.webp" type="image/webp">
<img src="/uploads/cache/photo-600.jpg" width="600" height="400" alt="">
</picture>
Если используется автоматическая обработка, важно не пересоздавать изображения на каждом запросе. Генерация должна происходить при загрузке, в фоне или один раз при первом запросе с сохранением результата.
Lazy loading
Изображения ниже первого экрана можно загружать лениво. Для многих страниц достаточно стандартного loading="lazy".
<img src="/uploads/cache/product-300.webp" loading="lazy" width="300" height="300" alt="">
Для изображений первого экрана lazy loading лучше использовать осторожно. Главный баннер или основное фото товара должны появляться быстро.
srcset для разных экранов
Если один и тот же блок открывается на телефоне и на широком мониторе, полезно отдавать разные размеры.
<img
src="/uploads/cache/photo-600.webp"
srcset="/uploads/cache/photo-300.webp 300w, /uploads/cache/photo-600.webp 600w, /uploads/cache/photo-1200.webp 1200w"
sizes="(max-width: 600px) 300px, 600px"
width="600"
height="400"
alt="">
Это особенно полезно для каталогов и блогов, где много превью.
Обработка загружаемых файлов
Если пользователи или администраторы загружают изображения, лучше сразу ограничивать размер и формат. Иначе через админку легко загрузить фото с телефона на 8 мегабайт.
public function rules()
{
return [
[
['image'],
'file',
'extensions' => ['jpg', 'jpeg', 'png', 'webp'],
'maxSize' => 8 * 1024 * 1024,
],
];
}
После загрузки можно создать несколько производных размеров. Важно хранить оригинал отдельно или хотя бы понимать, можно ли его удалить.
Кэширование статики
Оптимизированные изображения должны нормально кэшироваться браузером. Для файлов с неизменяемым именем нельзя ставить слишком долгий кэш без версии. Для файлов с hash или уникальным именем долгий кэш подходит лучше.
location ~* \.(jpg|jpeg|png|webp|gif|svg|ico)$ {
expires 30d;
add_header Cache-Control "public";
}
Не забыть alt и размеры
Оптимизация — не только сжатие. У изображений должны быть width и height, чтобы страница не прыгала при загрузке. alt нужен для доступности и нормального описания контента.
<img src="/uploads/cache/service.webp" width="800" height="500" alt="Настройка сайта">
Чек-лист
- Проверить вес изображений во вкладке Network.
- Не отдавать оригиналы там, где нужны превью.
- Создать размеры под реальные блоки.
- Использовать WebP там, где это уместно.
- Добавить lazy loading для изображений ниже первого экрана.
- Использовать srcset для разных экранов.
- Ограничить загрузки через админку.
- Настроить кэширование статики.
Изображения лучше оптимизировать системно. Разовая ручная сжатая картинка помогает только до следующей загрузки через админку. Нормальный процесс обработки экономит трафик постоянно и снижает риск, что сайт снова станет тяжёлым через месяц.
Комментарии (0)
Пока нет комментариев. Будьте первым!