Как стать автором
Обновить

Идеальный каталог, замеры производительности

Время на прочтение5 мин
Количество просмотров2.7K

Всем привет.

Я разрабатываю библиотеку для работы с Entity Attribute Value (репозиторий), сокращенно EAV (модель базы данных для хранения произвольных данных). В конце прошлой статьи я спросил у вас о чём мне ещё надо написать, вы попросили показать пример использования и сделать замеры быстродействия.

Что для нас важно при работе с данными ? Скорость записи (добавления или обновления) и скорость чтения (конкретно - фильтрации по моделям одной сущности). При чём скорость поиска в приоритете, потому что записываем мы один раз в цать дней, а читаем каждую минуту/секунду и даже не один раз, а может быть и не одну сотню раз.

Фишка библиотеки в том что бы работать не с представлением построенном на базовых таблицах EAV, а работать с небольшой частью этих данных записанных в отдельное материализованное представление или в отдельную таблицу.

В Новогодние каникулы я сделал замеры производительности и хочу с вами поделиться результатами.

Что будем измерять ?

Чтение:

  • Время вычитывания всех позиций категории

  • Время формирования параметров фильтрации

  • Время фильтрации

Запись:

  • Время добавления новой характеристики (атрибута)

  • Время добавления новой товарной позиции

  • Время обновления товарной позиции

Набор данных

История разработки библиотеки началась с разработки маркет плэйса, поэтому считайте, что мы работаем с каталогом товарных позиций.

Требования к набору данных

Для тестирования времени чтения из MATERIALIZED VIEW и из TABLE не так важно сколько записей было в исходных таблицах модели EAV, поэтому несколько сотен категорий будет достаточно для проверки гипотезы.

Характеристик у категории (и соответственно у товарной позиции) не больше 100 (для обычного интернет магазина это даже много, обычно характеристик у товара не больше пары десятков).

Характеристики набора данных

С учётом таких вводных,с помощью скрипта data-generator/generate.php, был создан набор данных:

  1. количество сущностей (категорий) - 320

  2. количество атрибутов (характеристик) - 144

  3. количество моделей (позиций во всех категориях) - 29 000

  4. числовых значений - 800 000

  5. строковых значений - 600 000

Суммарный объём EAV таблиц (с индексами) - 310 Мб.

Учёт вариативности данных

Объём данных в которых надо производить поиск (фильтрацию) имеет большое значение для времени поиска.

Разбиваем все сущности на три вида: много атрибутов, среднее количество и малое количество, выбираем по одной сущности из каждого вида:

  • Много - моделей 238, атрибутов 112, всего значений 26656

  • Среднее - моделей 75, атрибутов - 34, значений - 2550

  • Малое - моделей 4, атрибутов - 5, значений 20

Измеренные значения

Все измерения в миллисекундах

Сущность у которой много моделей и атрибутов

Много - моделей 238, атрибутов 112, всего значений 26656, фильтруем по 46 колонкам (из 112).

Чтение

Способ доступа

Получить все записи, без фильтрации

Получить фильтры

Отфильтровать

VIEW

400

382,6

82,8

MATERIALIZED VIEW

5

402,8

40,9

TABLE

4,9

395,9

46,1

Получить все записи без фильтрации из VIEW невозможно, потому что у нас как минимум один фильтр - по категории - уже должен быть. Почему получилось такое чудовищно большое время, я понять не могу.

Для измерения "Отфильтровать", производился отбор по 46 колонкам (из 112).

В том что касается чтения, то фильтрация по MATERIALIZED VIEW происходит на 10% быстрей чем по TABLE.

Запись

Способ доступа

добавить атрибут

добавить модель

обновить модель

VIEW

79,7

155,6

188,7

MATERIALIZED VIEW

1 338

1 112

1 462

TABLE

3

196,5

217

Добавление атрибута в представление это его пересоздание.

Добавление атрибута в MATERIALIZED VIEW это его полное обновление.

Добавление атрибута в таблицу это ALTER TABLE, поэтому всего 3 мс.

Добавление модели подразумевает под собой, создание записи в таблице thing и создание пустых значений в таблицах word и number. Соответственно 155 мс для представления, это вставка 112 записей в таблицу значений (числовые - number, строковые - word).

Для MATERIALIZED VIEW нам снова надо его полностью пересчитать - обновить целиком.

Для таблицы мы добавляем запись у которой будет 112 пустых колонок, это всего 40,9 мс, но добавление записи происходит на основе представления, поэтому 155,6 + 40,9 = 196,5.

Обновление записи (обновление всех 112 колонок) выполняется через обновлением данных в базовых таблицах EAV и затем:

  • Для представления этого достаточно;

  • Для MATERIALIZED VIEW нам снова надо всё полностью пересчитывать;

  • Для таблицы обновление происходит независимо от базовых таблиц, просто обновляется одна строка, но эта строка обновляется только после успешного обновления данных в базовых таблицах, поэтому мы видим 217 мс, по сути собственно обновление записи это 30 мс.

Выводы

Как мы видим использование MATERIALIZED VIEW даёт максимальный выигрыш по времени чтения (в два раза быстрей чем из представления и на 10% быстрей чем из таблицы), но при этом обновление данных занимает на порядок больше времени (проигрыш в 10 раз).

Использование таблицы, даёт выигрыш по чтению в два раза, а проигрыш по записи на 15%, и этот проигрыш обусловлен тем что мы ждём успешного обновления мастер данных, если не ждать то выигрыш будет в 6 раз.

Конечно, что бы не ждать, надо доработать напильником библиотеку, завести туда асинхронность или логику создания и выполнения джобов. Конечно, написать логику для eventual consistency.

Если мы обновляем данные в нашем "универсальном" каталоге раз в час, то потеря одной секунды на обновление несущественна, и это точно стоит того что бы получить дополнительный прирост 10% по сравнению с использованием таблицы.

Если обновления данных у нас происходит несколько раз за час, то я бы использовал таблицу.

Сущность у которой среднее количество моделей и атрибутов

Среднее - моделей 75, атрибутов - 34, значений - 2550, фильтруем по 14 колонкам (из 75).

Чтение

Способ доступа

Получить все записи, без фильтрации

Получить фильтры

Отфильтровать

VIEW

49,5

83

27,9

MATERIALIZED VIEW

1,7

69

12,3

TABLE

1,4

66

12,6

Запись

Способ доступа

добавить атрибут

добавить модель

обновить модель

VIEW

24,4

50

65

MATERIALIZED VIEW

207

212

242

TABLE

3

90

90

При обновлении записи, мы снова видим порядка 30 мс на собственно обновление записи в таблице, но по сравнению с 65 мс на обновление записи в базовых таблицах, это уже 50%.

Сущность у которой малое количество моделей и атрибутов

Малое - моделей 4, атрибутов - 5, значений 20, фильтруем по 2 колонкам (из 5).

Чтение

Способ доступа

Получить все записи, без фильтрации

Получить фильтры

Отфильтровать

VIEW

2,4

10

5,4

MATERIALIZED VIEW

1

13

4

TABLE

0,8

13

2,9

Запись

Способ доступа

добавить атрибут

добавить модель

обновить модель

VIEW

6,2

8,8

8,1

MATERIALIZED VIEW

29

19

27

TABLE

4,4

4,4

10,7

Общий вывод

С уменьшением количества данных, стирается разница между способом доступа к этим данным. Для средних категорий разницы по чтению нет, разница по записи всего в два раза.

Тем не менее общая тенденция сохраняется - поиск по материализованному представлению и таблице происходит в два раза быстрей чем по представлению созданному на основе EAV таблиц.

Если количество сущностей увеличить на порядок, то время поиска в "таблице" не измениться, а время поиска в представлении увеличиться (мне так кажется), поэтому конечно при работе с EAV следует использовать "таблицы".

Вопрос о том будет это материализованное представление, или это будет собственно таблица - решать надо исходя из баланса между чтением и записью.

Что дальше ?

В следующей статье я приведу пример использования библиотеки.

Надеюсь вам было интересно.

Только зарегистрированные пользователи могут участвовать в опросе. Войдите, пожалуйста.
Вам было интересно?
22.73% Что такое EAV?5
18.18% Да, было интересно4
45.45% EAV умер, не надо о нём писать10
13.64% NoSQL быстрее, могу доказать своим бенчмарком (пожалуйста, оставьте ссылку на исходники в комментариях)3
Проголосовали 22 пользователя. Воздержались 15 пользователей.
Теги:
Хабы:
Всего голосов 8: ↑4 и ↓4+2
Комментарии9

Публикации

Истории

Работа

PHP программист
168 вакансий

Ближайшие события

19 августа – 20 октября
RuCode.Финал. Чемпионат по алгоритмическому программированию и ИИ
МоскваНижний НовгородЕкатеринбургСтавропольНовосибрискКалининградПермьВладивостокЧитаКраснорскТомскИжевскПетрозаводскКазаньКурскТюменьВолгоградУфаМурманскБишкекСочиУльяновскСаратовИркутскДолгопрудныйОнлайн
24 – 25 октября
One Day Offer для AQA Engineer и Developers
Онлайн
25 октября
Конференция по росту продуктов EGC’24
МоскваОнлайн
26 октября
ProIT Network Fest
Санкт-Петербург
7 – 8 ноября
Конференция byteoilgas_conf 2024
МоскваОнлайн
7 – 8 ноября
Конференция «Матемаркетинг»
МоскваОнлайн
15 – 16 ноября
IT-конференция Merge Skolkovo
Москва
25 – 26 апреля
IT-конференция Merge Tatarstan 2025
Казань