Skip to main content

Rivalwin API — Meta Commercial Ads

Descripción general

La API de Meta Commercial permite generar informes de publicidad comercial en la plataforma Meta (Facebook, Instagram) de forma programática. Los informes analizan los anuncios comerciales de un competidor durante un período determinado, proporcionando datos de creatividades, copys, impresiones, segmentación demográfica, de edades y análisis de IA.

Base URL: https://rivalwin.com/api/v1/meta/companies/


Autenticación

Todas las peticiones requieren una API Key válida enviada en el header X-API-Key.

X-API-Key: tu_api_key_aqui

Rate Limiting

La API aplica dos tipos de limitación:

Rate limit por hora

Cada API Key tiene un límite de peticiones por hora configurado. Los headers de respuesta indican el estado:

X-RateLimit-Limit-Hour: 600
X-RateLimit-Remaining-Hour: 598

Si se excede el límite: 429 Too Many Requests con header Retry-After.

Cooldown entre informes

Existe un tiempo mínimo de espera entre la creación de informes consecutivos (por defecto 10 segundos, configurable por plan/empresa). Si intentas crear un informe antes de que transcurra este tiempo:

{
"error": "cooldown_active",
"message": "Please wait 7 seconds before creating another report.",
"cooldown_seconds": 10,
"retry_after": 7
}

Requisitos de la cuenta

  • Su cuenta de Rivalwin debe estar activa.
  • El plan contratado debe estar activo y no vencido (contrato o trial).
  • El plan debe incluir acceso a la API.

Si alguna de estas condiciones no se cumple, recibirás un error 403 Forbidden con el motivo específico.


Recepción de resultados

Existen dos formas de recibir los datos de un informe completado:

Polling

Consulta el endpoint report_status periódicamente (cada 15-30 segundos) hasta que el estado sea DONE. Es el método más simple y no requiere configuración adicional.

Webhook

Configura una URL de webhook en el módulo Integraciones & API Keys del sistema. Cuando un informe pase al estado DONE, la API enviará automáticamente un POST a la URL configurada con el payload completo del informe (mismo contenido que devuelve report_status en estado DONE).

De esta forma no necesitas hacer polling: simplemente esperas a recibir la notificación en tu servidor.


Endpoints

1. Crear un nuevo informe comercial (new_report)

Crea un informe de publicidad comercial de Meta de forma asíncrona. Devuelve inmediatamente un hash identificador para consultar el estado.

POST /api/v1/meta/companies/new_report

Headers

HeaderTipoRequeridoDescripción
X-API-KeystringTu API Key
Idempotency-KeystringNoClave de idempotencia para evitar informes duplicados
Content-Typestringapplication/json

Body (JSON)

ParámetroTipoRequeridoDescripción
rival_refstringReferencia del rival
date_fromstringFecha inicio del período (YYYY-MM-DD)
date_tostringFecha fin del período (YYYY-MM-DD)
countrystringISO-2 (ES, AR, EU, etc.)

Ejemplo de petición

curl -X POST https://rivalwin.com/api/v1/meta/companies/new_report \
-H "X-API-Key: tu_api_key" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: meta-com-report-20260315" \
-d '{
"rival_ref": "rvl_4a7e9f12",
"date_from": "2026-03-01",
"date_to": "2026-03-31",
"country": "AR"
}'

Respuesta exitosa (202 Accepted)

{
"hash": "...",
"status": "PENDING",
"created_at": "2026-03-15 14:00:00"
}

Validaciones y restricciones

ReglaDetalle
Rango máximo de fechas60 días
Fecha fin máximaAyer (no se permite el día actual ni futuro)
Fecha inicio mínimaHasta 1 año atrás
Formato de fechaYYYY-MM-DD estricto
PaísCódigo ISO de 2 letras
CréditosSe descuentan al crear el informe

Idempotencia

Si envías el header Idempotency-Key con un valor previamente usado, la API devuelve el informe existente sin crear uno nuevo ni descontar créditos adicionales.


2. Consultar estado del informe (report_status)

Consulta el estado de un informe y obtiene los datos del reporte cuando está completo.

POST /api/v1/meta/companies/report_status

Headers requeridos

HeaderTipoRequeridoDescripción
X-API-KeystringTu API Key
Content-Typestringapplication/json

Body (JSON)

ParámetroTipoRequeridoDescripción
hashstringHash del informe (obtenido de new_report)

Ejemplo de petición

curl -X POST https://rivalwin.com/api/v1/meta/companies/report_status \
-H "X-API-Key: tu_api_key" \
-H "Content-Type: application/json" \
-d '{"hash": "..."}'

Respuesta según estado

PENDING — El informe está en cola:

{
"hash": "...",
"status": "PENDING",
"created_at": "2026-03-15 14:00:00",
"message": "The report is queued and will start processing shortly."
}

PROCESSING — El informe se está generando:

{
"hash": "...",
"status": "PROCESSING",
"created_at": "2026-03-15 14:00:00",
"started_at": "2026-03-15 14:00:08",
"message": "The report is being generated. Please check back in a few moments."
}

DONE — El informe está completo con todos los datos:

{
"hash": "...",
"status": "DONE",
"created_at": "2026-03-15 14:00:00",
"started_at": "2026-03-15 14:00:08",
"completed_at": "2026-03-15 14:02:30",
"report": {
"report_id": 1234,
"platform": "Meta",
"rival": {
"ref": "rvl_4a7e9f12",
"name": "Empresa Competidora S.A.",
"logo": "https://.../competidor.png",
"web": "https://competidor.com",
"description": "Competidor directo en retail"
},
"sector": "Retail / E-commerce",
"country": "AR",
"campaign_start": "2026-03-01",
"campaign_end": "2026-03-31",
"inform_created": "2026-03-15 14:00:00",
"kpis": {
"ads_total": 28,
"impressions_lower": 800000,
"impressions_upper": 2500000,
"reach_total": 450000
},
"demographics": {
"18-24": {"male": 15, "female": 22, "unknown": 3},
"25-34": {"male": 25, "female": 30, "unknown": 5},
"35-44": {"male": 18, "female": 20, "unknown": 2},
"45-54": {"male": 10, "female": 12, "unknown": 1},
"55-64": {"male": 5, "female": 8, "unknown": 0},
"65+": {"male": 2, "female": 4, "unknown": 0}
},
"insights": {
"gpt_analysis": "Análisis detallado de la estrategia publicitaria generado por IA."
},
"ads": [
{
"ad_id": "987654321",
"start_date": "2026-03-05",
"end_date": "2026-03-25",
"content": "Texto del anuncio comercial: ¡Oferta especial!...",
"image_url": "https://scontent.xx.fbcdn.net/...",
"video_url": null,
"platforms": ["facebook", "instagram"],
"display_format": "image",
"spend": {
"min": 200,
"max": 500,
"currency": "ARS"
},
"impressions": {
"lower": 10000,
"upper": 50000
},
"reach": 15000,
"demographics": {
"25-34": {"male": 12, "female": 18, "unknown": 2}
},
"creatives": {
"images": ["https://scontent.xx.fbcdn.net/image1.jpg"],
"videos": []
}
}
],
"pdf_url": "https://.../report_1234.pdf"
}
}

ERROR — Error durante la generación:

{
"hash": "...",
"status": "ERROR",
"created_at": "2026-03-15 14:00:00",
"completed_at": "2026-03-15 14:01:30",
"error_message": "Report failed during processing."
}

Estructura completa del reporte

Campos principales (report)

CampoTipoDescripción
report_idintID interno del informe
platformstringPlataforma analizada (Meta)
rivalobjectDatos del competidor analizado
sectorstringSector o industria del competidor
countrystringPaís filtrado
campaign_startstringFecha inicio del período analizado
campaign_endstringFecha fin del período analizado
inform_createdstringFecha de creación del informe
kpisobjectIndicadores clave agregados
demographicsobjectMatriz demográfica agregada de todos los anuncios
insightsobjectAnálisis generado por IA
adsarrayLista detallada de anuncios
pdf_urlstringURL del PDF del informe (si está disponible)

KPIs (kpis)

CampoTipoDescripción
ads_totalintegerTotal de anuncios encontrados en el período
impressions_lowerintegerLímite inferior de impresiones totales estimadas
impressions_upperintegerLímite superior de impresiones totales estimadas
reach_totalintegerAlcance total estimado

Demografía (demographics)

La matriz demográfica agrega los datos de segmentación de todos los anuncios. Cada rango de edad contiene porcentajes por género:

{
"25-34": {
"male": 25,
"female": 30,
"unknown": 5
}
}

Los rangos de edad disponibles son: 18-24, 25-34, 35-44, 45-54, 55-64, 65+.

Datos del rival (rival)

CampoTipoDescripción
refstringReferencia del rival
namestringNombre de la empresa
logostringURL del logo (puede ser null)
webstringSitio web (puede ser null)
descriptionstringDescripción del competidor

Anuncios (ads[])

Cada anuncio contiene la siguiente información:

CampoTipoDescripción
ad_idstringID del anuncio en Meta Ad Library
start_datestringFecha de inicio del anuncio
end_datestringFecha de finalización o última vez visto
contentstringTexto/copy principal del anuncio
image_urlstringURL de la imagen principal (puede ser null)
video_urlstringURL del video (puede ser null)
platformsarrayPlataformas (facebook, instagram, messenger)
display_formatstringFormato del anuncio (image, video, carousel)
impressionsobjectRango de impresiones (lower, upper)
reachintegerAlcance estimado del anuncio
demographicsobjectSegmentación demográfica específica de este anuncio
creativesobjectCreatividades: images[] y videos[]

Insights de IA (insights)

CampoTipoDescripción
gpt_analysisstringAnálisis HTML generado por IA sobre la estrategia publicitaria

El análisis incluye observaciones sobre los mensajes clave, tono de comunicación, segmentación, formatos utilizados y recomendaciones estratégicas.


Ejemplos de código

PHP

<?php
$apiKey = "tu_api_key";
$baseUrl = "https://rivalwin.com/api/v1/meta/companies";

$rivalRef = "rvl_4a7e9f12";

// 1. Crear informe
$report = apiCall("$baseUrl/new_report", [
'rival_ref' => $rivalRef,
'date_from' => '2026-03-01',
'date_to' => '2026-03-31',
'country' => 'AR',
], $apiKey);

$hash = $report['hash'];
echo "Informe creado: $hash\n";

// 2. Polling hasta que esté listo
do {
sleep(20);
$status = apiCall("$baseUrl/report_status", ['hash' => $hash], $apiKey);
echo "Estado: " . $status['status'] . "\n";
} while (in_array($status['status'], ['PENDING', 'PROCESSING']));

// 3. Procesar resultado
if ($status['status'] === 'DONE') {
$data = $status['report'];
echo "Rival: " . $data['rival']['name'] . "\n";
echo "Anuncios encontrados: " . $data['kpis']['ads_total'] . "\n";
echo "Inversión: $" . $data['kpis']['investment_min_usd'] . " - $" . $data['kpis']['investment_max_usd'] . " USD\n";
echo "Impresiones: " . number_format($data['kpis']['impressions_lower']) . " - " . number_format($data['kpis']['impressions_upper']) . "\n";

// Recorrer anuncios
foreach ($data['ads'] as $ad) {
echo " Ad #{$ad['ad_id']}: {$ad['content']}\n";
echo " Período: {$ad['start_date']}{$ad['end_date']}\n";
echo " Inversión: {$ad['spend']['min']} - {$ad['spend']['max']} {$ad['spend']['currency']}\n";
}
}

function apiCall(string $url, array $body, string $apiKey): array {
$ch = curl_init($url);
curl_setopt_array($ch, [
CURLOPT_POST => true,
CURLOPT_POSTFIELDS => json_encode($body),
CURLOPT_RETURNTRANSFER => true,
CURLOPT_HTTPHEADER => [
'Content-Type: application/json',
'X-API-Key: ' . $apiKey,
],
]);
$response = curl_exec($ch);
curl_close($ch);
return json_decode($response, true);
}

Python

import requests
import time

api_key = "tu_api_key"
base_url = "https://rivalwin.com/api/v1/meta/companies"
headers = {
"Content-Type": "application/json",
"X-API-Key": api_key,
}

rival_ref = "rvl_4a7e9f12"

# 1. Crear informe
report = requests.post(f"{base_url}/new_report", json={
"rival_ref": rival_ref,
"date_from": "2026-03-01",
"date_to": "2026-03-31",
"country": "AR",
}, headers=headers).json()

hash_id = report["hash"]
print(f"Informe creado: {hash_id}")

# 2. Polling
while True:
time.sleep(20)
status = requests.post(f"{base_url}/report_status", json={"hash": hash_id}, headers=headers).json()
print(f"Estado: {status['status']}")
if status["status"] not in ["PENDING", "PROCESSING"]:
break

# 3. Resultados
if status["status"] == "DONE":
data = status["report"]
print(f"Total anuncios: {data['kpis']['ads_total']}")
print(f"Inversión USD: ${data['kpis']['investment_min_usd']} - ${data['kpis']['investment_max_usd']}")

Códigos de error

Código HTTPErrorDescripción
400missing_parametersFaltan parámetros requeridos en el body
400invalid_date_fromFormato de date_from inválido (debe ser YYYY-MM-DD)
400invalid_date_toFormato de date_to inválido (debe ser YYYY-MM-DD)
400invalid_date_rangeRango de fechas inválido (futuro, invertido o > 60 días)
400invalid_countryCódigo de país inválido (debe ser 2 letras ISO)
401missing_api_keyNo se envió el header X-API-Key
401invalid_api_keyLa API Key no es válida o está revocada
402insufficient_creditsCréditos insuficientes para generar el informe
403account_inactiveLa cuenta de la empresa está desactivada
403plan_inactiveEl plan contratado está desactivado
403contract_expiredEl contrato ha expirado
403trial_expiredEl período de prueba ha expirado
403api_not_in_planEl plan no incluye acceso a la API
404rival_not_foundEl rival_ref no existe o está inactivo
404rival_data_not_foundDatos del rival no encontrados en el sistema
404job_not_foundNo se encontró un informe con el hash proporcionado
429rate_limit_exceededSe excedió el límite de peticiones por hora
429cooldown_activeDebe esperar antes de crear otro informe
500internal_errorError interno del servidor

Notas importantes

  • Los informes se generan de forma asíncrona. La creación devuelve un hash inmediatamente y el informe se procesa en segundo plano.
  • El tiempo de generación típico es de 1 a 5 minutos, dependiendo del volumen de anuncios y la generación del análisis IA + PDF.
  • La ads_data_url es una URL firmada con 1 hora de vigencia para descargar los datos crudos originales.
  • El pdf_url contiene el informe visual en formato PDF listo para descarga.
  • Cada informe consume créditos de tu cuenta según el sistema.
  • El gpt_analysis viene en formato HTML y puede contener etiquetas <p>, <ul>, <li>, etc.