Привет, Хабр! Меня зовут Сергей Качкин. Вместе с командой я несколько лет занимался тестированием производительности систем хранения данных: много тестов делали сами, видели результаты наших коллег и заказчиков. Так у нас накопилось некоторое количество опыта, которым хочется поделиться.
В этой статье я расскажу про тестирование блочных стораджей. Начнем с теории — поговорим о выборе цели теста, отличиях синтетики от реальных нагрузок, выборе инструмента для генерации нагрузки. Затем перейдём к практике — тестированию случайного и последовательного доступа, измерению масштабируемости СХД.
Для тех, кто любит смотреть видео: доклад на эту тему я рассказывал на Перфоманс конф #8.
Выбор цели теста
Самое важное на старте тестирования — определить для себя, зачем это всё. Начинать тест с мыслями «так правильно», «так говорит руководитель» или «в инструкции написано, что должен быть какой‑нибудь тест перфоманса» — плохая идея. Есть ситуации, когда тест помогает, но иногда только вносит путаницу и добавляет вопросов. Поделюсь наблюдениями из практики.
Тестировать есть смысл, если:
вы хотите убедиться, что ваша СХД тянет эталонную нагрузку, которую вы знаете;
нужно локализовать аппаратную проблему или боттлнек;
вы просто из любопытства изучаете СХД, с которой вы работаете.
В тестирование лучше не лезть, если:
вы не знаете, что конкретно вы хотите;
вы хотите с помощью синтетики имитировать поведение сложного приложения (например, базы данных);
вы хотите воспроизвести проблему с продуктива в тестовом окружении c помощью синтетики.
Часто в такой ситуации вы думаете: «Ага, сейчас я воспроизведу её в тестовом окружении и спокойно, не торопясь, отдебажу». Но вместо решения вы можете получить две непонятных нагрузки: одну на продуктиве, вторую в тестовом окружении. Они будут совершенно разными по природе, но похожими по симптому. Законы Мёрфи тут срабатывают удивительно надёжно. Синтетические тесты плохо воспроизводят реальность. По субъективному опыту, лучше окунуться в трассировку запросов, статистику и логи с продакшена.
Отличия синтетики от реальных нагрузок
Почему синтетика не воспроизводит реальность? На самом деле, проблемы всего две: пространство и время.
Скорость поступления запросов реальных приложений
Время — это интервал между запросами. В синтетике скорость поступления запросов — это всегда какой-то случайный процесс с известным распределением: либо это равномерное распределение, либо это пуассоновский процесс, но это всегда что-то определённое.
В реальной жизни, если верить исследователям, скорость поступления запросов — это самоподобный процесс. Это значит, что в нём случается много выбросов, вне зависимости от масштаба выборки. Предположу, что возникают они из-за того, что в системах есть точки синхронизации. В файловых системах — fsync(), в базах данных — чекпоинты, когда большое количество блоков сливается в СХД разом. Эти выбросы в реальной жизни часто являются источником проблем — роста времени отклика, переполнения очередей и так далее.
Пятно данных
Вторая проблема — это пятно данных. Опять же, в синтетике мы чаще всего обращаемся к блокам случайно по заданному пятну данных или всей поверхности. В реальной жизни, если верить разработчикам теста SPC, вероятность повторного обращения к блоку зависит от времени с момента первого обращения. Если мы что-то «потрогали», скорее всего, мы сразу повторим это, а если нет, вероятность сильно снижается.
Однако, даже зная то, что синтетика не воспроизводит реальную жизнь, всё равно есть смысл ею заниматься: системы хранения данных разрабатываются, продаются и принимаются с синтетикой, и только потом — уже у заказчика — они встречаются с реальной жизнью.
Выбираем инструмент
Чем чаще всего пользуются инженеры, когда начинают тестировать диски? Классика — dd, cp и им подобные инструменты. Это плохо работает: они однопоточные, умеют воспроизводить только последовательные паттерны и дают крайне мало статистики на выходе.
Нагружайте СХД специальными утилитами. Их много, однако почти все давно заброшены. Из того, что можно использовать, и того, что применяем и мы, и заказчики, остались только fio и Vdbench.
Vdbench
Vdbench — инструмент, который хорошо прижился в энтерпрайзе. Многие наши заказчики тестируют с его помощью свои дисковые массивы, мы тоже его используем. Он логично сделан, у него понятная структура настроек, он кроссплатформенный, на нём можно компоновать сложные составные паттерны.
Но есть и минусы. Он умер в 2008 году. Второй недостаток (если первого недостаточно) — в нём нет асинхронного ввода-вывода. Тем не менее, Vdbench используется в повседневной работе — и у нас, и у заказчиков.
fio
Де-факто стандартом для тестирования блочного доступа является fio. В 2023 году это единственное, что стоит использовать. Его автор — Йенс Аксбо (Jens Axboe) — тот самый инженер, который разрабатывает блочный стек Linux. Соответственно, все новые фичи Linux сразу поддерживаются в fio. Инструмент гибкий, в нём много опций логирования и отчетов, к нему много готовых обёрток и парсеров, он постоянно дорабатывается.
Из минусов — в fio легче запутаться в настройках. В нём меньше возможностей, чтобы делать составные нагрузки. Вы не всегда сможете полностью перенести проект из Vdbench. Есть шанс налететь на баг, особенно в варианте клиент-сервер.
Тестирование случайного IO
С инструментом определились, теперь поговорим про сами нагрузки. Исторически они разделяются на случайный доступ и последовательный (тяжелое наследие механических жестких дисков, в которых паттерн влияет на скорость). Сейчас чаще всего мы встречаемся со случайным доступом. Это типовая нагрузка для SSD-дисков. Основные целевые приложения — базы данных. Они требовательны ко времени отклика, и их часто размещают на SSD.
Как правило, это мелкий блок (4k-32k) и какое-то соотношение чтение-запись (например, 70/30). Размером пятна данных мы регулируем количество кэш-хитов.
Частный случай — если надо проверить пропускную способность СХД с SSD дисками. Тут можно сделать большой блок (>128КБ).
Выбираем размер очереди
Есть один параметр, на который стоит обратить внимание — глубина очереди (IO depth). Её указывают во всех тестах, но никто не объясняет, как выбрано значение. Если вы возьмёте любой бенчмарк дисков, там будет написано: «Протестировано с такой-то глубиной очереди». Но почему именно такой?
Глубина очереди связана с результатом по закону Литтла:
Мы задаём на входе теста глубину очереди и на выходе получаем какое-то произведение IOPS и времени отклика (latency). Например, у нас есть требование: 100K IOPS со временем отклика 1 мс.
cлучайная нагрузка, 8KiB, чтение/запись = 70/30,
100 000 IOPS,
Время отклика — 1 мс.
Считаем очередь по закону Литтла:
Значит очередь должна быть 100 — ни больше, ни меньше. Дальше мы запускаем тест с очередью 100 и смотрим, получится ли 100 000 IOPS.
Может получиться:
200k IOPS, latency 0.5 ms,
10K IOPS, latency = 10 ms,
50K IOPS, latency = 2 ms.
Также закон Литтла можно переписать иначе:
И это тоже может стать основой теста. Мы сообщаем fio или Vdbench, сколько IOPS мы хотим получить, и утилита сама подберёт за нас нужную очередь. Такой подход «наоборот» тоже полезен. Он хорошо подходит для длительных тестов. Допустим, просим 100K IOPS и оставляем на неделю. Или начинаем делать СХД «больно» разными способами. В таком тесте хорошо видно влияние фоновых процессов, скрабберов, ребилда пула или влияние отказа компонентов, репликации и снэпшотов. Это удобно: мы видим, насколько отказы и дополнительные функции влияют на время отклика.
Измеряем масштабируемость дисковой подсистемы
Что делать, когда требования по производительности не сформулированы? Допустим, запрос на тестирование от заказчика или руководителя звучит просто и лаконично: «Надо измерить производительность стораджа». Измерение масштабируемости может помочь решить задачку.
Из теории мы знаем, что при росте нагрузки в какой-то момент производительность (IOPS) расти перестанет, а будет увеличиваться только время отклика (latency). Причём для разных конфигураций СХД насыщение будет наступать в разные моменты.
Поэтому когда нет чёткой цели на тестирование, будем увеличивать очередь и найдём область насыщения. В качестве производительности СХД будем показывать точку 95% утилизации системы и точку, где время отклика не превышает 1 мс. Тут нет тайного смысла, просто надо выбрать что-то конкретное и заданное в цифрах.
Для поиска этих точек и визуализации удобно использовать Universal Scalability Law. Это расширение закона Амдала, в который добавлен еще один компонент. Статья-первоисточник про USL выложена тут. Есть готовые проекты на R (и судя по всему, исследователи предпочитают использовать именно его — все последние апдейты заезжают в проект на R). Есть и проект на Python, тоже вполне рабочий.
Суть в том, что вы делаете несколько обмеров с разной глубиной очереди, дальше готовая библиотека вычисляет коэффициенты alpha, beta, gamma, которые описывают график.
На графике вы наглядно видите, в каком диапазоне очередей у вас система масштабируется, а где она уходит в насыщение (т.е. где IOPS перестают расти).
В тестировании web-сервисов, насколько я слышал, часто увеличивают нагрузку до некоторого процента отказов в обслуживании. К дискам такое неприменимо, отказов быть не должно никогда.
Важный момент, который надо проговорить: мы тестируем СХД целиком, а не отдельный диск. СХД — это софт, шины, кэши, медиа. В этом тесте мы не всегда требуем, чтобы диски были в “steady state” и считаем, что они FOB (fresh out of box). То есть на выходе мы получаем максимальные цифры, которые позволяет СХД. Если мы хотим более приближенные к жизни цифры, надо делать поправку на характеристики дисков с учётом числа, модели конкретного SSD и следовать методике SNIA.
Тест устоявшегося состояния СХД осложняется тем, что у нас нет прямого доступа к SSD диску, чтобы гарантированно прописать весь объем SSD с нужной интенсивностью. СХД может резервировать часть пространства под spare, и гарантированно прописать весь объем SSD не получится. Тестирование устоявшегося состояния в СХД с SSD — тема для отдельной статьи.
Вывод: результат теста мы считаем максимальным «попугаем», на который способна СХД. К примеру, для Татлин Unified с 24 NVMe дисками и iSCSI подключением к двум хостам, график получается вот такой.
По графику видно, что 95% утилизации система достигает при очереди 246 и скорости в 290K IOPS.
При этом 300K IOPS получается при очереди 300 с временем отклика 1 мс. Это вычисленное значение должно быть близко к максимуму этой конфигурации.
Можно запустить тест в одной точке на более долгое время, например, на 24 часа. График даёт понимание, как выбранная нагрузка расположена по отношению к точке насыщения системы.
Паттерн fio:
[global]
ioengine=libaio
direct=1
size=100%
group_reporting=1
time_based
randrepeat=0
ramp_time=60s
rw=randrw
numjobs=5
iodepth=30
runtime=24h
blocksize=8k
rwmixread=70
write_lat_log
write_bw_log
write_iops_log
write_hist_log
log_hist_msec=1000
log_hist_coarseness=4
log_avg_msec=1000
[oltp]
# десять сырых multipath устройств
host1
read: IOPS=113k, BW=881MiB/s (924MB/s)(72.6TiB/86400003msec)
write: IOPS=48.3k, BW=378MiB/s (396MB/s)(31.1TiB/86400003msec);
host2
read: IOPS=99.9k, BW=780MiB/s (818MB/s)(64.3TiB/86400001msec)
write: IOPS=42.8k, BW=334MiB/s (351MB/s)(27.5TiB/86400001msec.
Тестирование последовательного доступа
Тест потоковых нагрузок — чаще всего просто головная боль. Этот тип нагрузок характерен для механических жестких дисков. Это бэкапы, стриминг медиа, архивы. Это всегда что-то большим блоком — 128K–1024K. Если у вас случайная нагрузка, то скорее всего вам понадобятся SSD, если потоковая, то можно рассматривать обычные механические жесткие диски.
Проблема в том, что идеального последовательного IO не существует в обычной жизни. Чаще всего в тестах подразумевается тест в один поток. По крайней мере, в большинстве синтетических тестов это так. И это страшно далеко от реальности, в которой всегда есть несколько открытых файлов, несколько потоков бэкапа, несколько фильмов, которые пользователи смотрят одновременно. Сегодня потоковой нагрузкой заказчики обычно называют нагрузку, в которой можно выделить отдельные последовательные потоки, а не просто один поток.
Появляется вариативность настроек, из-за которой приходится делать исследовательскую работу. По-хорошему, для каждого теста надо уточнять, что именно считается потоковой нагрузкой в конкретном случае.
Часто требование для резервного копирования формулируется просто в МБ/c, например, «надо 3000 МБ/c». Но на практике это 10 потоков по 300 МБ/с, или 100 по 30? Для СХД это две большие разницы.
Как следствие, для потоковых нагрузок подходят две метрики.
Скорость на один поток в МБ/c. Определяется временем отклика СХД.
Общая пропускная способность на все потоки в МБ/c.
Потоковая нагрузка и самая частая ошибка с fio
Популярная ошибка с потоковой нагрузкой на сырых устройствах и fio — это увеличивать количество потоков, не разнося их по пятну данных. Это много где описано, но все всё равно наступают на эти грабли (и мы тоже).
[global]
direct=1
ioengine=libaio
rw=read
bs=128k
iodepth=4
numjobs=2
[sda]
filename=/dev/sde
Пятно данных обоих потоков будет выглядеть вот так:
Так делать не надо. Когда вы задаете в fio несколько потоков, они все начинают читать с начала диска. Соответственно, при первом обращении данные попадут в кэш. Вы получите кэш-хиты там, где вы их не ждали. Результат будет искажённый.
Как сделать лучше? Например, так:
[global]
ioengine=libaio
direct=1
size=100%
rw=randread:500
numjobs=2
iodepth=4
blocksize=256k
[sda]
filename=/dev/sda
Пятно данных выглядит примерно так:
Через 500 запросов каждый поток «прыгает» в случайный блок на диске. Таким образом есть надежда, что они не пересекутся. Вот ещё один пример.
[global]
ioengine=libaio
direct=1
rw=read
bs=256k
size=20%
offset_increment=20%
numjobs=5
iodepth=4
[sda]
filename=/dev/sda
Получается пять потоков fio, равномерно распределённых по поверхности.
Мы делим дисковое пространство на 5 областей (size=20%) и запираем каждый поток в свою область. Таким образом, мы покрываем все пространство диска. Это более предсказуемый паттерн.
Если нужна файловая система, то каждому потоку даем свой набор файлов, который они будут заполнять.
[global]
thread
direct=1
ioengine=libaio
rw=write
blocksize=256k
file_service_type=sequential
nrfiles=140
filesize=10g
numjobs=8
iodepth=8
[archive]
directory=/mnt/
Моё личное мнение про файловую систему — если есть возможность, лучше её не использовать. Она добавляет сложных компонентов: файловый кэш, журнал транзакций, алгоритмы оптимизации (read ahead, flush behind). Кроме того, невозможно проконтролировать, к каким блокам на диске мы обращаемся. Всё это будет искажать результаты.
На эту тему есть статья Benchmarking file system benchmarking: it *IS* rocket science, где наглядно описано, что все существующие бенчмарки файловых систем не очень хорошо работают. Поэтому, если условия позволяют упростить тест, лучше делать его на сырых устройствах.
От простых нагрузок больше пользы
Когда говорят о тестировании сложных СХД, часто рекомендуют делать составные нагрузки, имитирующие сложные приложения (OLTP, OLAP, VDI, и т.д.).
Например:
«горячие» и «холодные» зоны на диске;
смесь блоков разных размеров;
смесь последовательного и случайного доступа.
По моему субъективному опыту, от простых однокомпонентных нагрузок пользы больше. Да, это меньше похоже на реальные приложения и «продаётся» хуже. Если вы инженер и тестируете хранилище, от вас будут просить более реалистичные сценарии, составные паттерны. Все хотят видеть, как на вашей системе будет работать какой-нибудь Postgres, а не ваши 100 000 IOPS на странной синтетике 70/30 8K.
У меня есть несколько аргументов против составных нагрузок. Во-первых, это всё равно не будет похоже на реальное приложение, как я писал выше. Во-вторых, сложно анализировать, как это всё работает внутри СХД. В-третьих, такую нагрузку сложнее масштабировать. Не всегда можно корректно добавить 10% к напору. И последнее — если это «продающий» бенчмарк, который вы используете в маркетинге, то будут возникать сомнения, что нагрузку подогнали под нужный результат.
В статье я постарался описать особенности тестов производительности блочных СХД. Некоторым моментам обычно уделяют недостаточно внимания, например осознанному выбору размера очереди. Если цель тестирования не сформулирована в цифрах, можно попробовать оценить масштабируемость СХД. Тесты потоковой нагрузки можно делать многими разными способами и часто выбор непрост. Привёл пример с реальным TATLIN.UNIFIED. Надеюсь, это будет кому-то полезно.
Комментарии (17)
Thomas_Hanniball
00.00.0000 00:00+3Клиент, который покупает СХД, хочет знать:
1. Насколько новая железка быстрее того, что у него уже есть.
2. Насколько она быстрее того, что предлагает второй вендор в этом же ценовом диапазоне.
Клиент обращается к вендору с вопросом, насколько быстра СХД, ожидая в ответ получить какие-то цифры или индексы, а по факту вендор предлагает клиенту самостоятельно выполнить всё тестирование.
А почему вендор не может самостоятельно провести всё тестирование и потом просто опубликовать результаты этих тестов в открытый доступ? Зачем клиенту тратить своё время на тестирование, изучение кучи методик тестирования, чтобы вендор потом говорил: ой, да вы не правильно всё протестировали, надо было не синтетику запускать, а тестовые сценарии. Ой, да и тестовые сценарии тоже не подходят, надо на продуктиве всё смотреть и так до бесконечности.
Отсутствие цен в открытом доступе — это вторая проблема. Все цены только по запросу. Причём если делать запросы от разных компаний, то и цены будут разными.13werwolf13
00.00.0000 00:00+2А почему вендор не может самостоятельно провести всё тестирование и потом просто опубликовать результаты этих тестов в открытый доступ?
а вы замените в вашем тексте "всЁ тестированиЕ" на "всЕ тестированиЯ" и сразу станет понятно. под разные виды нагрузок существуют разные тесты, всё это помножается на кол-во файловых систем, на кол-во вариантов наполнения дисковой полки, на кол-во самих полок и контроллеров и так далее почти до бесконечности. даже заранее зная что хочешь протестировать и под какую задачу тратишь на это очень много времени, а чтобы протестировать все возможные вариации уйдут годы. но согласен что вендору бы выкладывать результаты тестирований которые делались для клиентов, так за пару лет можно набрать очень хороший набор результатов под разные кейсы.
Отсутствие цен в открытом доступе — это вторая проблема. Все цены только по запросу. Причём если делать запросы от разных компаний, то и цены будут разными.
а вот тут полностью согласен, мне кажется за плашку "цена по запросу" надо лишать возможности вести бизнес раз и навсегда
BenderH
00.00.0000 00:00не забывайте про наличие "шаблонных" нагрузок, которые встречаются у пользователей в 70-80%% случаев. Например — MSSQL. Или — серверная 1С, файловая 1С. И от пользователя к пользователю — характер нагрузки врядли изменяется. Чаще всего такие тесты и интересны.
13werwolf13
00.00.0000 00:00И от пользователя к пользователю — характер нагрузки врядли изменяется.
изменяется, и довольно сильно. мы можем взять типовые тесты для pgsql сервера, подобрать при и помощи железо которое покажет лучшие результаты, а потом в бою узнать что характер нагрузки постгри при работе с неким конкретным ПО всё же сильно отличается и не туда смотрели.. проходили знаем..
BenderH
00.00.0000 00:00При чем тут «типовые тесты для pgsql»? Есть стандартные нагрузки ограниченного списка приложений. И 1С — одно из этого списка. А не сферический конь в sql...
NKulikov
00.00.0000 00:00+1У большинства вендоров есть калькуляторы - вы забиваете (или отправляете) требуемые характеристики СХД (емкость, производительность, интерфейсы и т.д.), а в ответ получаете какую модель и в какой конфигурации надо купить для этого.
К тому же многие публикуют результаты тестов (сами или кто-то другой тестирует и публикует). Но вопрос в том - какое отношение имеют тесты, проведенные кем-то другим, по их методике, под их нагрузкой и в их конфигурации для конкретно вашего случая и ваших задач? В общем случае, никакого. Поэтому и берут (точнее должны брать) системы на тесты, чтобы проверить не коня в вакууме, а провести релевантный для конкретно вашего случая тест.
А чтобы не было "ой, да вы неправильно всё протестировали" согласуйте методику тестирования ДО её проведения и всё.
ZloyHAN
00.00.0000 00:00+1Потому что все потом грустят: как же так, оно неправильно работает и цифры не те
13werwolf13
00.00.0000 00:00Тестировать есть смысл, если:
- вы просто из любопытства изучаете СХД, с которой вы работаете.
В тестирование лучше не лезть, если:
- вы не знаете, что конкретно вы хотите;
простите, но это разве не одна и та же причина у вас одновременно и в "за" и в "против"?
kachini Автор
00.00.0000 00:00хм, вы правы, действительно сложно отделить одно от другого. Может быть, разница в осознанности действий. В одном случае её больше, чем в другом.
vasek07
00.00.0000 00:00А как вы относитесь к SPDK Performance Reports. Мы как то больше на него ориентированы в тестах СХД. Рекомендации вендора - реально мало интересны. Т.к. по сравнению с этим документом - у них маркетинговый/детский лепет - особенно привычка перформанс одного диска умножать на всю полку дисков или даже кластер и отключать все виды синхронизации.
vasek07
00.00.0000 00:00Вы в курсе что есть SNIA (Storage Networking Industry Association) по VPN сейчас доступен - у него сто лет как есть Solid State Storage (SSS) Performance Test Specification (PTS). Чтобы хотелось от СХД поставщиков - это тест (SPDK или PTS) на голой операционке и точно такой же тест с установленной СХД - например на RAID6 с дедупликацией и сжатием. Иначе читаешь - сообщение о данных теста как записки сумасшедшего. У вас в компании - наверняка есть такие тесты - вот они реально интересны. Если руководство вам разрешит - лучше о них напишите.
kachini Автор
00.00.0000 00:00PTS тоже не идеальна. Например, в части последовательно доступа , тест только с TC1/QD32 - какой вывод из этого можно сделать? Кмк, это взяли с HDD, и перенесли на SSD. Часть тестов XSR, CBW ,.. - выглядят несколько хммм.. академично.
SPDK пишут отличные full disclosure report, но у них просто коробка с дисками, подключённая по NVMe, это всё таки не СХД и проверяют они софтовый стек.
dizh
Спасибо, прям хорошо!
Ждём вторую часть про то, как сдернуть профиль рабочей нагрузки (с тем самым пятном) с существующей инфраструктуры заказчика для воспроизведения на стенде.
NKulikov
Я вот тут не много писал об этом Enterprise Storage Synthetic Benchmarking Guide and Best Practices. Part 2. Success Criteria and Benchmarking Parameters.
kachini Автор
Оо.. интересный материал, спасибо. Но не могу отделаться от настороженного отношения к HCIbench. Однокомпонентные нагрузки как-то понятнее, без Random/Sequential Ratio, например. Но когда виртуалки и облака, видимо всё равно к этому приду.
NKulikov
Enterprise СХД крайне редко работают только на одну нагрузку (если мы не говорим про отдельные кейсы, когда СХД целиком отдается под один приклад типа АБС или mission-critical СУБД), обычно источником нагрузки является множество клиентов/приложений и т.д. Поэтому и тестировать их надо под такой же смешанной нагрузкой, ибо это обычно намного релевантнее и ближе к действительности.
А насчет HCIBench - это просто обвязка по автоматизации и GUI над теми же vdbench и FIO. Сам по себе он не генерирует никакую нагрузку - он просто деплоит worker'ы, создает конфигурационный файл в зависимости от того, что вы накликали в интерфейсе, разливает его воркеры, а потом собирает результаты. Ровно то же самое вы можете сделать в fio/vdbench руками. Я об этом тоже упоминал, но в первой части статьи :)
При этом вам абсолютно ничего не мешает развернуть хоть только одну ВМ через него и тестировать обычный datastore c SAN/NAS СХД. Сам профиль тестирования может быть тоже абсолютно любой - просто создайте конфигурационный файл fio/vdbench руками и загрузите в HCIBench. Но надо отметить, что работает он только с vSphere.
kachini Автор
да, посмотрел все части и трогал HCIbench тоже. ) Я встречался с результатами HCIbench от заказчиков и было много спорного и непонятного (для меня). Насколько адекватно выбрана смешанная нагрузка - вопрос. Как понять, насколько она правильно выбрана? Верить разработчикам HCIbench на cлово? Например, в некоторых тестах 90% рандом, а почему именно 90%? Зачем нужны 10% seq и почему 10, а не 5 и не 20%. Где-то должно быть обоснование, но я не встречал.
Я защищаю идею, как и в статье, что от простых нагрузок пользы больше по результату. Но это просто имхо, жизнь заставит возиться со смешанными, буду..