Обсудить задачу

DikLabГайдыn8n

Гайд · n8n · sheets

Пять мест, где сценарий n8n падает молча

8 минn8nsheets

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

Поставить это мне

Содержание

В чём фокус

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

Почему зелёный прогон ничего не доказывает

Статус ноды означает одно: вызов вернулся и не выбросил исключение. Он не означает, что строка записалась, что фильтр сработал или что обработались все записи.

Два примера, которые встречаются постоянно. PostgREST на UPDATE, не совпавший ни с одной строкой, отвечает 200 — для n8n это успех, хотя не изменилось ничего. Google Sheets в режиме автосопоставления пишет только те колонки, которые пришли во входных данных, — не пришло поле, ячейка просто осталась прежней, и ошибки не будет.

Отсюда рабочее правило: смотреть не на статус, а на то, что нода реально вернула.

Первое: Google Sheets не пишет ничего и говорит, что всё хорошо

Нода Google Sheets в операции «добавить или обновить» с автосопоставлением требует заполненную схему колонок — список всех столбцов листа, где столбец сопоставления помечен как пригодный для поиска. Если оставить только сам столбец сопоставления, а схему не заполнить, нода в момент выполнения падает с невнятным Could not get parameter.

Дальше начинается интересное. Если на ноде стоит «продолжать при ошибке», прогон помечается успешным, а в лист не пишется ничего. Симптом выглядит так: сценарий активен, прогоны зелёные, а таблица заморожена на дате последней рабочей записи.

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

Настройки ноды Google Sheets: выбран лист, режим Map Automatically и столбец сопоставления. Списка колонок на экране нет.
Автоматическое сопоставление: на экране три поля, а схема колонок живёт под капотом — по форме не скажешь, собрана она или пуста

Для сравнения — тот же узел в ручном режиме. Здесь каждая колонка на виду, и если что-то не так, это заметно сразу.

Настройки ноды Google Sheets в режиме Map Each Column Manually: под столбцом сопоставления перечислены все колонки листа.
Ручное сопоставление: колонки перечислены, и пустое место видно глазами

Отсюда практический вывод. Если нода в автоматическом режиме перестала писать, форма вам ничего не подскажет — смотреть надо в данные прогона.

Так замёрзли три листа из четырёх в одном из моих сборщиков: патч через API проставил столбец сопоставления, но срезал схему. Четвёртый лист, где схему не тронули, писал как ни в чём не бывало — поэтому и не заметили сразу.

Второе: фильтр, которого нет

В ноде Supabase на операции «получить все» условия фильтра применяются, только если задан отдельный параметр — в интерфейсе он называется Must Match, в описании сценария лежит как matchType. Без него нода молча игнорирует все условия и возвращает всю таблицу. Статус — успех.

Настройки фильтра в ноде Supabase: строка Must Match со значением All Filters, ниже перечислены условия.
Must Match стоит НАД условиями, отдельной строкой. Уберите её — условия останутся на экране и перестанут работать

Во что это превратилось у меня: сценарий напоминаний выбирал записи «ещё не отправлено и время пришло», но параметр не был задан. Значит, каждую минуту выбирались вообще все напоминания, включая уже отправленные, уходили в Telegram, помечались отправленными вхолостую — и на следующей минуте всё повторялось. Остановили руками. Тот же дефект нашёлся ещё в девяти нодах того же сценария.

Обратите внимание, где он стоит: не внутри условий, а над ними. Поэтому его и пропускают — взгляд идёт сразу к полям, где задаются поле, условие и значение.

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

Третье: Code-нода двигает одну запись из десяти

Code-нода по умолчанию стоит в режиме Run Once for All Items — «выполнить один раз для всех записей». В этом режиме обращение к текущим данным даёт только первую запись входа. Типовой код, который берёт данные, дописывает поле и возвращает массив из одного элемента, получает на вход десять записей и отдаёт одну. Девять исчезают. Ошибки нет, прогон успешный.

Вкладка Parameters Code-ноды: список Mode со значением Run Once for All Items и список Language со значением JavaScript.
Это значение стоит по умолчанию, и менять его никто не приходит — код просто пишут под него, не зная, что видит только первую запись
Два режима Code-ноды
РежимЧто внутриЧто вернуть
Один раз для всехТолько первая запись входаМассив записей
Для каждой записиТекущая записьОдин объект, без массива

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

Четвёртое: переключатель «выполнить однократно» врёт в обе стороны

Ноды Supabase по умолчанию выполняются на каждую входную запись. Если предыдущая нода вернула две строки, а следующая грузит «всё про пользователя» и стоит без флага однократного выполнения, она отработает дважды и вернёт удвоенный список.

Обратная ошибка тише и злее: поставить флаг там, где нода должна обработать каждую запись, — тогда обработается только первая, а остальные пропадут без следа.

Живёт переключатель не в параметрах ноды, а на соседней вкладке настроек — там же, где поведение при ошибке.

Вкладка Settings узла n8n: переключатели Always Output Data, Execute Once, Retry On Fail и список On Error со значением Stop Workflow.
Execute Once и On Error лежат на вкладке Settings — в параметрах ноды их не видно, поэтому туда редко заглядывают

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

Пятое: одна нода на весь список и таймаут в минуту

Два дефекта, которые всегда приходят вместе.

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

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

Лечение: на ноду отправки поставить «продолжать по ветке ошибки», чтобы упавшая запись уходила в отдельный выход, а остальные доходили. Это тот же список On Error на вкладке настроек, что на снимке выше: по умолчанию там стоит «остановить сценарий».

Как проверять, а не догадываться

  1. Открыть данные прогона, а не его статус

    В истории выполнений запросите прогон вместе с данными и посмотрите, что вернула конкретная нода. Зелёная галочка рядом с {"error": "Could not get parameter"} в выводе — обычное дело.

  2. Сверить с рабочей нодой того же типа

    Если в сценарии есть нода, которая работает, сравнивайте настройки с ней, а не с документацией. Расхождение находится за минуту.

  3. Проверять на сломанной копии

    Починили — сломайте обратно и убедитесь, что проверка краснеет. Иначе вы не знаете, что именно её чинило.

Грабли по соседству

Сборщик сценария создаёт новый сценарий, а не правит старый.

Скрипты, которые собирают конвейер целиком, заводят новый идентификатор. Живой сценарий — источник правды, и перед любой правкой через API его надо сначала прочитать.

Перед записью всегда чтение.

Обновление через API затирает то, что правили руками в интерфейсе. Сначала забрать текущее состояние, потом отправлять изменённое.

Сценарий обработки ошибок работает, только если сам включён.

Выключенный сценарий-обработчик не сработает ни разу и не сообщит об этом.

Частые вопросы

А если у меня всё зелёное и данные на месте — это точно нормально?
Проверьте объём. Три из пяти случаев выше дают не пустоту, а неполноту: часть записей прошла, часть исчезла. Сравните количество на входе и на выходе — это единственная быстрая проверка.
А можно поймать такое тестом, а не глазами?
Можно, если тест смотрит на данные ноды, а не на статус прогона. Тест, который проверяет только «успех», зелёный на всех пяти случаях.
Это баги n8n или так и задумано?
Задумано. Во всех пяти случаях платформа делает ровно то, что ей сказали, — просто по умолчанию она сказана иначе, чем ожидает человек.

Источники

  1. docs.n8n.io — нода Google SheetsОперация «добавить или обновить строку», работа с листом внутри документа
  2. docs.n8n.io — нода CodeОба режима названы там же: «Run Once for All Items» стоит по умолчанию
  3. docs.n8n.io — нода SupabaseОперации со строками. Параметра «тип совпадения» на странице нет — поэтому на него и не смотрят

Пишу об этом в канале

Короткие разборы и то, что не дотянуло до отдельного материала.