Гид по технологиям

Превышено время CPU Apex — причины и решения

5 min read Salesforce Обновлено 10 Dec 2025
Превышено время CPU Apex — причины и решения
Превышено время CPU Apex — причины и решения

Предупреждение: превышено время CPU Apex в Salesforce

Кратко

Apex CPU time limit exceeded — это ошибка Salesforce, которая возникает, когда транзакция использует слишком много процессорного времени. В статье объяснено, почему это случается, как быстро проверить распространённые причины и какие практические шаги предпринять для исправления и профилактики.

Ключевые причины

  • Логирование включено (LoggingEnabled = true). Дополнительная запись логов увеличивает нагрузку на CPU при массовых операциях.
  • Триггер выполняется несколько раз. После выполнения триггера срабатывают workflow/process builder, которые обновляют запись и снова вызывают триггер.
  • Глубокие вложенные циклы. Три и более уровней вложенности приводят к экспоненциальному росту операций и времени выполнения.
  • Код в управляемых пакетах. Внешний (managed) код может быть «чёрным ящиком» и потреблять много CPU без возможности правки — требуется помощь вендора.
  • Множество автоматизаций на одном объекте. Если на один объект навешано несколько Process Builder / Flow / Workflow, они суммируют нагрузку.

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

Как быстро диагностировать проблему

  • Включите системные логи и посмотрите статистику по времени CPU для транзакции.
  • Найдите повторяющиеся вызовы одного и того же триггера в логах.
  • Оцените, есть ли в процессе массовые операции (bulk) или массовые объёмы данных.
  • Посмотрите, какие автоматизации запускаются на том же событии (Process Builder / Flow / Workflow).

Предварительные проверки

  • Отключите необязательные Process Builder, если это возможно.
  • Перезапустите рабочую машину и убедитесь, что локальные проблемы (например, при локальном тестировании через CLI) не влияют.
  • Сведите к минимуму одновременные автоматизации на одном объекте.
  • Избегайте вложенных циклов. Часто Maps и Set позволяют заменить вложенные for.

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

Как исправить проблему

1. Отключите LoggingEnabled (если используется)

Если у вас есть кастомная настройка, которая включает подробное логирование в рабочем процессе, временно выключите её:

  1. Перейдите в окружение Lightning, нажмите шестерёнку Settings и выберите Setup.

Меню Настройки в Lightning

  1. В поле Quick Find введите Custom Settings и откройте Custom Settings.
  2. Найдите General Settings и нажмите Manage рядом с ним.

Ссылка Manage для Custom Settings

  1. Нажмите Edit рядом с LoggingEnabled.

Форма редактирования LoggingEnabled

  1. В поле Value установите false и сохраните.

LoggingEnabled обычно используется для отладки. В рабочем режиме оно редко нужно и только увеличивает вероятность таймаута.

2. Замените Process Builder на Flow

Process Builder часто добавляет скрытую нагрузку и многократно упоминался в сообщениях об ошибках CPU timeout. Salesforce рекомендует переход на Flow — он более эффективен и гибок.

Когда менять: если у вас сложные цепочки Process Builder с обновлением записей и вызовом других автоматизаций. Переносите логику в Flow, где можно контролировать bulk-обработку и уменьшать число обновлений.

3. Избегайте вложенных циклов и используйте Map-based подход

Типичная ошибка — проход по списку записей и внутри каждого элемента запускать ещё один цикл или запрос. Вместо этого используйте Map и операции в один проход.

Плохой пример (увеличивает CPU из-за внутреннего цикла):

List accList = [SELECT Id, Name FROM Account LIMIT 100];
Set setIds = new Set();
for (Account acc : accList) {
    // Дополнительная нагрузка из-за цикла
    setIds.add(acc.Id);
}

Лучший вариант — использовать Map и обращаться к данным напрямую без вложенных проходов. Пример с сопоставлением по Id:

Map accountsById = new Map([SELECT Id, Name FROM Account WHERE Id IN :someIds]);
// Доступ к записи по accountsById.get(id) — без вложенных циклов

Ещё один приём — собрать все Id, выполнить один SOQL-запрос с фильтром IN, затем в одном цикле обновить данные.

4. Bulkify триггеры и избегайте DML в циклах

Всегда пишите триггеры с учётом bulk (работы с коллекцией записей). Не допускайте DML-операций или запросов внутри for-циклов. Собирайте данные в коллекции, выполняйте один DML и один SOQL на «пакет».

5. Проверьте код управляемых пакетов

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

Альтернативные подходы

  • Использовать @future/@queueable для дорогостоящих операций, которые можно вынести асинхронно.
  • Переносить агрегации и тяжёлую обработку на внешние ETL/инструменты, если это уместно.
  • Разбивать большие транзакции на несколько меньших батчей.

Когда эти методы не работают

  • Если пакетный код вендора выполняет тяжёлые операции и вы не можете его изменить — нужна поддержка вендора.
  • Если бизнес-требования заставляют постоянно выполнять тяжёлые вычисления в единой транзакции — необходимо пересмотреть архитектуру.

Практическая методология (мини-план)

  1. Воспроизведите ошибку в sandbox.
  2. Снимите лог транзакции и проанализируйте источник CPU-горуза.
  3. Выполните быстрые исправления: выключите LoggingEnabled, отключите лишние Process Builder.
  4. Оптимизируйте код: bulkify, убрать вложенные циклы, использовать Map, избегать DML в циклах.
  5. Перенесите тяжёлую работу в асинхронные процессы при необходимости.
  6. Тестируйте и валидация: убедитесь, что количество ошибок и время транзакции снизились.

Проверки для ролей

Проверки для администратора

  • Отключены ли временно Process Builder для проблемного объекта?
  • LoggingEnabled установлен в false в проде и sandbox?
  • Какие managed packages взаимодействуют с объектом?

Проверки для разработчика

  • Триггер bulk-ready и нет DML/сообщений внутри циклов?
  • Используются ли Maps и Set для уменьшения вложенности?
  • Есть ли unit-тесты, покрывающие bulk-случаи и моделирующие большую нагрузку?

Критерии приёмки

  • Ошибка Apex CPU time limit больше не воспроизводится в sandbox при тех же входных данных.
  • Время выполнения транзакции снизилось и устойчиво в пределах дозволенных лимитов.
  • Нет регрессий в функциональности, автоматизации работают корректно.

Риски и способы смягчения

  • Риск: отключение логирования усложнит диагностику других ошибок. Смягчение: сохраняйте логи перед отключением и включайте выборочно для короткого времени.
  • Риск: перенос логики в асинхронный процесс меняет порядок выполнения бизнес-правил. Смягчение: документируйте изменения и обновите тесты.

Краткий глоссарий

  • Bulkify — писать код, который корректно обрабатывает коллекции записей.
  • DML — операции вставки/обновления/удаления записей в Salesforce.
  • Managed package — сторонний пакет с кодом, обновляемый вендором.

Короткая памятка (cheat sheet)

  • Проверить логи → выключить LoggingEnabled → отключить ненужные Process Builder → bulkify код → заменить вложенные циклы на Map → если нужно, использовать @queueable.

Итог

  • Превышение CPU обычно связано с лишними циклами, логированием, неоднозначной автоматизацией или сторонним кодом.
  • Быстрые победы: отключить LoggingEnabled и убрать лишние Process Builder.
  • Долгосрочные решения: оптимизация кода, bulk-ориентированная логика и перенос тяжёлых задач в асинхрон.

Если у вас остались вопросы или вы хотите пример мини-рефакторинга вашего триггера — опишите текущую логику в комментарии, и мы поможем с планом правок.

Поделиться: X/Twitter Facebook LinkedIn Telegram
Автор
Редакция

Похожие материалы

RDP: полный гид по настройке и безопасности
Инфраструктура

RDP: полный гид по настройке и безопасности

Android как клавиатура и трекпад для Windows
Гайды

Android как клавиатура и трекпад для Windows

Советы и приёмы для работы с PDF
Документы

Советы и приёмы для работы с PDF

Calibration в Lightroom Classic: как и когда использовать
Фото

Calibration в Lightroom Classic: как и когда использовать

Отключить Siri Suggestions на iPhone
iOS

Отключить Siri Suggestions на iPhone

Рисование таблиц в Microsoft Word — руководство
Office

Рисование таблиц в Microsoft Word — руководство