БлогУскоряем бутстрап или борьба с неправильным удалением модулей
На одном из проектов я столкнулся с необходимостью оптимизации сайта. Проанализировав серверную часть сайта я заметил, что бутстрап на каждую загрузку страницы съедал ~350 милисекунд. Довольно много, учитывая, что это лишь загрузка необходимых компонентов. Потратив ещё некоторое время на поиск проблемы я выяснил, что каждый раз при загрузке страницы Друпал сканировал все мои папки с темами и модулями заново. Это и являлось основой задержкой в бутстрапе, т.к. на это сканирование тратилось около 280 милисекунд (102 модуля и 2 темы). И это при том, что проект стоит на отдельном сервере, который полностью заточен под Drupal 7.
После осознания проблемы у меня возникло два вполне логичных вопроса:
1. Какого @#$ так долго?
2. Почему это нельзя было закэшировать?
Как выяснилось - Друпал это уже кэширует. И всё обычно хорошо и правильно работает ... пока разработчик не начинает удалять модули неправильно. Некоторые разработчики удаляют модули деревянным способом: физическим удалением модуля с сервера. И вроде бы модуль перестаёт работать, и вроде бы результат достигнут... Однако что при этом происходит в Друпале?
На последнем этапе бутстрапа Друпал загружает из таблицы {system} список включенных модулей. После этого он пытается их загрузить путём простого require_once(). Однако если модуль включен, но на сервере файл ИМЯМОДУЛЯ.module не найден, то Друпал начинает судорожно сканировать все папки с модулями и темами в надежде найти там этот пропавший файл. И, естественно, не находит. И так при каждой загрузке страницы. Именно поэтому просто критически важно удалять файлы через специально предназначенный раздел админки (/admin/modules/uninstall). В противном случае время выполнения бутстрапа сразу увеличивается в N раз (пропорционально количеству модулей и тем).
Решение проблемы
По традиции, к любой проблеме я прилагаю её решение. В данном случае я написал модуль Bootstrap optimizer, который ищет включенные модули, которых нет на своём физическом месте, и удаляет их. Работа с ним проста и интуитивно понятна. Он имеет всего 2 кнопки: Анализировать файлы и Удалить пропавшие файлы. По нажатию первой вы получите список "пропавших" файлов, по нажатию второй - эти файлы будут подчищены из таблицы с модулями.
Вот так это выглядит у меня на локальном сервере:
После удаления лишних файлов:
Разница по времени существена. Даже с учётом того, что это локальный сервер.
А вот так смотрятся эти же данные на боевом сервере при включеном профилировании:
P.S. Всем рекомендую поставить модуль и проверить, можно ли ускорить загрузку ваших сайтов в несколько кликов ;)
P.P.S. По возможности оставляйте фидбэки об использовании модуля. И мне приятно, и понятны результаты работы.
- Spleshka
- 21.10.2012
- 34389
Комментарии
Я пользуюсь драш-командой clean-modules и ещё своим дополнением для решения противоположенной проблемы :)
Очень удобно при первом анализе сайта-пациента сразу прогнать эти команды, чтобы увидеть картину маслом.
Наверно также можно добавить, что чтобы перестроить пути, если вы переложили включенный модуль из папки в папку, достаточно запустить drush rr.
Полезное дополнение, спасибо :)
Отличный пост, полгаю стоит разместить линк на официальный issue
А для 6-ки? ;)
А от куда последние два скрина, это хостинг предоставляет или какой-то модуль?
P.S. Сорри, не увидел предпоследнего абзаца
Так а где сам модуль? Мечтаю попробовать. Ссылки не вижу :(
Товарищ! Дайте возможность попробовать модуль. Нет ссылки
Плохо ищете. Их в статье аж две.
Спасибо, полезно )))
p.s.: ты бы это, тузо то вытащил, а то неприлично как-то :D
Здорово.
А на D6 как поступать в подобной ситуации?
Портировать модуль под Drupal 6 и поступать точно так же :)
А что делать, если в админке осталась информация о старых модулях, которых уже давно нет на сайте? Как удалить такую информацию?
В админке - это где именно?
На странице /admin.
У меня там, например, остались ссылки на настройки модулей FeedBurner, Modr8, которые я еще на шестерке ставил. При нормальном удалении модулей эти ссылки остались. Сейчас сайт переведен на семерку, ссылки все еще есть...
Надеялся, что этот модуль поможет их удалить.
Вообще модуль и должен был их удалить, если раньше эти модули были включены. Как убрать эти модули из админки - скачать их на Д7, включить на сайте, а потом удалить корректно.
Я проделывал тоже самое на шестерке, данные оставались в БД, т.е. модули не удаляли свою инфу при корректном удалении...
Обрати внимание на http://drupal.org/project/variable_clean, возможно, поможет.
Может вы выложите, под drupal 6 модуль.
Думаю народ будет благодарен...
А вы готовы платить деньги за потраченное время на порт ?
Или бесплатно хотите ?
Не знаю как в 6-ке, 7-ке, но еще в 5-ке в ядре был код, который постоянно проверял существование файлов модулей в системе, прежде чем их подгрузить.
То есть, вызывается функция проверки существования файла в системе, а эта функция в php не кэшируется никак, ни имеет право php результат ее выполнения кэшировать, а на тот момент у меня было установлено около 100 модулей, каждый из которых имел не по одному .module или .inc файлу для включения.
Функция дорогая, даже если по 5 мс на 100 файлах проверить, это получится уже полсекунды.
Допустим у вас мощная система и быстрый винчестер, но отдавать больше 100 мс на то чтобы при каждой генерации страницы друпал только лишь проверял существование файла модуля который включен в админке считаю верх свинства. И никакой eaccelerator не спасет, так как include то конечно может и в опкоде уже, а вот операцию file exist этот ускоритель тоже не кешировал. И надеюсь не под виндовс друпал запускаете.
И да, забыл сказать, после того как файл существует, он его подгружает.
в общем об этом я писал еще тут http://www.drupal.ru/node/43857
Скажите, чем вы пользуетесь дял такого подробного просмотра инфы о функциях времени и т.д.?
Вот так происходят проверки.
Так как насчет портировать на 6 эту плезность? Цену вопроса огласите плз
При попытке установить ваш модуль получил ошибку:
Возникла AJAX HTTP ошибка. Полученный код HTTP: 200 Следует отладочная информация. Путь: /batch?render=overlay&id=41&op=do Текст Состояния: OK Текст Ответа: {"status":true,"percentage":"100","message":"\u0412\u044b\u043f\u043e\u043b\u043d\u0435\u043d\u043e 3 \u0438\u0437 3.\u003Cbr \/\u003E\u0418\u043c\u043f\u043e\u0440\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u043e: \u003Cem class=\u0022placeholder\u0022\u003Ebootstrap_optimizer-7.x-1.0-beta2.ru.po\u003C\/em\u003E."}Время выполнения скрипта: 1.1967990398407 сек.
... отключил ваш модуль, удалил на странице unistall, удалил физически папку с модулем - все равно выводит надпись "Время выполнения скрипта:" на страницах. Это что, вирус такой!? оО
Модуль супер. Долго ломал голову в чем причина медленной работы. Поставил Devel - выяснил проблема в кэше. Мрдули конечно удалены неправильно. Типа они работают. Поставил Bootstrap optimizer - все стало супер.
Комментировать