Utilisation de BigQuery, Firebase Analytics pour engager, attirer et évaluer les utilisateurs de votre application

Table des matières

Utilisation de BigQuery, Firebase Analytics pour engager, attirer et évaluer les utilisateurs de votre application

Conseils utiles et transformations importantes lorsque vous traitez des données de flux de clics avec des exemples de requête puissants.

Varshita Sher

Vous avez développé une application étonnante, mais comment savoir si les utilisateurs l’utilisent correctement ou quelles parties de l’application les intéressent le plus? Firebase Analytics est l’une des meilleures bibliothèques gratuites disponibles pour enregistrer vos analyses utilisateur. Que votre application soit pour le Web, iOS, Android ou même Flutter, Firebase Analytics peut y être intégré. Une fois que vous avez intégré la bibliothèque d’analyse, vous devez enregistrer tous les événements qui vous intéressent ainsi que tous les paramètres spécifiques à cet événement, comme app_purchase(montant des achats), audio_play(identifiant audio), etc. Firebase par défaut vous montre un certain nombre de graphiques différents pour interpréter les événements que vous enregistrez. Si vous souhaitez effectuer une analyse plus personnalisée, vous pouvez toujours lier vos analyses Firebase à BigQuery dans le tableau de bord Firebase. BigQuery contiendra tous les événements de données brutes et vous pouvez les traiter pour effectuer une analyse plus complexe. Cet article précise comment… ..

La source

Vous venez de créer et de lancer votre application mobile (ou site Web) et vous souhaitez maintenant savoir comment interroger cet énorme ensemble de données que Firebase génère pour vous chaque seconde au moment où nous parlons. Ou vous êtes simplement curieux de connaître certaines requêtes utiles sur les données d’un événement clickstream qui peuvent vous fournir des informations exploitables. Quoi qu’il en soit, bravo et bienvenue dans le tutoriel. Aujourd’hui, nous allons parler de trucs, astuces et bien plus encore quand il s’agit de travailler avec Google BigQuery. Commençons!

Voici à quoi devrait ressembler votre console une fois que vous avez lié les analyses Firebase à BigQuery. Je vais mentionner sur cet écran quelques éléments que j’utilise au quotidien:

  • Bouton Enregistrer la requête: bouton pour enregistrer une requête importante pour référence future.
  • Requêtes enregistrées: c’est là que se trouvent toutes les requêtes que nous allons enregistrer à l’aide du bouton Enregistrer la requête.
  • Historique des requêtes: il stocke tout les requêtes que vous avez exécutées dans le passé (utile lorsque vous souhaitez réutiliser une requête).

Firebase est bon pour suivre beaucoup de événements des données à chaque clic sur votre application ou votre site Web. Par exemple, des informations concernant le moment où l’application a été ouverte pour la première fois, la dernière mise à jour de l’application, le moment où un achat intégré a été effectué, etc. Cela signifie que l’heure et la date associées à chacun de ces événements peuvent être très utiles pour fournir des informations. Par défaut, Firebase enregistre la date et l’heure d’un événement en tant que entier dans la colonne event_timestamp.

SELECT 
FORMAT_DATE('%d-%m-%Y', PARSE_DATE('%Y%m%d', event_date)) AS date,
FORMAT_TIME('%T', TIME(TIMESTAMP_MICROS(event_timestamp))) AS time
FROM analytics_xxxxxxxxx.events_*
SELECT
CAST(TIMESTAMP_MICROS(event_timestamp) AS DATETIME) As UTC_Time
FROM analytics_xxxxxxxxx.events_*
Remarque: L’heure stockée est le fuseau horaire UTC par défaut

Conversion de l’heure UTC en heure locale

L’UTC est le fuseau horaire par défaut utilisé par Firebase pour stocker la date et l’heure associées à un événement. Il existe une autre fonctionnalité appelée «Time_zone_offset_seconds» enregistré dans la base de données des événements qui stocke le décalage par rapport à GMT en quelques secondes (peut être positif ou négatif selon le pays). Ainsi, l’ajout de ce décalage à une heure UTC donnée devrait nous donner l’heure locale correcte.

WITH CTE AS (
SELECT *,
CAST(TIMESTAMP_MICROS(event_timestamp) AS DATETIME) As UTC_Time,
device.time_zone_offset_seconds AS offset_seconds,
FROM analytics_xxxxxxxxx.events_*
)
SELECT UTC_Time, offset_seconds,
CASE
WHEN offset_seconds is NULL then UTC_Time
ELSE DATETIME_ADD(
UTC_Time, INTERVAL CAST(offset_seconds/3600 AS INT64) HOUR)
END As local_time
FROM CTE
WITH CTE AS (
SELECT *,
CAST(TIMESTAMP_MICROS(event_timestamp) AS DATETIME) As UTC_Time,
device.time_zone_offset_seconds AS offset_seconds,
FROM analytics_xxxxxxxxx.events_*
)

SELECT *,
CASE
WHEN offset_seconds IS NULL AND geo.country IN ('India', 'Pakistan') THEN DATETIME_ADD(UTC_Time, INTERVAL CAST(5.5 AS INT64) HOUR)
WHEN offset_seconds IS NULL AND geo.country = 'United States' THEN DATETIME_SUB(UTC_Time, INTERVAL CAST(5 AS INT64) HOUR)
WHEN offset_seconds IS NULL AND geo.country = 'Australia' THEN DATETIME_ADD(UTC_Time, INTERVAL CAST(10 AS INT64) HOUR)
WHEN offset_seconds IS NULL AND geo.country = 'Canada' THEN DATETIME_SUB(UTC_Time, INTERVAL CAST(5 AS INT64) HOUR)
WHEN offset_seconds IS NULL AND geo.country = 'China' THEN DATETIME_ADD(UTC_Time, INTERVAL CAST(8 AS INT64) HOUR)
WHEN offset_seconds IS NULL AND geo.country IN ('France', 'Spain', 'Germany', 'Sweden', 'Italy', 'Sweden', 'United Kingdom', 'Ireland') THEN DATETIME_ADD(UTC_Time, INTERVAL CAST(1 AS INT64) HOUR)
WHEN offset_seconds IS NOT NULL THEN DATETIME_ADD(UTC_Time, INTERVAL CAST(IFNULL(offset_seconds,0)/3600 AS INT64) HOUR)
ELSE UTC_time
END As local_time
FROM CTE

Transformations sur l’heure locale pour extraire le jour de la semaine, le nom du jour de la semaine et l’heure de la journée

Une fois l’heure locale déterminée, nous pouvons aller plus loin en y introduisant de nouvelles transformations. La requête finale incluant tout le code ci-dessus ressemble à ceci:

WITH CTE AS (
SELECT *,
CAST(TIMESTAMP_MICROS(event_timestamp) AS DATETIME) As UTC_Time,
device.time_zone_offset_seconds AS offset_seconds,
FROM analytics_xxxxxxxxx.events_*
),
CTE2 AS (
SELECT *,
CASE
WHEN offset_seconds IS NULL AND geo.country IN ('India', 'Pakistan') THEN DATETIME_ADD(UTC_Time, INTERVAL CAST(5.5 AS INT64) HOUR)
WHEN offset_seconds IS NULL AND geo.country = 'United States' THEN DATETIME_SUB(UTC_Time, INTERVAL CAST(5 AS INT64) HOUR)
WHEN offset_seconds IS NULL AND geo.country = 'Australia' THEN DATETIME_ADD(UTC_Time, INTERVAL CAST(10 AS INT64) HOUR)
WHEN offset_seconds IS NULL AND geo.country = 'Canada' THEN DATETIME_SUB(UTC_Time, INTERVAL CAST(5 AS INT64) HOUR)
WHEN offset_seconds IS NULL AND geo.country = 'China' THEN DATETIME_ADD(UTC_Time, INTERVAL CAST(8 AS INT64) HOUR)
WHEN offset_seconds IS NULL AND geo.country IN ('France', 'Spain', 'Germany', 'Sweden', 'Italy', 'Sweden', 'United Kingdom', 'Ireland') THEN DATETIME_ADD(UTC_Time, INTERVAL CAST(1 AS INT64) HOUR)
WHEN offset_seconds IS NOT NULL THEN DATETIME_ADD(UTC_Time, INTERVAL CAST(IFNULL(offset_seconds,0)/3600 AS INT64) HOUR)
ELSE UTC_time
END As local_time
FROM CTE
)
SELECT
DATE(local_time) as date, -- returns a DATE
EXTRACT(DAYOFWEEK FROM DATE(local_time)) as day_of_Week,
FORMAT_DATE('%a', DATE(local_time)) as weekday_name,
TIME(local_time) as time, -- returns a TIME
CASE
WHEN TIME(local_time) BETWEEN '06:00:00' AND '11:00:00' THEN 'Morning'
WHEN TIME(local_time) BETWEEN '11:00:00' AND '16:00:00' THEN 'Afternoon'
WHEN TIME(local_time) BETWEEN '16:00:00' AND '19:00:00' THEN 'Evening'
WHEN TIME(local_time) BETWEEN '19:00:00' AND '23:59:00' THEN 'Night'
ELSE 'LateNight'
END AS time_of_day
from CTE2

Les systèmes de recommandation suggèrent des éléments qui intéressent les utilisateurs en fonction de leurs préférences explicites (par exemple: évaluations) et implicites (par exemple: temps passé), des préférences des autres utilisateurs et des attributs des utilisateurs et des éléments. À son niveau le plus élémentaire, le bloc de données requis pour créer de telles recommandations pour votre application aurait besoin de trois colonnes: user_id, item_id et rating. Voyons comment l’interroger à partir de la base de données.

  • guid: épisode id
  • note: un entier entre 1 et 5
  • interactionType: 0- supprimer; 1- créer; 2- éditer
SELECT user_pseudo_id, event_name, event_params
FROM analytics_xxxxxxxxx.events_*
WHERE event_name LIKE '%logReview%'
SELECT user_pseudo_id,
(SELECT value.int_value
FROM UNNEST(event_params) WHERE key = 'rating'
) AS rating
FROM analytics_xxxxxxxxx.events_*
WHERE event_name LIKE '%logReview%'
SELECT user_pseudo_id,
(SELECT value.int_value
FROM UNNEST(event_params) WHERE key = 'rating'
) AS rating,
(SELECT value.string_value
FROM UNNEST(event_params) WHERE key = 'guid'
) AS episode_id,
(SELECT value.int_value
FROM UNNEST(event_params) WHERE key = 'collectionId'
) AS podcast_id
FROM analytics_xxxxxxxxx.events_*
WHERE event_name LIKE '%logReview%'
WITH CTE AS (
SELECT user_pseudo_id,
(
SELECT value.int_value
FROM UNNEST(event_params) WHERE key = 'rating'
) AS rating,
(
SELECT value.string_value
FROM UNNEST(event_params) WHERE key = 'guid'
) AS episode_id,
(
SELECT value.int_value
FROM UNNEST(event_params) WHERE key = 'collectionId'
) AS podcast_id,
(
SELECT value.int_value
FROM UNNEST(event_params) WHERE key = 'interactionType'
) AS interaction_type,
event_timestamp, time
FROM analytics_xxxxxxxxx.events_*
WHERE event_name LIKE '%logReview%'
)
SELECT DISTINCT user_pseudo_id, episode_id, podcast_id,
LAST_VALUE(rating) OVER (PARTITION BY user_pseudo_id, episode_id ORDER BY event_timestamp ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) AS latest_rating
FROM CTE

Il est naturel qu’en tant que développeur d’application, vous déployiez une nouvelle version de votre application toutes les quelques semaines. Idéalement, la nouvelle version aura plus de fonctionnalités et de fonctionnalités et aurait résolu quelques bugs désagréables de la version précédente de l’application. Par conséquent, il est important que vous vous assuriez que la plupart de vos premiers utilisateurs sont passés à cette dernière version, et s’ils ne le font pas, de leur envoyer de petits coups de pouce par e-mail.

WITH CTE AS (
SELECT
user_id,
FIRST_VALUE(app_info.version) OVER (user_event_window) AS initial_version,
LAST_VALUE(app_info.version) OVER (user_event_window) AS latest_version,
LAST_VALUE(event_timestamp) OVER (user_event_window) AS app_last_used
FROM analytics_xxxxxxxxx.events_*
WHERE device.operating_system <> 'WEB' AND user_id IS NOT NULL
WINDOW user_event_window AS (PARTITION BY user_id ORDER BY event_timestamp ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING)
)
DATE_DIFF(CURRENT_DATE(), DATE(TIMESTAMP_MICROS(app_last_used)), DAY) AS gap
WITH CTE AS (
SELECT
user_id,
FIRST_VALUE(app_info.version) OVER (user_event_window) AS initial_version,
LAST_VALUE(app_info.version) OVER (user_event_window) AS latest_version,
LAST_VALUE(event_timestamp) OVER (user_event_window) AS app_last_used
FROM `podcastapp-767c2.analytics_193436959.events_*`
WHERE device.operating_system <> 'WEB' AND user_id IS NOT NULL
WINDOW user_event_window AS (PARTITION BY user_id ORDER BY event_timestamp ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING)
)
SELECT user_id, initial_version, latest_version,
DATE(TIMESTAMP_MICROS(app_last_used)) AS last_used,
DATE_DIFF(CURRENT_DATE(), DATE(TIMESTAMP_MICROS(app_last_used)), DAY) AS gap
FROM CTE
WHERE latest_version NOT IN ('1.1.3') -- update the version here in future
GROUP BY user_id, initial_version, latest_version, app_last_used
HAVING gap <= 10