Intellect Board — cистема управления сайтом

Построение сайта на основе форума

Intellect Board — cистема управления сайтом »   Техническая поддержка версии 2.22 »   Перегрузка сервера.
RSS

Перегрузка сервера.

Когда таблица _Post весит больше 2 GB и содержет больше 2000000 записей.

Текущий рейтинг темы: Нет
Выводить сообщения

<<Назад  Вперед>>Модераторы: aerograf, wsxПечать
 
Gich
Почетный участник

Gich
Всего сообщений: 123
Рейтинг пользователя: 6


Ссылка


Дата регистрации на форуме:
10 нояб. 2006
И так! Рано или поздно все столкнуться с этой проблемой! - перегрузка. Когда даже собственный сервер насинает загибаться под запросами к mysql. Мало ли кому понадобится это руконоговодство.
Суть в том, что когда БД начинает весить от 400 мегабайт (у каждого своя производительность жедеза) и число записей подходит к миллиону, mysql с большим трудом находит там нужные данные. 600-700тысяч сообщений, это порог после которого время запроса к _Post таблице резко возрастает с 0,01 до 2-5 секунд.
Лекарство:
- дорогой апгрейд сервера - т.к. происходит перегрузка дисковой подсистемы: установа SATA3 контроллера (если его нет), вынос БД на отдельные SAS или SSD диски и прочй головняк.
- допилить _Post таблицу до партицианирования. Как это сделать:

Руководство подразумевает, что читатель представляет в общих чертах, что такое партиционирование и с чем его едят. Если нет, то в гугль, и сюда глянуть можно сюда и сюда
Также, подразумевается что есть доступ к ssh консоли сервера и читатель представляет как работать с командами оболочки mysql под linux через ssh. Ну или хотябы раз входил в оболочку mysql.

1) На всякий случай сделайте бэкап всей БД через mysqldump

2) Чтобы при случае долго не рыться в поисках таблицы, отдельно задампим её
mysqldump -p ваша_бд_форума --tables XXX_Post >XXX_Post_all.dmp

3) Отдельно дампим данные
mysqldump -p ваша_бд_форума --tables --no-create-info XXX_Post >XXX_Post_data.dmp

4) Отдельно структура
mysqldump -p ваша_бд_форума --tables --no-data XXX_Post >XXX_Post_str.dmp

5) Модифицируем структуру таблицы в файле XXX_Post_str.dmp, примерно таким образом:
a. PRIMARY KEY (`p_id`,`p_tid`,`p_uid`,`p__premoderate`), добавили p_tid. Его тут раньше не было
b Заремим — FULLTEXT KEY `topics` (`p_text`,`p_title`) - добавили перед строкой вот это: --
Иначе партиция не создаётся.
c. В предыдущей строке убрали запятую.Стало так: KEY `tidkey` (`p_tid`,`p__premoderate`,`p__time`)
d. Переделываем конец запроса к такому виду:
) ENGINE=MyISAM AUTO_INCREMENT=XXXXXXX DEFAULT CHARSET=cp1251
PARTITION BY RANGE(`p_tid`) (
PARTITION post_tid_0050 VALUES LESS THAN(50),
PARTITION post_tid_0150 VALUES LESS THAN(150),
PARTITION post_tid_0200 VALUES LESS THAN(200),
PARTITION post_tid_0250 VALUES LESS THAN(250),
PARTITION post_tid_0300 VALUES LESS THAN(300),
PARTITION post_tid_0350 VALUES LESS THAN(350),
PARTITION post_tid_0400 VALUES LESS THAN(400),
PARTITION post_tid_0450 VALUES LESS THAN(450),
PARTITION post_tid_0500 VALUES LESS THAN(500),
.........
Сколько там у вас тем есть и ожидается. Разбивка 50 тем на партицию.
.........
PARTITION post_tid_5000 VALUES LESS THAN(50-0),
PARTITION post_tid_max VALUES LESS THAN(MAXVALUE)
);
Сохраняете файл.
e. Заходите в mysql.
f. \u ваша_бд_форума (выбираем базу)
g. \.XXX_Post_str.dmp XXX_Post_str.dmp (Загружаем структуру)
h. \.XXX_Post_data.dmp XXX_Post_data.dmp (загружаете данные)
i. exit
Всё. Чёрное дело сделано.
* примечание XXX - префикс вашей таблицы.

6) Проверяем как работает.
Пример с темой 144. Выберете свою тему.
mysql> explain partitions select count(p_id) from ваш_префикс_Post where p_tid=144;
+----+-------------+-----------+---------------+------+---------------+------+---------+-------+------+-------+
| id | select_type | table | partitions | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+-----------+---------------+------+---------------+------+---------+-------+------+-------+
| 1 | SIMPLE | XXX_Post | post_tid_0150 | ref | tid,tidkey | tid | 4 | const | 298 | |
+----+-------------+-----------+---------------+------+---------------+------+---------+-------+------+-------+
1 row in set (0.01 sec)

До запуска партицианирования выполнялось около 1 секунды. Тут видно, что используется партиция post_tid_0150

Если что-то совсем не понятно - ищите админа fisher.spb.ru
Gram
Администратор

Gram
Откуда: Нижний Новгород
Всего сообщений: 1011
Рейтинг пользователя: 38


Ссылка


Дата регистрации на форуме:
23 июля 2003
Запросы тоже нужно менять будет?
Gich
Почетный участник

Gich
Всего сообщений: 123
Рейтинг пользователя: 6


Ссылка


Дата регистрации на форуме:
10 нояб. 2006
Gram
Запросы менять не нужно. Но пока как показала практика отвалился поиск по fulltext индексам. Проблема находится в стадии решения. В ближайшее время решу и напишу тут как лечить

Прелесть партиционирования - всю эту возню выполняет mysql не напрягая программиста.
aerograf
Модератор форума

aerograf
Всего сообщений: 486
Рейтинг пользователя: 15


Ссылка


Дата регистрации на форуме:
29 дек. 2007
Gram может изначально внести в дистрибутив? Или в доки к дистрибутиву...
Gich ждемс с нетерпением :-)



Всех с Рождеством!!!

assessor
Долгожитель форума


Всего сообщений: 495
Рейтинг пользователя: 14


Ссылка


Дата регистрации на форуме:
13 фев. 2007
Приветы всем! А если сервер держит 2 000 посетителей одновременно- нужно эту доработку делать?
Gich
Почетный участник

Gich
Всего сообщений: 123
Рейтинг пользователя: 6


Ссылка


Дата регистрации на форуме:
10 нояб. 2006
Присоединяюсь к поздравлениям!

assessor Вопрос не в количестве пользователей, а скорее в их качестве ).
Либо моему серверу в музее прогулы ставят. Ну железо там не первой свежести, но и не третьей...

Когда надо делать этот апгрейд.:
1) Средняя нагрузка около 200 постоянно присустствующих пользователей
2) Большая "дительность" активных тем по времени (некоторые открыты в 2003 и в них туева хуча сообщений)
3) Вес таблицы _Post около 400 мегабайт и более
4) Значительное число длинных сообщений: боле чем в 2 раза длиннее того, которое вы сейчас читаете
5) Общее число сообщений близко к миллиону

Симптоматика:
Время проявления от "не было" до звонка в датацентр "отправьте пожалуйста сервере в ребут" примерно 2 недели. (как раз в конце отпуска или в самой его середине).
- диагностика: отключить нагрузку от форума. Либо тестить в ночной минимум
а. время выполнения запросов главной форума 0,001-0,02
б. время выполнения запросов списка тем раздела 0,001-0,02
г. время выполнения запросов при открытии темы 0,01-0,5 - этот параметр мониторить! Добавлю! если на mysql включено кеширование, это значение справедливо только для !первого! входа в тему, при условии, что её пользователи не смотрели 2-5 минут. От части по этой причине диагностика производится только в часы минимальной нагрузки или в даунтайм. В час пик вы ничего не поймёте. Там от других "источников" возрастает время выполнения запросов при открытии топика.

По опыту. Динамика роста времени выполнения запросов от 0,02 до 5-10 секунд итд в час-пик - 3 недели. Я первое время думал, что червяка форум сожрал, тем более что соседний ресурс подвергался попыткам взлома. На проблему вышел уже через анализ выполнения запросов на открытии топика. Чему был сильно удивлён.
Gich
Почетный участник

Gich
Всего сообщений: 123
Рейтинг пользователя: 6


Ссылка


Дата регистрации на форуме:
10 нояб. 2006
Что касается "не прошенного" но "предвиденного" эффекта (перефразируя Булгакова) - отвалившийся поиск по причине отключения fulltext индексов. Как пишут в одном из багрепортов - это недокументированная фича mysql. fulltext индексы - только для не партиционируемых таблиц! Надеюсь, что разработчики форума примут этот факт во внимание, тем более что фатальных различий по времени поиска между fulltext и LIKE методами я не заметил. Ну думает LIKE какое-то время . Так fulltext не быстр!
В печку лирику!

Мой код, который могу вам предложить, к сожалению без напильника не пойдёт. Это связано с глубокой модификацией системы поиска, и этот код применим без адаптаций только к ней. На моём форуме он двухступенчатый. Я уже выкладывал когда-то доработку поисковой системы. Вот она: http://intboard.ru/99/1942/

Для совместимостью с партиционированием я изменил:
1) механизм релевантности (на втором этапе поиска она игнорируется, да и она не нужна теперь там)
2) на первом этапе поиска добавлена радиоконопка: Искать как: фразу () или () набор слов ? (Набор слов - по сути оригинальный поиск без кавычек. Фраза - оригинальный поиск с кавычками.) Все остальные условия доппоиска отстрелены как не нужные. Ими за 8 лет ни кто не пользовался ни разу (судя по логам).
3) механизм fulltext заменён на LIKE.

Далее представлю вашему внеманию пинцип модификации запросов:
1) Изменяем вычисление переменной condition.
переменная $s_set определят что ищем? Фразу или набор слов. 0 - фраза. Набор слов разбивается указанным кодом на подусловия LIKE. При чём делает это, прошу заметить, особо извращённым способом. Разметка текста по пробелам. Пробел между словами заменяется на это %\' AND p.p_title LIKE \'%. Кончено костылём таким эпическим попахивает... Но работает отлично!

[q]
//$condition="p.p_text LIKE '%$text%' OR p.p_title LIKE '%$text%'";
// блочим оригинальный
if ($s_set==0) $condition="p.p_text LIKE '%$text%' OR p.p_title LIKE '%$text%'";
else{
$text=trim($text);
$text=str_replace(' ',' ',$text);
$text=str_replace(' ',' ',$text);
$text=str_replace(' ',' ',$text);
$text=str_replace(' ',' ',$text);
$text=str_replace(' ',' ',$text);
$text=str_replace(' ',' ',$text);
$text_p=str_replace(' ','%\' AND p.p_text LIKE \'%',$text);
$text_t=str_replace(' ','%\' AND p.p_title LIKE \'%',$text);
$condition="p.p_text LIKE '%$text_p%' OR p.p_title LIKE '%$text_t%'";
}
[/q]

!!!! код выше отображается не совсем корректно! в грядке из 5 одинаковых str_replace разное количество пробелов. от 2 до 7. Это элемент защиты от дибильных ошибок, чтобы LIKE-и не размножались бесконтрольно!


Вот так доаботаны запросы 2 ступени :
[q]
$sql = "INSERT INTO ".$GLOBALS['DBprefix']."SearchResult (srid,srpid,relevancy) ".
"SELECT $id,p_id, 10 AS relevancy FROM ".$GLOBALS['DBprefix']."Forum f, ".$GLOBALS['DBprefix']."Topic t, ".$GLOBALS['DBprefix']."Post p ".
"WHERE ($condition) AND ($sqldata) AND p_tid=t_id AND t_fid=f_id AND p_tid=$stem_search AND p__premoderate=0 $timelimit ORDER BY $order $descr $limit";
[/q]


[q]
$sql = "INSERT INTO ".$GLOBALS['DBprefix']."SearchResult (srid,srpid,relevancy) ".
"SELECT $id,p_id, 10 AS relevancy FROM ".$GLOBALS['DBprefix']."Forum f, ".$GLOBALS['DBprefix']."Topic t, ".$GLOBALS['DBprefix']."Post p ".
"WHERE ($condition) AND ($sqldata) AND p_tid=t_id AND t_fid=f_id AND p__premoderate=0 $timelimit ORDER BY $order $descr $limit";

[/q]

Вместо relevancy по сути число 10. Первое, что в голову пришло. В общем-то реливаси тут уже роли не играет. $condition генерирует мой код выше.

Вот так доаботаны запросы 1 ступени :

[q]
$sql = "INSERT INTO ".$GLOBALS['DBprefix']."SearchResult (srid,srpid,relevancy) ".
"SELECT $id,t_id, count(p.p_id) AS relevancy ".
"FROM ".$GLOBALS['DBprefix']."Forum f, ".$GLOBALS['DBprefix']."Topic t, ".$GLOBALS['DBprefix']."Post p ".
"WHERE ($condition) AND ($sqldata) AND t_fid=f_id AND t__pcount>0 AND p_id=t__startpostid $timelimit GROUP BY t_id ORDER BY $order $descr $limit";
[/q]


Всё аналогично, но relevancy тут вычисляется тупо через count(p.p_id). по сути число совпадений в теме. Чем больше совпадений - тем выше relevancy - тем выше она в результате поиска первой ступени. Тоесть тут:
http://intboard.ru/file.php?a=...1068282538

По моим ощущениям - качество поиска кратно лучше!

Оффтопик:
Люди... Ну почините плз баркоды! Даже ссылку-картинку не привинтить!





Gich
Почетный участник

Gich
Всего сообщений: 123
Рейтинг пользователя: 6


Ссылка


Дата регистрации на форуме:
10 нояб. 2006
Тут файл search.php директории forums
ПРЕДУПРЕЖДАЮ!заливать можно себе только если выполнен этот "народный" мод http://intboard.ru/99/1942/

Прикрепленный файл (search.php, 18811 байт, скачан: 637 раз)
Gich
Почетный участник

Gich
Всего сообщений: 123
Рейтинг пользователя: 6


Ссылка


Дата регистрации на форуме:
10 нояб. 2006
Тут файл search.php директории styles/ваш_набор_стилей
ПРЕДУПРЕЖДАЮ! заливать можно себе только если выполнен этот "народный" мод http://intboard.ru/99/1942/

Оффтопик:
У меня на форума загрузка файлов полностью переделана. Можно заливать до 4 файлов любых разрешенных типов, если фотки - то любого размера, на ходу пережимаются, ставятся водяные знаки форума. Загрузка пачкой.

У нас этот движок живёт, и очень жаль, что XXXXPRO похоронил его заживо...


Прикрепленный файл (search.php, 7607 байт, скачан: 659 раз)
assessor
Долгожитель форума


Всего сообщений: 495
Рейтинг пользователя: 14


Ссылка


Дата регистрации на форуме:
13 фев. 2007
Gich, здравствуй. Громадное спасибо за столь ценную информацию. Но ... я, по крайней мере, не готов к её применению: жизнь еще не заставила и не разбираюсь в таких тонкостях.

Gich написал:
[q]
У нас этот движок живёт, и очень жаль, что XXXXPRO похоронил его заживо...
[/q]
Так и у нас живет. Мы детей своих выкармливаем, и до внуков дожили и до правнуков, б-г даст доживем вместе с движком. \":thumbup\"

<<Назад  Вперед>>Модераторы: aerograf, wsxПечать
Intellect Board — cистема управления сайтом »   Техническая поддержка версии 2.22 »   Перегрузка сервера.
RSS

1 посетитель просмотрел эту тему за последние 10 минут
В том числе: 1 гость, 0 скрытых пользователей

Последние RSS
Ограничение доступа
не отображаются разделы
Архив версий
Установка стиля на Intellect Board 2.22
Завершилась работа над новой версией 3.00

Самые активные 5 тем RSS


Время выполнения скрипта: 0.0824. Количество выполненных запросов: 17, время выполнения запросов 0.0000
Creative Commons License Rambler's Top100 Rambler's Top100 Рейтинг@Mail.ru Valid HTML 4.01 Transitional Valid CSS!