При использовании CMS Битрикс часто встает проблема увеличения объема находящихся на сервере файлов, что создает неудобства для администрации и пользователей сайта, может привести к техническим сбоям и даже полной неработоспособности ресурса. Причин проблемы может быть много. Это плодящиеся файлы кэша, бэкапы и многое другое. Мы поговорим о папке upload, в которой хранятся пользовательские файлы.
Итак, что это за папка и почему она разрастается? В папке upload Битрикса хранятся различные неисполняемые файлы, в основном изображения — например, файлы медиабиблиотеки. Но нас интересует вложенная в upload папка iblock. Она содержит изображения, прикрепленные к инфоблокам. В отличие от находящейся там же папки resize_cache, в которой содержится кэш отмасштабированных фотографий, и всю информацию из которой можно безболезненно стереть, здесь хранятся оригиналы фотографий. Если стереть изображение в ней, оно пропадет на сайте полностью.
Зачем из upload/iblock вообще что-то стирать? Дело в механизме Битрикса при работе с инфоблоками, а точнее их картинками. При прикреплении изображения к инфоблоку для картинки создается отдельная директория в папке iblock, в которую помещается картинка. Также создается запись в специальной таблице базы данных с путем к изображениям, по которой в дальнейшем она и ищется. Однако при удалении элемента инфоблока, Битрикс удаляет только запись из таблицы, а директория с изображениями остается на сервере.
Со временем изображения копятся и занимают значительный объем. Менеджеры по незнанию или лени не всегда обрабатывают загружаемые картинки, и они могут весить десятки мегабайт. Особенно остро проблема проявляется у динамичных сайтов с большим количеством информации, например, интернет-магазинов. Вот тут и встает вопрос очистки этой папки. Почему это так реализовано в Битриксе, и почему программисты должны лепить заплатки сами — не понятно, но примем как данность.
Предлагаемое решение построено на использовании агента, который будет каждые сутки чистить нашу папку. Это позволит забыть о проблеме.
Сделаем файл /bitrix/php_interface/includes/agents.php:
<? function CleanUpUpload() { global $DB; define("NO_KEEP_STATISTIC", true); define("NOT_CHECK_PERMISSIONS", true); $deleteFiles = 'yes'; //Удалять ли найденые файлы yes/no $saveBackup = 'yes'; //Создаст бэкап файла yes/no //Папка для бэкапа $patchBackup = $_SERVER['DOCUMENT_ROOT'] . "/upload/iblock_Backup/"; //Целевая папка для поиска файлов $rootDirPath = $_SERVER['DOCUMENT_ROOT'] . "/upload/iblock"; $time_start = microtime(true); //Создание папки для бэкапа if (!file_exists($patchBackup)) { CheckDirPath($patchBackup); } // Получаем записи из таблицы b_file $arFilesCache = array(); $result = $DB->Query('SELECT FILE_NAME, SUBDIR FROM b_file WHERE MODULE_ID = "iblock"'); while ($row = $result->Fetch()) { $arFilesCache[$row['FILE_NAME']] = $row['SUBDIR']; } $hRootDir = opendir($rootDirPath); $count = 0; $contDir = 0; $countFile = 0; $i = 1; $removeFile=0; while (false !== ($subDirName = readdir($hRootDir))) { if ($subDirName == '.' || $subDirName == '..') { continue; } //Счётчик пройденых файлов $filesCount = 0; $subDirPath = "$rootDirPath/$subDirName"; //Путь до подкатегорий с файлами $hSubDir = opendir($subDirPath); while (false !== ($fileName = readdir($hSubDir))) { if ($fileName == '.' || $fileName == '..') { continue; } $countFile++; if (array_key_exists($fileName, $arFilesCache)) { //Файл с диска есть в списке файлов базы - пропуск $filesCount++; continue; } $fullPath = "$subDirPath/$fileName"; // полный путь до файла $backTrue = false; //для создание бэкапа if ($deleteFiles === 'yes') { if (!file_exists($patchBackup . $subDirName)) { if (CheckDirPath($patchBackup . $subDirName . '/')) { //создал поддиректорию $backTrue = true; } } else { $backTrue = true; } if ($backTrue) { if ($saveBackup === 'yes') { CopyDirFiles($fullPath, $patchBackup . $subDirName . '/' . $fileName); //копия в бэкап } } //Удаление файла if (unlink($fullPath)) { $removeFile++; } } else { $filesCount++; } $i++; $count++; unset($fileName, $backTrue); } closedir($hSubDir); //Удалить поддиректорию, если удаление активно и счётчик файлов пустой - т.е каталог пуст if ($deleteFiles && !$filesCount) { rmdir($subDirPath); } $contDir++; } closedir($hRootDir); return "CleanUpUpload();"; } ?>
Добавим строки в /bitrix/php_interface/init.php
if (file_exists($_SERVER["DOCUMENT_ROOT"]."/bitrix/php_interface/include/agents.php")){ require_once($_SERVER["DOCUMENT_ROOT"]."/bitrix/php_interface/include/agents.php"); }
Последний шаг — настроить выполнение агента. Заходим в Настройки > Настройки продукта > Агенты и заполняем форму следующим образом:
Сохраняем. Все. Если выполнение агентов настроено правильно (это тема для другой статьи), то каждую ночь в 4 утра или при исполнении на хитах при первом посещении сайта после 4 утра, агент будет проверять наличие неиспользуемых файлов и удалять их без чьего-либо участия.