Resumen
La API responde JSON por HTTPS. Cada ruta de esta página empieza con esta URL base:
https://app.meloraconnect.com/api/public/v1Para enterarse de los cambios en el momento en que ocurren, use los webhooks. Para usar las mismas operaciones desde un cliente MCP, consulte el servidor MCP.
Quién puede usarla
La API está incluida en todos los planes de Melora Connect. Las claves las crea en Melora Connect el personal que puede administrar la configuración de la organización. Si la API deja de formar parte del plan de la organización, sus claves dejan de funcionar en la siguiente solicitud y vuelven a funcionar cuando el plan la incluya de nuevo, salvo que se hayan revocado o hayan vencido.
Autenticación
Cada solicitud lleva una clave de API en el encabezado Authorization, después de la palabra Bearer:
Authorization: Bearer melora_YOUR_KEYCrear una clave
- En Melora Connect, abra Settings y luego la pestaña API keys.
- Ponga a la clave el nombre del sistema que la usará, elija sus permisos y cuándo vence, y haga clic en Make key.
- Copie la clave y guárdela en su servidor. Se muestra una sola vez.
Sobre las claves
- Una clave pertenece a una sola organización. Cada solicitud actúa en esa organización y en ninguna otra, y nada en una solicitud puede elegir otra. Un registro de otra organización responde
404, como si no existiera. - Melora Connect guarda solo una huella de la clave (un hash SHA-256), así que no puede volver a mostrarla. Guárdela como una contraseña, en su servidor, nunca en una página web ni en una aplicación móvil.
- Las claves empiezan con
melora_seguido de 43 caracteres. La pestaña API keys muestra los primeros 15 caracteres de cada clave, para distinguirlas, y cuándo se usó cada una por última vez. - Una clave puede vencer a los 30, 90 o 365 días, o nunca, y puede revocarse en cualquier momento con Revoke. Una clave revocada o vencida se rechaza desde la siguiente solicitud.
- Una organización puede tener hasta 25 claves activas (las revocadas y las vencidas no cuentan). Cree una clave por sistema, para poder revocar una sin afectar a las demás.
- Los permisos de una clave se fijan al crearla. Para cambiarlos, cree una clave nueva y revoque la anterior.
Permisos
Cada clave lleva solo los permisos elegidos para ella, de entre los mismos permisos que usan los roles del personal en Melora Connect. Quien crea una clave solo puede darle permisos que tiene. Una solicitud que la clave no permite responde 403 con el código permission_denied.
| Permiso de la clave | Qué permite |
|---|---|
members.read | Leer miembros: el padrón y un miembro. |
members.write | Agregar miembros, cambiar los campos de miembro indicados y dar de baja a un miembro del email de marketing de la organización. |
events.read | Leer eventos, y un evento con sus inscripciones. |
events.manage | Crear eventos en borrador. |
members.billing.read | Leer facturas de cuotas. |
settings.manage | Suscribir y cancelar URL de webhooks (lo que usa Zapier). |
Versiones
La versión está en la ruta, /v1. Dentro de v1, Melora Connect solo agrega: endpoints nuevos, parámetros opcionales nuevos y campos nuevos en las respuestas, así que su código debe ignorar los campos que no conoce. Todo lo que rompería una integración que funciona llega como una versión nueva, y v1 sigue funcionando al mismo tiempo.
Límites
- Cada clave puede hacer 120 solicitudes cada 60 segundos. Pasado ese número, la respuesta es
429con un encabezadoRetry-Afteren segundos. - Sumando todas sus claves, una organización puede hacer 600 solicitudes cada 60 segundos. Pasado ese número, todas las claves reciben
429hasta que avance la ventana. - Una dirección que presenta más de 30 claves desconocidas en 10 minutos también recibe
429. - El cuerpo de una solicitud es JSON, enviado con
Content-Type: application/json, y puede tener hasta 64 KB. Uno más grande recibe413(payload_too_large) sin leerse.
Listas y formatos
Cada lista acepta page (desde 1) y per_page (de 1 a 100, 50 por defecto) y responde con data, page, per_page y has_more. Pida la página siguiente mientras has_more sea verdadero.
Los miembros llegan del cambio más antiguo al más reciente. Para mantener una copia al día, envíe el updated_at más reciente que tenga como updated_since: vuelven los registros cambiados en ese momento o después. Los eventos llegan por hora de inicio, y las facturas de cuotas de la más antigua a la más reciente.
Las horas están en ISO 8601 con zona horaria (por ejemplo 2026-11-12T08:00:00-05:00), las fechas en YYYY-MM-DD, los importes en centavos y los id son UUID. Un id que no es un UUID responde 404.
Lista de endpoints
Cada endpoint, el permiso que necesita su clave y qué hace. Cada uno se explica más abajo con un ejemplo.
| Solicitud | Permiso requerido | Qué hace |
|---|---|---|
GET /members | members.read | Listar miembros, del cambio más antiguo al más reciente. |
GET /members/{id} | members.read | Un miembro. |
POST /members | members.write | Agregar un miembro. Responde 201 con el miembro nuevo. |
PATCH /members/{id} | members.write | Cambiar los campos que envíe de un miembro. |
POST /members/{id}/email-preferences | members.write | Da de baja a un miembro del email de marketing de la organización, como lo hace el enlace de baja de una campaña. Responde 200. |
GET /events | events.read | Listar eventos por hora de inicio. |
GET /events/{id} | events.read | Un evento con sus inscripciones. |
POST /events | events.manage | Crear un evento en borrador. Responde 201 con el evento. |
GET /dues-invoices | members.billing.read | Listar facturas de cuotas, de la más antigua a la más reciente. |
POST /webhooks | settings.manage | Suscribir una URL de webhook a eventos. Es lo que usa Zapier. |
DELETE /webhooks/{id} | settings.manage | Cancelar la suscripción de un webhook suscrito por la API. |
GET /api/public/v1/members
Listar miembros, del cambio más antiguo al más reciente.
Permiso requerido: members.read
Parámetros
status(opcional): active, pending, lapsed, expired, suspended, archived o at_risk.membership_type_id(opcional): el id de uno de los tipos de membresía de la organización.updated_since(opcional): una fecha y hora con zona horaria. Solo los miembros cambiados en ese momento o después.email_marketing_opt_out(opcional):truelista solo los miembros que se han dado de baja del email de marketing de la organización,falsesolo los demás.pageyper_page(opcionales): vea Listas y formatos.
Cada miembro tiene los campos de abajo. custom_fields contiene los campos de miembro propios de la organización, como clave del campo y valor.
email_marketing_opt_out es true cuando el miembro se ha dado de baja del email de marketing de la organización, y email_marketing_opted_out_at indica cuándo (null mientras no lo haya hecho). Es la misma lectura que usan las campañas de Melora Connect: un enlace de baja o una queja desde la dirección, para esta organización o para todo Melora Connect, o el interruptor de email del miembro para la organización apagado (también desde una audiencia de Mailchimp conectada). Un rebote no es una baja, y la baja de una organización nunca da de baja al miembro de otra. Una baja no cambia updated_at: siga los webhooks member.unsubscribed y member.resubscribed, y concilie de vez en cuando con email_marketing_opt_out=true.
Campos: id, name, first_name, last_name, email, company, title, industry, phone, website, linkedin_url, city, state, zip, bio, status, membership_type_id, membership_category, tier, join_date, renewal_date, tags, show_in_directory, chapter_id, created_at, updated_at, custom_fields, email_marketing_opt_out, email_marketing_opted_out_at.
Solicitud de ejemplo
curl "https://app.meloraconnect.com/api/public/v1/members?status=active&per_page=50&page=1" \
-H "Authorization: Bearer $MELORA_API_KEY"Respuesta de ejemplo, HTTP 200
{
"data": [
{
"id": "8d2c6f0e-3f59-4a53-9c0e-0f6f5b3a1b21",
"name": "Ana Ruiz",
"first_name": "Ana",
"last_name": "Ruiz",
"email": "ana@example.org",
"company": "Ruiz Consulting",
"status": "active",
"membership_type_id": "0b7a3c62-7f3e-4d7c-8a57-25a1c0a9d7e4",
"join_date": "2026-03-02",
"renewal_date": "2027-03-02",
"tags": ["board"],
"updated_at": "2026-09-28T14:03:11.402Z",
"email_marketing_opt_out": false,
"email_marketing_opted_out_at": null
}
],
"page": 1,
"per_page": 50,
"has_more": false
}GET /api/public/v1/members/{id}
Un miembro.
Permiso requerido: members.read
Parámetros
id(en la ruta): el id del miembro.
El miembro tiene los mismos campos que en la lista. Un miembro que no existe, o que pertenece a otra organización, responde 404.
Solicitud de ejemplo
curl "https://app.meloraconnect.com/api/public/v1/members/8d2c6f0e-3f59-4a53-9c0e-0f6f5b3a1b21" \
-H "Authorization: Bearer $MELORA_API_KEY"Respuesta de ejemplo, HTTP 200
{
"data": {
"id": "8d2c6f0e-3f59-4a53-9c0e-0f6f5b3a1b21",
"name": "Ana Ruiz",
"first_name": "Ana",
"last_name": "Ruiz",
"email": "ana@example.org",
"company": "Ruiz Consulting",
"status": "active",
"membership_type_id": "0b7a3c62-7f3e-4d7c-8a57-25a1c0a9d7e4",
"join_date": "2026-03-02",
"renewal_date": "2027-03-02",
"tags": [
"board"
],
"updated_at": "2026-09-28T14:03:11.402Z",
"email_marketing_opt_out": false,
"email_marketing_opted_out_at": null,
"custom_fields": {
"member_since_year": 2019
}
}
}POST /api/public/v1/members
Agregar un miembro. Responde 201 con el miembro nuevo.
Permiso requerido: members.write
Parámetros
email(obligatorio): un miembro por dirección de correo en la organización.name, ofirst_nameylast_name(obligatorio): al menos uno de ellos.status(opcional): active, el valor por defecto, o pending, lapsed, expired, suspended o archived.join_dateyrenewal_date(opcionales): fechas enYYYY-MM-DD.membership_type_id(opcional): uno de los tipos de membresía de la organización.- También opcionales:
company,title,industry,phone,website,linkedin_url,city,state,zip,bioytags(una lista de palabras). start_welcome_drips(opcional):truepara iniciar las campañas de New member de la organización para un miembro activo.
Un miembro activo ocupa uno de los lugares de miembros activos del plan; cuando no queda ninguno, la respuesta es 403 limit_reached. Un correo que ya pertenece a un miembro de la organización responde 409 conflict, con el id de ese miembro en details.existing_member_id.
Un miembro agregado por la API no entra en ninguna campaña automática de correo de la organización, así que un sistema que copia un padrón entero no le envía una bienvenida a todos. Para dar la bienvenida a un miembro nuevo, envíe start_welcome_drips como true: un miembro activo entra entonces en las campañas de New member de la organización, igual que un miembro agregado a mano, y la respuesta incluye welcome_drips.enrolled, el número de campañas en las que entró (0 para un miembro que no está activo).
phone debe tener de 7 a 15 dígitos y se guarda como sus dígitos, conservando un + inicial (+1 (703) 555-0142 se guarda como +17035550142). website debe ser una dirección http o https y se guarda con su esquema (se agrega https:// si no se envía ninguno). linkedin_url debe ser una dirección https en linkedin.com. Un valor vacío borra el campo. Un valor no válido responde 422 validation_failed, y details nombra el campo.
Solicitud de ejemplo
curl -X POST "https://app.meloraconnect.com/api/public/v1/members" \
-H "Authorization: Bearer $MELORA_API_KEY" \
-H "Content-Type: application/json" \
-d '{"first_name":"Ana","last_name":"Ruiz","email":"ana@example.org","company":"Ruiz Consulting","status":"active","renewal_date":"2027-03-02","tags":["board"]}'Respuesta de ejemplo, HTTP 201
{
"data": {
"id": "8d2c6f0e-3f59-4a53-9c0e-0f6f5b3a1b21",
"name": "Ana Ruiz",
"first_name": "Ana",
"last_name": "Ruiz",
"email": "ana@example.org",
"company": "Ruiz Consulting",
"status": "active",
"membership_type_id": "0b7a3c62-7f3e-4d7c-8a57-25a1c0a9d7e4",
"join_date": "2026-03-02",
"renewal_date": "2027-03-02",
"tags": [
"board"
],
"updated_at": "2026-09-28T14:03:11.402Z",
"email_marketing_opt_out": false,
"email_marketing_opted_out_at": null,
"custom_fields": {}
}
}PATCH /api/public/v1/members/{id}
Cambiar los campos que envíe de un miembro.
Permiso requerido: members.write
Parámetros
id(en la ruta): el id del miembro.- Cuerpo: cualquiera de
name,first_name,last_name,email,company,title,industry,phone,website,linkedin_url,city,state,zip,bio,tags,membership_type_id,statusyrenewal_date. Envíe al menos uno.
Cualquier otro campo se rechaza con 422. El estado at_risk lo calcula Melora Connect a partir de la actividad del miembro y no se puede fijar, y los puntos, la participación y los datos de inicio de sesión no se pueden cambiar. membership_type_id debe ser uno de los tipos de membresía de la organización.
Activar a un miembro ocupa uno de los lugares de miembros activos del plan. Si el estado del miembro cambió mientras se procesaba su solicitud, la respuesta es 409 conflict: lea el miembro e intente de nuevo.
phone, website y linkedin_url se verifican igual que al agregar un miembro. Envíe solo los campos que cambia: un registro más antiguo puede tener un teléfono que no pasa las verificaciones de hoy, así que reenviar el registro completo puede rechazarse.
Solicitud de ejemplo
curl -X PATCH "https://app.meloraconnect.com/api/public/v1/members/8d2c6f0e-3f59-4a53-9c0e-0f6f5b3a1b21" \
-H "Authorization: Bearer $MELORA_API_KEY" \
-H "Content-Type: application/json" \
-d '{"phone":"+1 555 0100","status":"lapsed"}'Respuesta de ejemplo, HTTP 200
{
"data": {
"id": "8d2c6f0e-3f59-4a53-9c0e-0f6f5b3a1b21",
"name": "Ana Ruiz",
"first_name": "Ana",
"last_name": "Ruiz",
"email": "ana@example.org",
"company": "Ruiz Consulting",
"status": "lapsed",
"membership_type_id": "0b7a3c62-7f3e-4d7c-8a57-25a1c0a9d7e4",
"join_date": "2026-03-02",
"renewal_date": "2027-03-02",
"tags": [
"board"
],
"updated_at": "2026-10-04T10:12:45.118Z",
"email_marketing_opt_out": false,
"email_marketing_opted_out_at": null,
"phone": "+15550100"
}
}POST /api/public/v1/members/{id}/email-preferences
Da de baja a un miembro del email de marketing de la organización, como lo hace el enlace de baja de una campaña. Responde 200.
Permiso requerido: members.write
Parámetros
id(en la ruta): el id del miembro.- Cuerpo:
email_marketing_opt_out(obligatorio),true. Cualquier otro campo se rechaza con422.
La próxima campaña de la organización deja fuera al miembro, su interruptor de email para la organización se apaga y sale de sus listas de boletines. El email de otras organizaciones no se toca. La respuesta lleva member_id, email_marketing_opt_out y email_marketing_opted_out_at; pedirlo de nuevo para un miembro ya dado de baja no cambia nada. El cambio queda en el registro de auditoría de la organización con el nombre de la clave. Un miembro sin dirección de email responde 422.
Una clave no puede volver a suscribir a un miembro: false responde 422 validation_failed. Solo el miembro puede volver a activar el email de la organización, en Melora Connect, y entonces se envía member.resubscribed.
Solicitud de ejemplo
curl -X POST "https://app.meloraconnect.com/api/public/v1/members/8d2c6f0e-3f59-4a53-9c0e-0f6f5b3a1b21/email-preferences" \
-H "Authorization: Bearer $MELORA_API_KEY" \
-H "Content-Type: application/json" \
-d '{"email_marketing_opt_out":true}'Respuesta de ejemplo, HTTP 200
{
"data": {
"member_id": "8d2c6f0e-3f59-4a53-9c0e-0f6f5b3a1b21",
"email_marketing_opt_out": true,
"email_marketing_opted_out_at": "2026-11-05T09:12:44.120Z"
}
}GET /api/public/v1/events
Listar eventos por hora de inicio.
Permiso requerido: events.read
Parámetros
status(opcional): draft, published, cancelled, completed o archived.starts_after(opcional): una fecha y hora con zona horaria. Solo los eventos que empiezan en ese momento o después.updated_since(opcional): solo los eventos cambiados en ese momento o después.pageyper_page(opcionales): vea Listas y formatos.
Cada evento tiene los campos de abajo. Los precios están en centavos.
Campos: id, title, description, event_type, status, starts_at, ends_at, timezone, venue, address, is_virtual, capacity, ticket_price_cents, member_price_cents, highlights, slug, published_at, created_at, updated_at, tags.
Solicitud de ejemplo
curl "https://app.meloraconnect.com/api/public/v1/events?starts_after=2026-11-01T00:00:00Z&per_page=20" \
-H "Authorization: Bearer $MELORA_API_KEY"Respuesta de ejemplo, HTTP 200
{
"data": [
{
"id": "5e0c1d8a-9b2f-4c1e-8f3a-6a7b8c9d0e1f",
"title": "Autumn networking breakfast",
"event_type": "networking",
"status": "published",
"starts_at": "2026-11-12T13:00:00+00:00",
"ends_at": "2026-11-12T14:30:00+00:00",
"timezone": "America/New_York",
"venue": "Harbor Hall",
"is_virtual": false,
"capacity": 80,
"ticket_price_cents": 2500,
"member_price_cents": 1500,
"published_at": "2026-10-01T15:00:00+00:00"
}
],
"page": 1,
"per_page": 20,
"has_more": false
}GET /api/public/v1/events/{id}
Un evento con sus inscripciones.
Permiso requerido: events.read
Parámetros
id(en la ruta): el id del evento.
Los campos del evento, más host_committee_name (el comité que lo organiza, o null) y registrations, cada una con los campos de abajo. En una inscripción, member_id es el registro de miembro de la persona inscrita, o null para un invitado.
Campos: id, status, member_id, guest_name, guest_email, ticket_tier_id, checked_in_at, created_at.
Solicitud de ejemplo
curl "https://app.meloraconnect.com/api/public/v1/events/5e0c1d8a-9b2f-4c1e-8f3a-6a7b8c9d0e1f" \
-H "Authorization: Bearer $MELORA_API_KEY"Respuesta de ejemplo, HTTP 200
{
"data": {
"id": "5e0c1d8a-9b2f-4c1e-8f3a-6a7b8c9d0e1f",
"title": "Autumn networking breakfast",
"status": "published",
"starts_at": "2026-11-12T13:00:00+00:00",
"capacity": 80,
"registrations": [
{
"id": "a1b2c3d4-0000-4000-8000-000000000001",
"status": "confirmed",
"member_id": "8d2c6f0e-3f59-4a53-9c0e-0f6f5b3a1b21",
"guest_name": null,
"guest_email": null,
"ticket_tier_id": null,
"checked_in_at": null,
"created_at": "2026-10-02T15:20:00+00:00"
}
]
}
}POST /api/public/v1/events
Crear un evento en borrador. Responde 201 con el evento.
Permiso requerido: events.manage
Parámetros
title(obligatorio): de 2 a 120 caracteres.event_type(obligatorio): el tipo de evento, por ejemplo networking.format(obligatorio): in_person, virtual o hybrid.starts_at(obligatorio) yends_at(opcional): fechas y horas con zona horaria.timezone(opcional): el nombre de una zona horaria como America/New_York, que es el valor por defecto.ticket_price_centsymember_price_cents(opcionales): precios en centavos, 0 por defecto.capacity(opcional): el número de lugares.- También opcionales:
description,venue,address,highlights,tags(una lista de palabras) ylanguage(en, es o fr).
El evento se guarda como borrador. El personal lo revisa y lo publica en Melora Connect, y ahí agrega el enlace para unirse a un evento virtual. Si los eventos no forman parte del plan de la organización, la respuesta es 403 plan_required.
Solicitud de ejemplo
curl -X POST "https://app.meloraconnect.com/api/public/v1/events" \
-H "Authorization: Bearer $MELORA_API_KEY" \
-H "Content-Type: application/json" \
-d '{"title":"Autumn networking breakfast","event_type":"networking","format":"in_person","starts_at":"2026-11-12T08:00:00-05:00","ends_at":"2026-11-12T09:30:00-05:00","timezone":"America/New_York","venue":"Harbor Hall","capacity":80,"ticket_price_cents":2500,"member_price_cents":1500}'Respuesta de ejemplo, HTTP 201
{
"data": {
"id": "5e0c1d8a-9b2f-4c1e-8f3a-6a7b8c9d0e1f",
"title": "Autumn networking breakfast",
"event_type": "networking",
"status": "draft",
"starts_at": "2026-11-12T13:00:00+00:00",
"ends_at": "2026-11-12T14:30:00+00:00",
"timezone": "America/New_York",
"venue": "Harbor Hall",
"is_virtual": false,
"capacity": 80,
"ticket_price_cents": 2500,
"member_price_cents": 1500,
"published_at": null
}
}GET /api/public/v1/dues-invoices
Listar facturas de cuotas, de la más antigua a la más reciente.
Permiso requerido: members.billing.read
Parámetros
status(opcional): open, paid, past_due, void, refunded o failed.member_id(opcional): solo las facturas de este miembro.updated_since(opcional): solo las facturas cambiadas en ese momento o después.pageyper_page(opcionales): vea Listas y formatos.
Cada factura tiene los campos de abajo. Los importes están en centavos. Las facturas son de solo lectura: los pagos se hacen en Melora Connect.
Campos: id, invoice_number, member_id, dues_subscription_id, status, amount_cents, subtotal_cents, discount_cents, discount_code, currency, period_start, period_end, due_at, paid_at, paid_via, voided_at, void_reason, replaces_invoice_id, created_at, updated_at.
Solicitud de ejemplo
curl "https://app.meloraconnect.com/api/public/v1/dues-invoices?status=paid&updated_since=2026-01-01T00:00:00Z" \
-H "Authorization: Bearer $MELORA_API_KEY"Respuesta de ejemplo, HTTP 200
{
"data": [
{
"id": "c4a1e7b2-6d3f-4e8a-9b1c-2d3e4f5a6b7c",
"invoice_number": "INV-2026-0142",
"member_id": "8d2c6f0e-3f59-4a53-9c0e-0f6f5b3a1b21",
"dues_subscription_id": "f1e2d3c4-b5a6-4978-8a9b-0c1d2e3f4a5b",
"status": "paid",
"amount_cents": 25000,
"subtotal_cents": 25000,
"discount_cents": 0,
"discount_code": null,
"currency": "USD",
"period_start": "2026-03-02",
"period_end": "2027-03-01",
"due_at": "2026-03-02T00:00:00+00:00",
"paid_at": "2026-02-27T16:40:12+00:00",
"paid_via": "stripe",
"voided_at": null,
"void_reason": null,
"replaces_invoice_id": null,
"created_at": "2026-02-01T09:00:00+00:00",
"updated_at": "2026-02-27T16:40:12+00:00"
}
],
"page": 1,
"per_page": 50,
"has_more": false
}POST /api/public/v1/webhooks
Suscribir una URL de webhook a eventos. Es lo que usa Zapier.
Permiso requerido: settings.manage
Parámetros
url(obligatorio): una dirección https que pasa las verificaciones del endpoint.events(obligatorio): una lista de uno o más eventos de webhook.include_contact_details(opcional):truepara enviar los datos de contacto de los miembros. La clave necesita entonces tambiénmembers.read.
Una URL nueva responde 201. Suscribir de nuevo la misma URL reemplaza sus eventos y responde 200. Cada URL cuenta para los 10 endpoints que puede tener una organización; pasado ese número, la respuesta es 403 limit_reached.
Una URL que el personal ya agregó en la pestaña Webhooks responde 409: elimínela allí primero. Si los webhooks no forman parte del plan de la organización, la respuesta es 403 plan_required.
La respuesta incluye id, url, events e include_contact_details del endpoint, pero no un secreto de firma. El endpoint aparece en la pestaña Webhooks como agregado por la API, donde el personal puede emitir un secreto nuevo, que se muestra una vez, para un receptor que verifica las firmas.
Solicitud de ejemplo
curl -X POST "https://app.meloraconnect.com/api/public/v1/webhooks" \
-H "Authorization: Bearer $MELORA_API_KEY" \
-H "Content-Type: application/json" \
-d '{"url":"https://hooks.example.com/melora/members","events":["member.created","member.status_changed"]}'Respuesta de ejemplo, HTTP 201
{
"data": {
"id": "2b3c4d5e-6f7a-4b8c-9d0e-1f2a3b4c5d6e",
"url": "https://hooks.example.com/melora/members",
"events": [
"member.created",
"member.status_changed"
],
"include_contact_details": false
}
}DELETE /api/public/v1/webhooks/{id}
Cancelar la suscripción de un webhook suscrito por la API.
Permiso requerido: settings.manage
Parámetros
id(en la ruta): el id que devolvió la suscripción.
Responde 204 sin cuerpo, y los envíos a esa URL se detienen. Un endpoint que el personal agregó en la pestaña Webhooks, o uno de otra organización, responde 404: una clave nunca elimina un endpoint que configuró el personal.
Solicitud de ejemplo
curl -X DELETE "https://app.meloraconnect.com/api/public/v1/webhooks/2b3c4d5e-6f7a-4b8c-9d0e-1f2a3b4c5d6e" \
-H "Authorization: Bearer $MELORA_API_KEY"Respuesta de ejemplo, HTTP 204
Sin cuerpo.
Errores
Cada error es JSON con un código que no cambia, un mensaje para personas y a veces details. Decida según el código, no según el mensaje.
HTTP/1.1 403 Forbidden
Content-Type: application/json; charset=utf-8
{
"error": {
"code": "permission_denied",
"message": "This API key does not have the members.write permission.",
"details": { "required_permission": "members.write" }
}
}| Estado HTTP | Código de error | Significado |
|---|---|---|
| 401 | invalid_api_key | Sin clave, una clave con forma incorrecta o una clave que Melora Connect no conoce. Envíe la clave después de Bearer en el encabezado Authorization. |
| 401 | api_key_revoked | La clave fue revocada. Cree una nueva. |
| 401 | api_key_expired | La clave pasó su fecha de vencimiento. Cree una nueva. |
| 403 | plan_required | El plan no incluye la API (o la función que necesita la solicitud), así que la solicitud se rechaza. |
| 403 | permission_denied | La clave no tiene el permiso que necesita esta solicitud. details.required_permission lo nombra. |
| 403 | billing_hold | La cuenta de Melora Connect está en espera por una factura impaga, lo que pausa este tipo de solicitud. |
| 403 | account_restricted | La cuenta está restringida, así que no se puede crear nada nuevo. |
| 403 | limit_reached | Se superaría un límite del plan, por ejemplo el de miembros activos. |
| 404 | not_found | No existe ese registro aquí. Los registros de otras organizaciones nunca se muestran. |
| 422 | validation_failed | El cuerpo de la solicitud o un parámetro de consulta no es válido. details enumera cada problema. |
| 409 | conflict | El registro entra en conflicto con uno que ya existe. |
| 413 | payload_too_large | El cuerpo de la solicitud supera los 64 KB. Envíe menos campos o divida el trabajo. |
| 429 | rate_limited | Demasiadas solicitudes. Espere los segundos que indica el encabezado Retry-After. |
| 500 | internal_error | Algo falló del lado de Melora Connect. Intente la solicitud de nuevo. |
Ejemplos de código
Node.js
Node.js 18 o posterior: leer todos los miembros activos, una página a la vez, y esperar cuando se alcanza el límite.
// Node.js 18 or later: read every active member, a page at a time.
const base = "https://app.meloraconnect.com/api/public/v1";
const headers = { Authorization: `Bearer ${process.env.MELORA_API_KEY}` };
async function allActiveMembers() {
const members = [];
for (let page = 1; ; page++) {
const res = await fetch(`${base}/members?status=active&per_page=100&page=${page}`, { headers });
if (res.status === 429) {
await new Promise((r) => setTimeout(r, Number(res.headers.get("retry-after") ?? 60) * 1000));
page--;
continue;
}
const body = await res.json();
if (!res.ok) throw new Error(`${body.error.code}: ${body.error.message}`);
members.push(...body.data);
if (!body.has_more) return members;
}
}Python
Python 3 con requests: agregar un miembro, o encontrar el que ya tiene ese correo.
# Python 3 with requests: add a member, or find the one that already has the email.
import os, requests
base = "https://app.meloraconnect.com/api/public/v1"
headers = {"Authorization": f"Bearer {os.environ['MELORA_API_KEY']}"}
res = requests.post(f"{base}/members", headers=headers, json={
"first_name": "Ana", "last_name": "Ruiz", "email": "ana@example.org",
})
if res.status_code == 409:
member_id = res.json()["error"]["details"]["existing_member_id"]
else:
res.raise_for_status()
member_id = res.json()["data"]["id"]Buenas prácticas
- Dé a cada clave solo los permisos que necesita su sistema.
- Guarde las claves en su servidor. Revoque una clave de inmediato si pudo haberse filtrado.
- Cada cambio hecho con una clave aparece en el registro de auditoría de la organización con el nombre de la clave.
- Para enterarse de los cambios en el momento en que ocurren, en lugar de preguntar una y otra vez, use los webhooks.

Personas · Eventos · Comunidades

