API (эндпоинты)
Все эндпоинты смонтированы с префиксом /vendor_endpoint/rb.
Базовый URL
https://rb.the-progress-machine.ru/vendor_endpoint/rb/...
GET /healthcheck
Проверка живости. Возвращает {"status": "ok"}. Исключён из логов logfire.
curl https://rb.the-progress-machine.ru/healthcheck
# {"status":"ok"}
GET /approve
Одобрение выкупа по категории.
| Параметр | Тип | Описание |
|---|---|---|
sheet_name |
str (query) | имя листа Google Sheets |
category |
str (query) | группа шага выкупа (ppstep_group) |
curl "https://rb.the-progress-machine.ru/vendor_endpoint/rb/approve?sheet_name=Sheet1&category=furniture"
Ответ: {"status": "ok"}
GET /update_status
Обновление статусов в таблице после поставки от контрагента.
| Параметр | Тип | Описание |
|---|---|---|
sheet_name |
str (query, opt) | лист. Если не задан — обновляются все листы, кроме шаблона/контрагентов |
Логика (src/services/replace_buyer/status.py):
sheet_name == zt_regular_buy_sheet_name→update_state_in_regular()(пропускает строки со статусомdone/trouble)- иначе →
update_state_by_stock(sheet_name=...)— строки, где остаток ≥ заказанному количеству, получают статусDone.
curl "https://rb.the-progress-machine.ru/vendor_endpoint/rb/update_status?sheet_name=Sheet1"
Ответ: {"status": "ok"}
GET /notify/trouble
Уведомление о проблеме с позицией. Ищет строку по productNumber + product_id,
формирует Telegram-сообщение (MarkdownV2) и шлёт его + email.
| Параметр | Тип | Описание |
|---|---|---|
sheetId |
int (query) | gid листа |
productNumber |
str (query) | номер в таблице |
product_id |
str (query) | UUID товара в МойСклад |
curl "https://rb.the-progress-machine.ru/vendor_endpoint/rb/notify/trouble?sheetId=1&productNumber=2&product_id=3"
Действия:
Sheets/Sheet→ чтение строк листа (FORMULArender).filter_rowsпо(nomer, productNumber)+(uuid, product_id).get_one_idr_and_row→ если строка не найдена, падаетValueError(известное ограничение — нет обработки «не найдено»).prepare_tg_msg→ MarkdownV2,send_message_ext_sync.delay(...)+send_email_double.delay(...).
Известный баг
Если строка не найдена, эндпоинт возвращает 500 (ValueError: not enough
values to unpack). В планах — вернуть 404 с понятным сообщением.
POST /webhook-processor
Приём вебхука от МойСклад (production-вход). Тело сохраняется через
save_webhook.delay(...) и возвращается {"status": "ok"}.
curl -X POST "https://rb.the-progress-machine.ru/vendor_endpoint/rb/webhook-processor" \
-H "Content-Type: application/json" \
-d '{"events":[{"action":"CREATE","meta":{"type":"processingplan","href":"..."}}]}'
POST /internal-webhook
Внутренний роутер вебхуков МойСклад. Разбирает массив events и
маршрутизирует по meta.type + action.
meta.type |
action |
Обработчик |
|---|---|---|
purchaseorder |
CREATE |
handle_create_purchaseorder(po_href=meta.href) |
processingplan |
CREATE |
pplan_trigger(pplan_href=meta.href) |
purchaseorder |
UPDATE |
RegTableApp().hanndle_update_purchaseorder(audit_href=auditContext.meta.href) |
processingplan |
UPDATE |
TableApp().handle_doc_changes(audit_href=auditContext.meta.href) |
| любой | DELETE |
save_webhook.delay(event) |
неизвестный type |
любой | проигнорирован (200) |
Про audit_href
Для UPDATE код передаёт audit_href из auditContext.meta.href, а не из
meta.href события. Это текущее поведение (задокументировано тестами в
test_moysklad_webhooks.py).
Тело запроса (структура МойСклад):
{
"events": [
{
"meta": {
"href": "https://api.moysklad.ru/api/remap/1.2/entity/processingplan/<uuid>",
"type": "processingplan",
"mediaType": "application/json"
},
"action": "CREATE"
}
],
"auditContext": {
"uid": "admin@company",
"moment": "2026-03-01 12:30:00.000",
"meta": {
"href": "https://api.moysklad.ru/api/remap/1.2/audit",
"type": "audit",
"mediaType": "application/json"
}
}
}
Ответ: 200 OK ({"status": "ok"} при пустых/неизвестных событиях).