ТестированиеНагрузочное тестированиеИнженер по нагрузочному тестированию

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

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

Проходите собеседования с ИИ помощником Hintsage

Краткий ответ

Одновременный рост метрик не доказывает, что первичным узким местом является ресурс с большей утилизацией. Нужно проверить причинность: провести контролируемое изменение одного ресурса или типа нагрузки и посмотреть, изменятся ли вслед за ним задержка, очередь и пропускная способность.

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

Исторический контекст

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

Поэтому диагностика постепенно сместилась от поиска ресурса с максимальным процентом загрузки к проверке того, какое изменение действительно улучшает поведение системы. Такой подход помогает не лечить симптом вместо причины.

Постановка проблемы

Предположим, при росте нагрузки CPU приложения достигает 85%, а время ожидания ответа базы увеличивается в несколько раз. Простое решение — масштабировать приложение или увеличить CPU, но оно может не дать результата, если основная задержка возникает в базе.

Обратная ошибка также возможна: команда оптимизирует запросы, хотя приложение тратит CPU на сериализацию, шифрование или бесконечные повторы. В результате тест может показать кратковременное улучшение отдельной метрики, но целевой SLA и пропускная способность не изменятся.

Подробное решение

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

Затем следует сопоставить события во времени и проверить направление зависимости. Рост ожидания базы, после которого растёт число занятых потоков приложения и его CPU, указывает на возможное распространение задержки вверх по цепочке. Но совпадение временных рядов само по себе недостаточно: общий всплеск нагрузки способен одновременно увеличить обе метрики.

Наиболее надёжный способ — контролируемая проверка с неизменным профилем запросов. Варианты проверки:

  • уменьшить стоимость запросов или задержку базы и сравнить CPU приложения, p95/p99, длину очередей и успешный RPS;
  • ограничить CPU приложения либо изменить его обработку и проверить, уменьшатся ли число запросов к базе и ожидание;
  • повторить тест с тем же RPS, но с другой долей операций, чтобы отделить стоимость бизнес-операций от общей интенсивности нагрузки.

Первичным следует считать не ресурс с самой высокой утилизацией, а ограничение, устранение которого улучшает целевые показатели без переноса узкого места в другой компонент. Важно контролировать побочные эффекты: ускорение базы может только быстрее перегрузить приложение, а увеличение CPU приложения — увеличить поток запросов к базе.

Ситуация из практики

В тесте оформления заказа CPU приложения достигал 82%, а ожидание базы занимало 40% времени запроса. Команда рассмотрела два варианта: добавить экземпляры приложения, что быстро увеличило бы вычислительный ресурс, но могло усилить нагрузку на базу, или оптимизировать медленный запрос, что требовало анализа плана выполнения и не гарантировало устранения CPU-затрат приложения.

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

Что кандидаты часто упускают

  1. Достаточно ли сравнить процент утилизации ресурсов, чтобы найти узкое место?

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

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

  1. Как отличить первичное ожидание базы от ожидания пула соединений приложения?

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

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

  1. Что делать, если оптимизация одного компонента сразу переносит узкое место в другой?

Это нормальный результат устранения ограничения в многоступенчатой системе. После каждого изменения нужно повторно измерять сквозную задержку, успешный RPS, ошибки, очереди и утилизацию всех существенных компонентов, а не объявлять успехом улучшение одной метрики.

Например, ускорение базы может увеличить поток ответов и перегрузить CPU приложения или сетевой канал. Корректная цель — найти конфигурацию, при которой система выдерживает требуемый профиль нагрузки и SLA; единственного постоянного узкого места у системы может не быть.