Наверное, все уже в курсе, что одно из главных узких мест серверов — дисковая подсистема. Особенно это заметно на web-серверах и больших СУБД. Производители жестких дисков находятся в постоянной гонке за производительность, но против физики не попрешь — головка жесткого диска не может болтаться со скоростью света :).
Приходят SSD, казалось бы, вот оно — счастье! Нет механики, не надо ждать, пока головка доедет до нужной точки (особенно если данные фрагментированы или ОС пытается считать много всего сразу). Ан нет — дорого, ненадежно, места мало — в общем, на сервер не поставишь.
Какое решение? Правильно, совместить! Задача — получить скорость и время доступа SSD и надежность и обьем HDD. Существуют аппаратные решения, но мы же бедные экономически подкованные — поэтому будем делать программно.
Как все начиналось
Где-то с года два назад один мой друг всерьёз занялся проектом сайта с подбором и продажей автомобилей из Германии. Сайт до этого жил на shared-хостинге и ужасно тупил — движок был написан непонятно когда и непонятно кем, главная страница генерировалась около 2-3 секунд. Быстрый рост посещаемости привел к переезду на отдельный, на котором он и живет до сих пор — акционный i7 от fastvps (реселлер hetzner). Через некоторое время load average в районе 8-10 стал почти нормой — стало понятно, что надо проводить ревизию кода.
Над одним моментом я смеялся довольно-таки долго — на главной странице был include, который работал около 3 секунд и непонятно что делал, но без него не работает. Результаты ревизии хоть и предсказуемы, но все равно печальны: оказалось, что проще всё переписать с нуля (чем мы сейчас и занимаемся), чем править то, что есть. Немного помогло вынесение некоторых блоков в SSI с кешированием (тогда там уже крутился nginx + php-fpm), но надо было что-то делать. Писать всё заново — долго (да и владелец до сих пор не совсем рад такому решению — привет, дядь Саш! :) ), стали искать альтернативные решения. Краешек сознания вытолкнул на поверхность где-то услышанную мысль — можно кешировать на SSD. Мысль покрутилась и утонула.
Полгода назад наступил переломный момент — улетели в Страну Мальборо сразу два (shit happens) жестких диска в составе RAID-1. Пока hetzner менял HDD, решили — умирать, так с музыкой! И заказали в дополнение еще и SSD.
Что из этого получилось
Мы используем flashcache от facebook, о котором на Хабре почему-то почти нет упоминаний.
Настраивалось всё полгода назад, делалось сразу с flashcache, поэтому для построения графиков «до» и «после» мне пришлось всё останавливать.
Итак, на графиках, кусками слева направо:
- работа с flashcache
- перерыв на отключение
- работа без flashcache напрямую с HDD (бедный zabbix из-за нагрузки не успевал сохранять данные — давайте его поймем и простим)
- перерыв на включение всего назад (тут я сделал ошибку, о которой позже)
- работа с flashcache
- перерыв на исправление ошибки
- нормальная работа в штатном режиме (с flashcache)
Загрузка CPU
Возвращаемся в старые добрые времена огромного LA:
Загрузка HDD и SSD
Здесь sda — HDD в составе RAID (mdadm), sdc — SSD, работающий как кеш. sdb — второй HDD из рейда, я не стал приводить график — там все очень похоже на sda.
Загрузка HDD:
Как видим, HDD становится очень плохо — время отклика доходит до 1 секунды.
SSD, здесь всё просто и понятно:
Время загрузки сайта
Замерялось время загрузки главной страницы сайта. Там несколько SSI с блочным кешированием. Это мой любимый график:
По-моему, результаты очевидны.
Итоги и подводные камни
Наш сервер стал намного более отзывчивым, MySQL — шустрей (замеры не проводились), а волосы — более мягкими и шелковистыми.
Если ваш сервер еле дышит из-за большой нагрузки на i/o — не думайте. Ставьте flashcache. На странице проекта есть неплохое описание, как его и с чем готовить. Я не буду на этом останавливаться — для этого существует документация. Хочу лишь осветить некоторые трудности, с которыми я столкнулся:
- Flashcache не работает на 32-битных системах. Там какая-то дурацкая ошибка в коде, которую никто не спешит исправлять — у Facebook всё окружение 64-битное.
- В комплекте есть hook и скрипты в initramfs для инициализации flashcache-томов в Debian при запуске, но он не работает для томов поверх lvm (т.к. в момент запуска lvm ещё не инициализирован). Я решил хаком — /sbin/vgchange -ay в начале скрипта. Неправильно, конечно, но тогда надо было сделать быстро.
- Категорически нельзя монтировать и использовать том, поверх которого работает flashcache (даже если он отключен). Ну то есть, конечно, можно, но flashcache тогда не будет знать о изменениях. Для меня это закончилось слегка побитой ФС после повторного запуска (третий провал на графиках). Правильно — останавливаем flashcache, отключаем его (dmsetup remove), делаем с томом все что надо, удаляем flashcache-том на SSD (flashcache_destroy), создаем flashcache заново. Для операций вроде проверки fs это всё делать необязательно — просто проверяем уже flashcache-том.
Автор: Obramko