uindocs
API RESTWebhooks

Webhook de cambio de estado de publicación

BehaviorOS te avisa cuando una publicación cambia de estado en el marketplace — útil para invalidar tu cache local del catálogo

Cuando una publicación cambia de estado en BehaviorOS (se publica, se despublica manualmente o se pausa automáticamente por falta de stock), te enviamos un POST HTTP al endpoint que configures. Sirve para invalidar la cache local del catálogo sin tener que poolear constantemente la API.

Si no configurás este webhook, BehaviorOS no te avisa de los cambios de estado y vas a tener que consultarlos vía GET cuando los necesites.

Endpoints disponibles

GET    /webhooks/publication-status        ← consultar la configuración actual
PUT    /webhooks/publication-status        ← cargar / actualizar la configuración
POST   /webhooks/publication-status/test   ← disparar un evento de prueba
DELETE /webhooks/publication-status        ← eliminar la configuración (detiene envíos)

Todos están documentados en el Swagger. Requieren Authorization: Bearer <token> de tu client admin.

Configurarlo en el Control Center

  1. Entrá al Control CenterWebhooksCambio de estado de publicación.
  2. Completá:
    • URL del webhook — endpoint público de tu sistema (https://...).
    • Método HTTP — sólo POST.
    • Autenticación — ver modos de autenticación.
  3. Guardar configuración.
  4. Probar webhook — disparás un evento sintético para verificar conectividad y auth.

Cuándo se dispara

Hay cuatro situaciones que disparan el webhook. Las distinguís por los campos status y pauseReason del payload:

SituaciónCuándo ocurreStatus / Pause reason
PublicaciónTu equipo (o un admin de UIN) publica una publicación que estaba en DRAFTstatus: "PUBLISHED_ON_MARKETPLACE", pauseReason: "NONE"
Despublicación manualTu equipo (o un admin de UIN) despublica una publicaciónstatus: "DRAFT", pauseReason: "MANUAL"
Pausa por agotamiento de stock de la publicaciónUna compra deja el availableStock de la publicación en 0status: "DRAFT", pauseReason: "PUBLICATION_OUT_OF_STOCK"
Pausa por agotamiento del agreement subyacenteEl agreement se queda sin stock y todas las publicaciones vinculadas se pausan a la vezstatus: "DRAFT", pauseReason: "AGREEMENT_OUT_OF_STOCK"

Un único endpoint de tu lado recibe los cuatro casos. No hace falta exponer cuatro URLs distintas.

Request

  • Method: POST.
  • URL: la que configuraste. Si elegiste auth por Query param, se agrega automáticamente.
  • Headers: Content-Type: application/json + el header de auth si configuraste HEADER. El detalle exacto de qué llega según el modo de auth está en Modos de autenticación.
  • Body: objeto JSON único (no array — un evento por request).

Body — ejemplo

{
  "publicationId": "c411df38-05b8-481c-9de2-aa27a16c6e55",
  "productId": "ae8b9a3f-1234-5678-9abc-def012345678",
  "clientId": "b8c7594e-8b91-4563-b460-8058343159f5",
  "status": "PUBLISHED_ON_MARKETPLACE",
  "pauseReason": "NONE",
  "availableStock": 50,
  "timestamp": "2026-06-11T17:00:00.000Z"
}

Campos del payload

CampoTipoDescripción
publicationIdUUIDIdentificador de la publicación que cambió de estado. Usalo para invalidar / refrescar tu cache.
productIdUUIDEl producto al que pertenece la publicación.
clientIdUUIDTu UUID de cliente. Útil si tenés un único receptor que atiende varios clientes de UIN.
status"PUBLISHED_ON_MARKETPLACE" | "DRAFT"Nuevo estado de la publicación.
pauseReason"NONE" | "MANUAL" | "PUBLICATION_OUT_OF_STOCK" | "AGREEMENT_OUT_OF_STOCK"Razón del cambio. "NONE" viene en publicaciones; el resto identifica la causa de despublicación.
availableStockintegerStock disponible al momento del cambio. Para pausa por stock=0 viene en 0; para pausa por agreement puede ser distinto de 0.
timestampISO-8601Momento del cambio de estado (no del envío HTTP).

Eventos de prueba

Cuando disparás una prueba con POST /webhooks/publication-status/test (o desde el botón "Probar webhook" del Control Center), recibís el mismo shape de payload pero con un campo extra "test": true a nivel raíz:

{
  "publicationId": "00000000-0000-0000-0000-000000000000",
  "productId": "00000000-0000-0000-0000-000000000000",
  "clientId": "<tu-clientId>",
  "status": "PUBLISHED_ON_MARKETPLACE",
  "pauseReason": "NONE",
  "availableStock": 0,
  "timestamp": "2026-06-12T18:00:00.000Z",
  "test": true
}

En tu endpoint: si el campo test del payload viene en true, no apliques efectos secundarios (no invalides cache, no escribas en DB). Los eventos reales no traen el campo test (está ausente, no llega en false). Ver conceptos comunes a todos los webhooks para el patrón completo.

Patrón recomendado en tu receptor

No confíes en los datos del payload como fuente de verdad — tratá el webhook como una señal de "algo cambió, volvé a consultar" y refrescá vía API usando publicationId. Esto te protege de reordenamientos, duplicados y race conditions:

Recibís webhook

   ├─ Extraés publicationId del body

   ├─ GET /marketplace/publications/{publicationId}    ← fuente de verdad

   └─ Actualizás tu cache con el estado actual devuelto por UIN

Particularidades de este webhook

Aparte de las garantías generales, tené en cuenta:

  • Fan-out en pausa por agreement. Cuando un agreement se agota y eso pausa N publicaciones a la vez, recibís N webhooks en paralelo — uno por cada publicación afectada. Tu endpoint debería tolerar una ráfaga.
  • El cambio puede haber ocurrido segundos antes. El campo timestamp registra el momento del cambio de estado, no el del envío. Si necesitás ordenar eventos en tu sistema, usá timestamp.
  • availableStock describe el estado al momento del cambio, no el estado actual. Si necesitás el stock actual, refrescá vía API.

Buenas prácticas

  • Respondé rápido — idealmente menos de 5s, idealmente con 200 o 204.
  • Validá la auth antes de procesar el body.
  • Idempotencia — usá publicationId + timestamp para deduplicar.
  • No esperes reintentos — el envío es best-effort. Reconciliá periódicamente con GET /marketplace/publications si necesitás cobertura total.
  • Loggeá los webhooks recibidos para debugging.

On this page