Перейти к содержимому

Коды ошибок

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

Минимальная:

{ "error": "Сообщение" }

Там, где ошибку удаётся привязать к конкретному месту отправленного тела, добавляется массив errors[]:

{
"error": "Ошибка валидации блоков",
"errors": [
{ "path": "blocks[0].placeholder_values.title", "message": "поле обязательно" },
{ "path": "site_id", "message": "This value should be of type int." }
]
}
  • error — есть всегда, одно предложение о том, что не так в целом.
  • errors[] — есть не всегда. path — dot-путь внутри payload (blocks[2].bindings.products.source) либо имя корневого поля; для ошибки без пути там root.

Правило работы с ответом: если errors[] пришёл — чинить нужно ровно то, на что он указывает, и повторять запрос; текста error для этого недостаточно.

Код Когда приходит Что делать
400 тело запроса не проходит проверку: отсутствует обязательное поле, placeholder_values не соответствуют схеме блока, q короче двух символов, файл не передан, публикация вызвана не тем методом разобрать errors[], исправить payload, повторить
401 ключ не передан или не найден см. API-ключи
403 ресурс принадлежит другому пользователю и не является глобальным; либо аккаунт заблокирован сменить ресурс — повтор не поможет
404 сущность не существует или не видна вашему ключу проверить идентификатор, подобрать замену
405 метод не поддерживается этим путём сверить метод со спецификацией
409 конфликт состояния: slug занят, блок используется на страницах, заявка в каталог уже подана изменить значение или снять зависимость
413 загружаемый файл больше 100 MB уменьшить файл; лимит стоит на nginx, до приложения запрос не доходит
422 тело синтаксически верно, но семантически невозможно: цикл в дереве папок, чужой parent_id, блок недоступен для коллекции, заблокированный major-апгрейд читать error/errors[] — это не про формат, а про смысл
500 внутренняя ошибка повторить позже; текст ошибки наружу не выдаётся, инцидент уже записан на стороне PageCraft
502 внешняя система вернула ошибку: 4CMS при публикации, S3 при загрузке сообщение провайдера — в теле ответа; проверить его настройки

Ключ не передан вовсе:

{ "error": "API key required. Pass it via Authorization: Bearer <key>" }

Ключ передан, но такого нет:

{ "error": "Invalid API key." }

Второй ответ приходит и когда ключ удалён, и когда потерялся префикс pb_ — сервер опознаёт ключевой запрос именно по Bearer pb_.

Разница не в вашем доступе, а в существовании ресурса: 404 — «такого нет», 403 — «есть, но чужое». Повторять запрос бессмысленно в обоих случаях.

Отдельный 403 — «Аккаунт заблокирован» на GET /sites: ключ рабочий, но пользователю закрыт доступ.

slug уникален в пределах сайта. При конфликте приходит:

{
"error": "Slug уже занят",
"errors": [{ "path": "slug", "message": "..." }]
}

Тот же код — при попытке удалить блок, который стоит на страницах, или макет, привязанный к сайту. Где именно используется блок, покажет GET /blocks/{id}/usages.

Особый случай с расширенным телом — блок обновился с ломающими изменениями:

{
"error": "major_upgrade_blocked",
"message": "Block has breaking changes (v1.2 → v2.0). Migrate manually…",
"current_pin": { "major": 1, "minor": 2 },
"library_version": { "major": 2, "minor": 0 },
"removed_fields": ["subtitle", "cta"]
}

Здесь error — код, а не текст; человекочитаемое сообщение в message. Автоматически такое не применяется намеренно: значения удалённых полей пропали бы молча. Порядок ручного переноса — Устаревание и апгрейды.

Тот же сценарий на POST /pages/{pageId}/blocks/upgrade-all кодом не падает: ответ 200, а проблемные блоки перечислены в skipped_major[].

Три разных причины под одним кодом, различаются по тексту:

  • «страница уже опубликована» — вызывайте publish-update;
  • «страница ещё не публиковалась» — вызывайте publish;
  • «у страницы нет сайта» — задайте site_id через PUT /pages/{id}.

Первых двух легко избежать: перед публикацией спросите GET /pages/{id}/publication — этот запрос локальный и во внешнюю систему не ходит.

PageCraft отработал, а внешняя система нет. Тело содержит сообщение, которое вернул провайдер: неверный токен 4CMS, несуществующая рубрика, отказ S3. Повтор помогает только при временном сбое; в остальных случаях чинится настройка сайта.

  • blocks: null в ответе GET /pages/{id} — блоки просто не запрашивались; добавьте with_blocks=1.
  • Пустой binding_slots у блока — блок статический, bindings ему не нужны.
  • Заглушки вместо реальных данных в предпросмотре — источники отдают stub по устройству, реальные данные появляются на витрине.
  • backend/src/EventListener/ApiExceptionListener.php — единая форма тела ошибки
  • backend/src/Security/ApiKeyAuthenticator.php — тексты ответов 401
  • backend/src/Exception/BlockPayloadValidationException.php (400 + errors[])
  • backend/src/Exception/SlugConflictException.php (409 + errors[])
  • openapi/v1.json — коды по эндпоинтам, схема MajorUpgradeBlockedError