Cómo se organiza la exportación de GA4
Cada propiedad de GA4 vinculada a BigQuery tiene un conjunto de datos llamado analytics_ seguido del ID de la propiedad. Dentro, Google crea estas tablas (con los nombres de su documentación, a octubre de 2026):
- events_AAAAMMDD: una tabla por día, de la exportación diaria. Es la que hay que consultar.
- events_intraday_AAAAMMDD: el día en curso, que se va llenando si la exportación continua está activada. Google la borra cuando la tabla diaria de ese día está completa.
- users_AAAAMMDD y pseudonymous_users_AAAAMMDD: la exportación opcional de datos de usuario. Una fila por ID de usuario o por ID seudónimo cuyos datos cambiaron ese día, con valor de vida, audiencias y predicciones.
Las tablas de eventos van fragmentadas por fecha, no particionadas: una tabla por día. Para consultar un rango de fechas se usa el comodín events_* y se filtra por _TABLE_SUFFIX. Ese filtro es también lo que mantiene el coste a raya, porque BigQuery solo lee las tablas que coinciden.
Antes de contar nada, una cosa más: Google sigue actualizando cada tabla diaria con los eventos que llegan hasta tres días tarde, así que los días más recientes todavía pueden cambiar. Si aún no tienes la exportación en marcha, qué se gana al exportar GA4 a BigQuery.
Los campos que más vas a usar
Fuente de tráfico: traffic_source, collected_traffic_source y session_traffic_source_last_click
Aquí es donde se pierde casi todo el mundo, porque la exportación tiene tres registros con fuente y medio, y cada uno contesta una pregunta distinta:
- traffic_source: la fuente, el medio y la campaña que captaron al usuario la primera vez. No cambia con las visitas siguientes y no se rellena en las tablas intradía.
- collected_traffic_source: lo que se recogió con cada evento: los valores UTM (manual_source, manual_medium, manual_campaign_name y el resto), gclid, dclid y srsltid. Es el dato en bruto, antes de que GA4 aplique ninguna atribución.
- session_traffic_source_last_click: la fuente de último clic de la sesión, entre Google Ads y las campañas manuales. Su subregistro cross_channel_campaign tiene source, medium y campaign_name, y hay subregistros aparte para Google Ads, Search Ads 360, Display & Video 360 y Campaign Manager 360.
Para informes de sesiones, session_traffic_source_last_click.cross_channel_campaign es lo más parecido a la fuente / medio de la sesión de GA4. Sigue siendo último clic. La atribución que GA4 aplica en sus propios informes, como la atribución basada en datos de los eventos clave, no está en la exportación; si quieres otro modelo, lo construyes tú: en qué se diferencian los modelos de atribución.
Si tu exportación es más antigua que este registro, comprueba que está relleno en las tablas más viejas antes de usarlo en comparaciones largas.
Cinco consultas SQL para GA4 en BigQuery
Estas consultas usan el SQL estándar de BigQuery. Cambia my-project.analytics_123456789 por tu proyecto y tu conjunto de datos, y las fechas por tu rango. Cada una lee solo las columnas que necesita, que es lo que se paga. La documentación para desarrolladores de Google tiene más ejemplos en sus páginas de consultas básicas y avanzadas.
1. Usuarios, usuarios activos y sesiones
SELECT
COUNT(DISTINCT user_pseudo_id) AS users,
COUNT(DISTINCT IF(is_active_user, user_pseudo_id, NULL)) AS active_users,
COUNT(DISTINCT CONCAT(user_pseudo_id, '-', CAST((SELECT value.int_value FROM UNNEST(event_params) WHERE key = 'ga_session_id') AS STRING))) AS sessions
FROM `my-project.analytics_123456789.events_*`
WHERE _TABLE_SUFFIX BETWEEN '20261001' AND '20261031'
Las sesiones se cuentan como pares únicos de usuario y ga_session_id en todo el rango, no sumando día a día: si no, una sesión que pasa de la medianoche cuenta dos veces.
2. Páginas vistas por página
SELECT
(SELECT value.string_value FROM UNNEST(event_params) WHERE key = 'page_location') AS page,
COUNT(*) AS page_views,
COUNT(DISTINCT user_pseudo_id) AS users
FROM `my-project.analytics_123456789.events_*`
WHERE _TABLE_SUFFIX BETWEEN '20261001' AND '20261031'
AND event_name = 'page_view'
GROUP BY page
ORDER BY page_views DESC
LIMIT 50
page_location es la URL completa, con los parámetros incluidos, así que la misma página con distintas etiquetas UTM sale en filas separadas. Quita los parámetros si necesitas rutas limpias.
3. Sesiones por fuente y medio
SELECT
session_traffic_source_last_click.cross_channel_campaign.source AS source,
session_traffic_source_last_click.cross_channel_campaign.medium AS medium,
COUNT(DISTINCT CONCAT(user_pseudo_id, '-', CAST((SELECT value.int_value FROM UNNEST(event_params) WHERE key = 'ga_session_id') AS STRING))) AS sessions
FROM `my-project.analytics_123456789.events_*`
WHERE _TABLE_SUFFIX BETWEEN '20261001' AND '20261031'
GROUP BY source, medium
ORDER BY sessions DESC
4. Eventos clave e ingresos por fuente y medio
SELECT
session_traffic_source_last_click.cross_channel_campaign.source AS source,
session_traffic_source_last_click.cross_channel_campaign.medium AS medium,
COUNTIF(event_name = 'generate_lead') AS leads,
COUNTIF(event_name = 'purchase') AS purchases,
SUM(IF(event_name = 'purchase', ecommerce.purchase_revenue, 0)) AS revenue
FROM `my-project.analytics_123456789.events_*`
WHERE _TABLE_SUFFIX BETWEEN '20261001' AND '20261031'
GROUP BY source, medium
ORDER BY leads DESC
No hay ninguna columna que marque los eventos clave: pon en la lista los nombres de los eventos que tienes marcados como clave en GA4.
5. Eventos clave por canal
WITH ev AS (
SELECT event_name,
LOWER(session_traffic_source_last_click.cross_channel_campaign.medium) AS medium
FROM `my-project.analytics_123456789.events_*`
WHERE _TABLE_SUFFIX BETWEEN '20261001' AND '20261031'
)
SELECT
CASE
WHEN medium IN ('cpc', 'ppc', 'paidsearch') THEN 'Paid search'
WHEN medium = 'organic' THEN 'Organic search'
WHEN medium = 'email' THEN 'Email'
WHEN medium = 'referral' THEN 'Referral'
WHEN medium IS NULL OR medium IN ('(none)', '(not set)') THEN 'Direct or unknown'
ELSE 'Other'
END AS channel,
COUNTIF(event_name = 'generate_lead') AS leads,
COUNTIF(event_name = 'purchase') AS purchases
FROM ev
GROUP BY channel
ORDER BY leads DESC
Es una agrupación simplificada. La exportación no trae una columna con la agrupación de canales predeterminada, y las reglas de GA4 son más largas (redes sociales, shopping, vídeo...), así que escribe tu versión una vez y guárdala en una vista compartida que use todo el equipo.
Por qué no cuadran los números de BigQuery y GA4
Antes de montar cuadros de mando sobre eventos en bruto
Todas las consultas de arriba repiten la misma subconsulta para sacar ga_session_id de event_params. Para analizar está bien. Un cuadro de mando que lanza esas consultas sobre los eventos en bruto cada vez que alguien lo abre vuelve a leer las tablas de eventos una y otra vez, y con el precio bajo demanda cada lectura se cobra: cuánto cuesta BigQuery, con ejemplos.
Lo habitual es una capa limpia: una tabla de sesiones, otra de eventos clave y una tabla de canales, que se rehacen una vez al día y de las que leen los cuadros de mando en Looker Studio (Data Studio desde abril de 2026) o Power BI en lugar de la exportación en bruto. Sale más barato, va más rápido y todo el mundo trabaja con las mismas definiciones.
Si la exportación todavía no funciona, o se ha pausado, lee cómo funciona el límite diario de exportación y qué se puede recuperar todavía del pasado.
Preguntas frecuentes sobre el esquema de GA4 en BigQuery
¿Cómo saco el ID de sesión en la exportación de GA4 a BigQuery?
Es el parámetro ga_session_id, guardado en event_params como número entero. Combínalo con user_pseudo_id, o con user_id, para tener una sesión única.
¿Consulto las tablas events_ o las events_intraday_?
Las events_AAAAMMDD. Google las recomienda porque son los datos estables y completos de cada día. La intradía es temporal y se borra cuando la diaria está completa.
¿Por qué BigQuery da más usuarios que GA4?
Normalmente por Google Signals, por los datos modelados del modo de consentimiento y por cómo estima GA4 las cuentas. Filtrar por is_active_user te acerca a los usuarios activos, pero aun así habrá una pequeña diferencia.
¿Dónde está la fuente y el medio de la sesión?
En session_traffic_source_last_click.cross_channel_campaign, que guarda la fuente, el medio y la campaña de último clic de la sesión. traffic_source es la fuente que captó al usuario la primera vez.
¿Hay una columna con la agrupación de canales predeterminada?
No. La exportación trae fuente, medio y campaña, y las reglas de agrupación las escribes tú en SQL.
¿Se ven las conversiones en BigQuery?
Sí, como eventos. No hay una marca de evento clave, así que filtras por los nombres de los eventos que tienes marcados como clave en GA4.
¿Quieres una capa limpia de GA4 en BigQuery?
Cuéntanos qué necesita medir tu equipo. En una llamada de 30 minutos miramos cómo está montada tu exportación y te decimos qué tablas y definiciones la harían útil sin escribir SQL cada día.
Reservar la llamada de 30 minutos