[ REVOPS AUTOMATION ]

Pipeline Automatizado de Conversiones Offline a Google Ads y HubSpot

Integración paso a paso con Google Ads API (UploadClickConversions), hashing SHA-256 de identificadores first-party y sincronización webhook bidireccional con HubSpot.

5 Septiembre 2026
10 min de lectura
RESUMEN ESTRATÉGICO // ANSWER FIRST

Cuando una oportunidad B2B se cierra tras meses de negociación, el valor final del contrato reside en el CRM o ERP de la empresa. Si esa señal de conversión no vuelve a Google Ads, el algoritmo de puja automática seguirá optimizando campañas hacia usuarios que rellenan formularios sin intención de compra. Este pipeline extrae transacciones ganadas desde el Data Warehouse y las inyecta de forma segura en la API de Google Ads y HubSpot.

01.

1. Captura Persistente de Identificadores (GCLID / GBRAID / WBRAID)

Para atribuir una conversión offline que ocurre 90 días después del primer clic, el parámetro `gclid` (o el identificador de modelado para iOS `gbraid`/`wbraid`) debe capturarse en la primera visita del usuario y persistirse en una cookie first-party `HttpOnly` y en campos ocultos del formulario web.

Buenas Prácticas de Captura

Almacena siempre el gclid junto a la marca de tiempo de captura. Google Ads acepta conversiones offline hasta 90 días posteriores a la fecha del clic original.

02.

2. Estructuración del Payload para Google Ads API (v17)

El servicio `ConversionUploadService.uploadClickConversions` recibe la lista de conversiones. Se incluye el valor monetario (`conversion_value`), la moneda (`currency_code`), la fecha formateada en zona horaria y los datos de usuario normalizados con SHA-256.

sync-google-ads-offline.ts
// Payload estructurado para la API de Google Ads
interface OfflineConversionPayload {
conversionAction: string; // resource name: customers/{customer_id}/conversionActions/{conversion_action_id}
gclid?: string;
conversionDateTime: string; // Formato: 'yyyy-mm-dd hh:mm:ss+|-hh:mm'
conversionValue: number;
currencyCode: string;
userIdentifiers?: Array<{
hashedEmail?: string;
hashedPhoneNumber?: string;
}>;
}
export async function uploadOfflineConversion(
customerId: string,
developerToken: string,
authToken: string,
conversion: OfflineConversionPayload
) {
const endpoint = `https://googleads.googleapis.com/v17/customers/${customerId}:uploadClickConversions`;
const response = await fetch(endpoint, {
method: 'POST',
headers: {
'Authorization': `Bearer ${authToken}`,
'developer-token': developerToken,
'Content-Type': 'application/json'
},
body: JSON.stringify({
conversions: [conversion],
partialFailure: true
})
});
return await response.json();
}
03.

3. Actualización de Propiedades en HubSpot CRM

En paralelo, cuando el pipeline detecta que la conversión se ha procesado con éxito, emite una llamada a la API de HubSpot para marcar la propiedad `sync_status = "SYNCHRONIZED_TO_ADS"` y registrar la fecha exacta, evitando duplicados en ejecuciones posteriores.

hubspot-patch.json
{
"properties": {
"marketing_offline_conversion_synced": "true",
"google_ads_sync_timestamp": "2026-09-05T14:30:00Z",
"calculated_net_margin_value": "18450.00",
"last_sync_log_id": "job_revops_89412"
}
}
04.

4. Diagnóstico de Errores Comunes en Subidas Offline

La siguiente tabla recopila los códigos de error más frecuentes devueltos por la API de Google Ads y sus soluciones inmediatas en producción.

Matriz de Errores Comunes en Google Ads Conversion Upload
Código de Error APICausa RaízSolución en el Pipeline
CLICK_NOT_FOUNDEl GCLID no existe o tiene más de 90 díasFiltrar eventos donde NOW() - click_date > 89 días
CONVERSION_PRECEDES_CLICKconversionDateTime es anterior al clicVerificar zonas horarias (UTC vs. hora local de la cuenta)
EXPIRED_GCLIDEl clic expiró la ventana de atribuciónFallback a Enhanced Conversions con hashed_email
UNAUTHORIZED_CUSTOMERToken OAuth sin permisos sobre el MCCRenovar refresh token con permisos admin sobre cuenta hija

Controles Técnicos

Muestra telemetría y especificaciones de verificación en producción.