Помилки
Zapys24 API використовує стандартні HTTP-коди статусу. Тіло відповіді завжди містить деталі помилки у JSON-форматі.
Формат відповіді
Загальна помилка
{
"statusCode": 404,
"error": "Not Found",
"message": "Послугу не знайдено"
}
Помилка валідації
{
"statusCode": 400,
"error": "Bad Request",
"message": ["serviceId must be a number", "date must be in format YYYY-MM-DD"]
}
Поле message може бути масивом — тоді кожен елемент описує окрему помилку валідації.
Перевищення ліміту запитів
{
"statusCode": 429,
"error": "Too Many Requests",
"message": "Rate limit exceeded. Limit: 60 requests/minute.",
"retryAfter": 42
}
Коди помилок
Клієнтські помилки (4xx)
| Код | Назва | Коли виникає | Що робити |
|---|---|---|---|
| 400 | Bad Request | Невалідні дані у запиті — неправильний формат дати, відсутнє обов'язкове поле, час у минулому | Перевірте параметри запиту. Поле message містить деталі |
| 401 | Unauthorized | Відсутній, невалідний, відкликаний або прострочений API-ключ | Перевірте чи передаєте ключ у заголовку X-API-Key. Перевірте статус ключа у панелі |
| 403 | Forbidden | Ключ не має потрібного scope, або функція недоступна на вашому тарифі | Перевірте дозволи ключа. Зверніться до адміністратора бізнесу |
| 404 | Not Found | Ресурс не знайдено — послуга, майстер або бронювання з таким ID не існує | Перевірте правильність ID |
| 409 | Conflict | Слот вже зайнятий іншим клієнтом | Запропонуйте клієнту обрати інший час. Оновіть список вільних слотів |
| 429 | Too Many Requests | Перевищено ліміт запитів (60/хв або 10000/добу) | Зачекайте retryAfter секунд. Кешуйте відповіді |
Серверні помилки (5xx)
| Код | Назва | Що робити |
|---|---|---|
| 500 | Internal Server Error | Помилка на стороні Zapys24. Спробуйте пізніше. Якщо повторюється — зверніться до підтримки |
| 503 | Service Unavailable | Сервіс тимчасово недоступний (технічні роботи). Спробуйте через кілька хвилин |
Рекомендації з обробки помилок
1. Завжди перевіряйте HTTP-код
const response = await fetch(url, { headers });
if (!response.ok) {
const error = await response.json();
switch (response.status) {
case 400:
// Покажіть помилки валідації користувачу
showValidationErrors(error.message);
break;
case 409:
// Слот зайнято — оновіть список
refreshSlots();
showMessage("Цей час вже зайнятий. Оберіть інший.");
break;
case 429:
// Зачекайте і повторіть
await delay(error.retryAfter * 1000);
return retry(request);
default:
showMessage("Щось пішло не так. Спробуйте пізніше.");
}
}
2. Обробляйте конфлікти слотів (409)
Між тим як клієнт побачив вільний слот і натиснув «Записатись», інший клієнт може зайняти цей час. Завжди будьте готові до 409:
async function createBooking(data) {
const res = await api.post("/bookings", data);
if (res.status === 409) {
// Оновити слоти та показати актуальні
const slots = await api.get(
`/slots?serviceId=${data.serviceId}&date=${data.date}`,
);
showMessage("На жаль, цей час вже зайнятий. Ось інші вільні слоти:");
renderSlots(slots);
return;
}
showSuccess(`Вас записано! Номер запису: ${res.data.bookingId}`);
}
3. Реалізуйте retry для 429 та 5xx
async function apiRequest(url, options, maxRetries = 3) {
for (let attempt = 0; attempt < maxRetries; attempt++) {
const res = await fetch(url, options);
if (res.status === 429) {
const { retryAfter } = await res.json();
await delay(retryAfter * 1000);
continue;
}
if (res.status >= 500 && attempt < maxRetries - 1) {
await delay(1000 * (attempt + 1)); // 1s, 2s, 3s
continue;
}
return res;
}
}
4. Не показуйте технічні деталі клієнтам
Перетворюйте серверні помилки у зрозумілі повідомлення:
| API помилка | Що показати клієнту |
|---|---|
400: date must be in format YYYY-MM-DD | «Оберіть дату зі списку» |
404: Service not found | «Ця послуга більше недоступна» |
409: Slot already booked | «На жаль, цей час щойно зайняли. Оберіть інший» |
429: Rate limit exceeded | «Забагато запитів. Зачекайте кілька секунд» |
500: Internal Server Error | «Технічна помилка. Спробуйте ще раз» |