Proprio come in SQL, un join in LookML viene utilizzato per combinare le righe di due o più tabelle in base a una colonna correlata tra loro.
In LookML, un'esplorazione, definita dal parametro LookML explore, viene utilizzata per definire in che modo un utente può eseguire query sui dati. Un'esplorazione è costituita da almeno una vista o da un insieme di viste unite. La vista principale dell'esplorazione è sempre inclusa nella query. Le viste unite vengono normalmente incluse solo se sono necessarie per soddisfare la query.
Una vista LookML corrisponde a una tabella SQL (o a un altro elemento con la struttura di una tabella) nel database o a una tabella derivata. La vista definisce quali campi o colonne sono disponibili nel database e come accedervi.
L'esempio seguente è una definizione per l'esplorazione orders.
explore: orders {
join: users {
type: left_outer
sql_on: ${orders.user_id} = ${users.id} ;;
relationship: many_to_one
}
}
La vista orders, che è la vista principale dell'esplorazione, viene unita alla vista users con un SQL LEFT OUTER JOIN, come indicato dal parametro LookML type: left_outer. La clausola SQL ON, definita dal parametro LookML sql_on, non utilizza table_alias.column, ma fa riferimento a to ${view_name.field_name}. In questo modo, se il nome della tabella o della colonna cambia nel database, la modifica deve essere apportata in un solo punto.
Il relationship parametro è importante. I join possono causare problemi di fanout in cui le righe vengono duplicate. Specificando che molti ordini verranno uniti a un solo utente, Looker riconosce che non si verificheranno fanout da questo join, quindi non è necessaria una gestione speciale. Tuttavia, le relazioni one_to_many possono attivare un fanout.
La generazione automatica di viste ed esplorazioni utilizza per impostazione predefinita un join esterno sinistro. Nell'esempio precedente, tuttavia, è molto probabile che ogni ordine abbia esattamente un utente, quindi il join in questo esempio può essere un join interno.
Per visualizzare l'SQL generato di un'esplorazione, puoi eseguire l'esplorazione nell'interfaccia utente e poi selezionare la scheda SQL nel riquadro Dati.
Ad esempio, se apri l'esplorazione Orders (Ordini), definita in precedenza, e poi selezioni i campi User ID (ID utente) e Count (Conteggio), l'SQL generato sarà simile al seguente:
SELECT
`user_id` AS `orders.user_id`,
COUNT(*) AS `orders.count`
FROM
`thelook`.`orders` AS `orders`
GROUP BY
1
ORDER BY
2 DESC
LIMIT 500
In questo esempio, la tabella users non viene mai utilizzata. Viene utilizzata solo se necessario.
Se rimuovi la dimensione User ID (ID utente) e aggiungi la dimensione ID dalla vista Users (Utenti), l'SQL sarà simile al seguente:
SELECT
`users`.`id` AS `users.id`,
COUNT(*) AS `orders.count`
FROM
`thelook`.`orders` AS `orders`
INNER JOIN `thelook`.`users` AS `users` ON `orders`.`user_id` = `users`.`id`
GROUP BY
1
ORDER BY
2 DESC
LIMIT 500
In questo caso, poiché è presente una selezione dalla vista Users (Utenti), il join è incluso.
L'esempio seguente mostra LookML nel file Explore orders, definito in precedenza, e aggiunge un join alla vista order_items:
explore: orders {
join: users {
type: inner
sql_on: ${orders.user_id} = ${users.id} ;;
relationship: many_to_one
}
join: order_items {
type: inner
sql_on: ${orders.id} = ${order_items.order_id} ;;
relationship: one_to_many
}
}
Ora, se apri l'esplorazione Orders (Ordini) nell'interfaccia utente, vedrai la vista Order Items (Articoli dell'ordine). Se selezioni la misura Total Sale Price (Prezzo di vendita totale) dalla vista Order Items (Articoli dell'ordine) insieme a Count (Conteggio) da Orders (Ordini) e ID da Users (Utenti), Looker genera il seguente SQL:
SELECT
`users`.`id` AS `users.id`,
COUNT(DISTINCT orders.id ) AS `orders.count`,
COALESCE(SUM(`order_items`.`sale_price`), 0) AS `order_items.total_sale_price`
FROM
`thelook`.`orders` AS `orders`
INNER JOIN `thelook`.`users` AS `users` ON `orders`.`user_id` = `users`.`id`
INNER JOIN `thelook`.`order_items` AS `order_items` ON `orders`.`id` = `order_items`.`order_id`
GROUP BY
1
ORDER BY
2 DESC
LIMIT 500
In questo esempio, COUNT(*) AS orders.count è diventato COUNT(DISTINCT orders.id ) AS orders.count. Looker ha rilevato una possibile situazione di fanout e ha aggiunto automaticamente la parola chiave SQL DISTINCT alla funzione SQL COUNT.