La clause GROUP BY est généralement utilisée avec des fonctions d'agrégation pour regrouper les lignes d'un résultat de requête. Chaque groupe repose sur les valeurs d'une ou de plusieurs colonnes, et chaque combinaison distincte de valeurs produit une ligne récapitulative. La clause GROUP BY ALL déduit automatiquement les clés de regroupement à partir de la liste SELECT, tandis que les clauses ROLLUP, CUBE et GROUPING SETS étendent la clause GROUP BY à d'autres modèles de regroupement.
Syntaxe
Simple Log Service prend en charge les formes de regroupement suivantes. Choisissez celle qui correspond aux clés de regroupement et aux sous-totaux requis par votre requête.
|
Clause |
À utiliser lorsque |
|
|
Vous regroupez les lignes selon des colonnes que vous listez explicitement. Il s'agit de la forme standard de regroupement. |
|
|
Vous disposez de nombreux champs de regroupement ou vous ajustez fréquemment les dimensions d'analyse, et vous souhaitez que les clés de regroupement soient déduites de la liste |
|
|
Vous avez besoin d'un sous-total pour chaque groupe ainsi que d'un total général pour l'ensemble des groupes. |
|
|
Vous avez besoin de toutes les combinaisons possibles des colonnes spécifiées. |
|
|
Vous avez besoin uniquement des regroupements que vous spécifiez. |
Quelle que soit la forme de regroupement utilisée, la liste SELECT ne peut contenir que des clés de regroupement et des résultats d'agrégation. Pour connaître la règle complète et voir une requête corrigée, consultez la note dans la section Exemples.
GROUP BY
Regroupe les résultats d'analyse selon une ou plusieurs colonnes spécifiées. Pour des exemples, reportez-vous à l'exemple 1, à l'exemple 2 et à l'exemple 3.
SELECT
key1,
...,
aggregate_function
GROUP BY
key1, ...
Paramètres :
key1: la colonne selon laquelle regrouper les lignes. Vous pouvez regrouper les lignes par noms de champs de journal ou par colonnes de résultat calculées par des fonctions d'agrégation. La clauseGROUP BYprend en charge une ou plusieurs colonnes.aggregate_function: la fonction d'agrégation appliquée à chaque groupe, telle quecount,min,max,avgousum.
GROUP BY ALL
La clause GROUP BY ALL utilise automatiquement comme clés de regroupement les expressions de la liste SELECT qui ne contiennent ni fonction d'agrégation ni fonction de fenêtrage. Vous n'avez donc pas besoin de répéter ces expressions dans la clause GROUP BY. Cette forme est utile lorsque vous disposez de nombreux champs de regroupement ou lorsque vous ajustez fréquemment les dimensions d'analyse. Pour des exemples, reportez-vous à l'exemple 7, à l'exemple 8 et à l'exemple 9.
SELECT
key1,
key2,
aggregate_function
GROUP BY ALL
Paramètres :
key1etkey2: champs ou expressions de regroupement, tels questatus,request_method,substr(request_method, 1, 1)ou une expressionCASE. Une expression est regroupée selon son résultat calculé complet. La clauseGROUP BY ALLne prend aucune liste de champs ; vous ne devez donc pas répéter un alias ou une expression après celle-ci.aggregate_function: la fonction d'agrégation appliquée à chaque groupe, telle quecount(*),sum(request_time)ouavg(request_time).
Par exemple, les deux instructions de requête suivantes sont équivalentes :
* | SELECT request_method, status, count(*) AS PV GROUP BY ALL
* | SELECT request_method, status, count(*) AS PV GROUP BY request_method, status
Règles et limites :
Le regroupement automatique repose sur la liste
SELECTactuelle, et non sur tous les champs présents dans les journaux. L'ajout ou la suppression d'une expression non agrégée et sans fenêtrage modifie les dimensions de regroupement en conséquence.La sélection par caractère générique n'est pas prise en charge au même niveau de requête : vous ne pouvez pas combiner
GROUP BY ALLavecSELECT *,SELECT table_alias.*ouSELECT *, count(*). Listez les champs explicitement. Cette limite s'applique à la sélection par caractère générique elle-même, et non aux fonctions d'agrégation ; ainsi,count(*)fonctionne comme d'habitude aux côtés des champs listés explicitement.Une expression entière contenant une fonction d'agrégation ou une fonction de fenêtrage n'est pas automatiquement ajoutée en tant que clé de regroupement. Par exemple,
sum(request_time) / count(*)n'est pas utilisée pour le regroupement, et les champs contenus dans les appels de fonction d'agrégation ne deviennent pas des clés de regroupement. Tout champ non agrégé que vous sélectionnez aux côtés d'une telle expression doit toujours respecter les règles standard de regroupement de la clauseGROUP BY. Dans l'instructionSELECT request_method, status, count(*) AS PV GROUP BY ALL,request_methodetstatussont tous deux des clés de regroupement.Si la liste
SELECTne contient que des expressions d'agrégation, toutes les données répondant aux conditions de la requête sont agrégées globalement. Par exemple,* | SELECT count(*) AS PV, sum(request_time) AS total_time GROUP BY ALLéquivaut à omettre la clauseGROUP BY ALL.Vous pouvez utiliser
GROUP BY ALLavec les clausesWHERE,HAVING,ORDER BYet avec des fonctions de fenêtrage. Les fonctions de fenêtrage s'appliquent aux résultats groupés et agrégés, et les champs auxquels elles font référence doivent toujours respecter les règles de regroupement.Pour déduire automatiquement les clés de regroupement, utilisez
GROUP BY ALLseul. Dans les expressionsGROUP BY ALL statusouGROUP BY ALL ROLLUP (...), le mot-cléALLmodifie la spécification de regroupement qui le suit ; aucune clé de regroupement n'est donc déduite automatiquement.Pour effectuer un regroupement selon un champ ou un alias nommé
all, placez le nom entre guillemets doubles, comme dansGROUP BY "all". Par défaut, une clauseGROUP BY ALLisolée déduit automatiquement les clés de regroupement, même si un champ nomméallexiste.
GROUP BY ROLLUP
La clause GROUP BY ROLLUP regroupe les données en récapitulatifs hiérarchiques. Elle renvoie un sous-total pour chaque groupe et un total général pour l'ensemble des groupes. Par exemple, GROUP BY ROLLUP (a, b) produit un ensemble de résultats pour les ensembles de regroupement (a, b), (a, null) et (null, null). Une valeur null dans un ensemble de regroupement signifie que la colonne est agrégée dans cet ensemble, de sorte que la ligne constitue un sous-total. Pour un exemple, reportez-vous à l'exemple 6.
SELECT
key1,
...,
aggregate_function
GROUP BY ROLLUP (key1, ...)
Paramètres
key1: la colonne selon laquelle regrouper les lignes. Vous pouvez regrouper les lignes par noms de champs de journal ou par colonnes de résultat d'une fonction d'agrégation. La clauseGROUP BYprend en charge le regroupement selon une ou plusieurs colonnes.aggregate_function: les fonctions d'agrégation appliquées à chaque groupe, telles quecount,min,max,avgousum.
GROUP BY CUBE
La clause GROUP BY CUBE regroupe les données selon toutes les combinaisons possibles des colonnes spécifiées. Par exemple, GROUP BY CUBE (a, b) produit un ensemble de résultats pour les ensembles de regroupement (a, b), (null, b), (a, null) et (null, null). Une valeur null dans un ensemble de regroupement signifie que la colonne est agrégée dans cet ensemble, de sorte que la ligne constitue un sous-total. Pour un exemple, reportez-vous à l'exemple 5.
SELECT
key1,
...,
aggregate_function
GROUP BY CUBE (key1, ...)
Paramètres
key1: la colonne selon laquelle regrouper les lignes. Vous pouvez regrouper les lignes par noms de champs de journal ou par colonnes de résultat d'une fonction d'agrégation. La clauseGROUP BYprend en charge le regroupement selon une ou plusieurs colonnes.aggregate_function: les fonctions d'agrégation appliquées à chaque groupe, telles quecount,min,max,avgousum.
GROUP BY GROUPING SETS
La clause GROUP BY GROUPING SETS vous permet de spécifier plusieurs regroupements distincts dans une seule requête. Par exemple, GROUP BY GROUPING SETS (a, b) équivaut à combiner les résultats de GROUP BY a et de GROUP BY b, et produit un ensemble de résultats pour les ensembles de regroupement (a, null) et (null, b). Une colonne qui ne fait pas partie d'un ensemble de regroupement prend la valeur null dans les lignes correspondant à cet ensemble. Pour un exemple, reportez-vous à l'exemple 4.
SELECT
key1,
...,
aggregate_function
GROUP BY GROUPING SETS (key1, ...)
Paramètres
key1: la colonne selon laquelle regrouper les lignes. Vous pouvez regrouper les lignes par noms de champs de journal ou par colonnes de résultat d'une fonction d'agrégation. La clauseGROUP BYprend en charge le regroupement selon une ou plusieurs colonnes.aggregate_function: les fonctions d'agrégation appliquées à chaque groupe, telles quecount,min,max,avgousum.
Exemples
Dans une instruction SQL, la liste SELECT d'une requête de regroupement ne peut contenir que les éléments suivants :
Les colonnes ou expressions spécifiées dans la clause
GROUP BY.Les colonnes ou expressions que la clause
GROUP BY ALLdéduit automatiquement en tant que clés de regroupement à partir de la listeSELECT.Les résultats de calculs d'agrégation sur des colonnes, tels que
COUNT()ouSUM().
Vous pouvez également utiliser des fonctions de fenêtrage sur les résultats groupés. Pour plus d'informations, reportez-vous à l'exemple 9.
Vous ne pouvez pas sélectionner directement une colonne qui n'est pas incluse dans la clause GROUP BY, car cette colonne peut avoir plusieurs valeurs après le regroupement, ce qui rendrait sa signification ambiguë. Par exemple, l'instruction de requête suivante n'est pas valide :
* | SELECT status, request_time, COUNT(*) AS PV GROUP BY status
L'instruction de requête n'est pas valide car request_time n'est pas incluse dans la clause GROUP BY et n'est pas traitée par une fonction d'agrégation. Vous pouvez réécrire l'instruction de requête comme suit :
* | SELECT status, arbitrary(request_time), COUNT(*) AS PV GROUP BY status
Ici, arbitrary(request_time) est une opération d'agrégation sur request_time qui sélectionne une valeur request_time arbitraire dans chaque groupe. Cela vous permet d'inclure la colonne dans votre requête.
Exemple 1 : Calculer les pages vues (PV) pour chaque code d'état
Calculez les PV pour chaque code d'état en utilisant la clause GROUP BY.
Instruction de requête
* | SELECT status, count(*) AS PV GROUP BY status
Résultats de la requête : une table comportant les colonnes status et PV, qui affiche chaque code d'état HTTP et son nombre de PV.
Exemple 2 : Calculer les PV horaires d'un site web
Calculez les PV d'un site web avec une granularité horaire en utilisant la clause GROUP BY.
Instruction de requête
Le champ __time__ est un champ réservé dans Simple Log Service qui représente la colonne temporelle. Dans cette requête, time est un alias pour date_trunc('hour', __time__). Pour plus d'informations sur la fonction date_trunc, consultez la fonction date_trunc.
* |
SELECT
count(*) AS PV,
date_trunc('hour', __time__) AS time
GROUP BY
time
ORDER BY
time
LIMIT
1000
Résultats de la requête : la requête renvoie un ensemble de résultats avec les colonnes PV et time. Dans les données d'exemple, les valeurs PV 1202, 10159 et 28001 correspondent respectivement à 2021-08-10 00:00:00.000, 2021-08-10 01:00:00.000 et 2021-08-10 02:00:00.000.
Exemple 3 : Calculer les PV avec une granularité de 5 minutes
Calculez les PV avec une granularité de 5 minutes en utilisant la clause GROUP BY.
Instruction de requête
La fonction date_trunc ne peut regrouper les données que par intervalle fixe. Pour regrouper les données par intervalle de temps personnalisé, utilisez l'opération modulo. Par exemple, % 300 aligne les horodatages sur une granularité de 5 minutes (300 secondes).
* |
SELECT
count(*) AS PV,
__time__-__time__ % 300 AS time
GROUP BY
time
LIMIT
1000
Résultats de la requête : la requête renvoie trois enregistrements : PV=143 pour time=1628525100, PV=31 pour time=1628526600 et PV=44 pour time=1628526900.
Exemple 4 : Regrouper indépendamment par méthode de requête et par état (GROUPING SETS)
Regroupez les données indépendamment par méthode de requête et par état, et calculez les PV pour chaque méthode de requête et pour chaque code d'état.
Instruction de requête
* |
SELECT
request_method,
status,
count(*) AS PV
GROUP BY
GROUPING SETS (request_method, status)
Résultats de la requête : lorsque les données sont regroupées par
request_method,statusest null, et le nombre de PV est de 189 pour GET, 47 pour POST, 39 pour PUT, 9 pour DELETE et 1 pour HEAD. Lorsque les données sont regroupées parstatus,request_methodest null, et le nombre de PV est, par exemple, de 259 pour 200, 2 pour 201 et 2 pour 202.
Exemple 5 : Regrouper par toutes les combinaisons de méthode de requête et d'état (CUBE)
Regroupez les données par méthode de requête et par état de requête. Les ensembles de regroupement incluent (null, null), (request_method, null), (null, status) et (request_method, status). Calculez les PV pour chaque ensemble de regroupement.
Instruction de requête
* |
SELECT
request_method,
status,
count(*) AS PV
GROUP BY
CUBE (request_method, status)
Résultats de la requête : l'ensemble de résultats contient les colonnes request_method, status et PV et comporte 43 enregistrements. Dans les lignes d'agrégation générées par CUBE, une valeur null pour
request_methodoustatusindique un sous-total pour cette dimension. Par exemple, le nombre de PV est de 285 pour null/null (le total général), 189 pour GET/null, 47 pour POST/null, 39 pour PUT/null, 9 pour DELETE/null et 1 pour HEAD/null. Le nombre de PV est de 259 pour null/200, et de 2 pour chacun des couples null/201 et null/202.
Exemple 6 : Générer des sous-totaux hiérarchiques pour la méthode de requête et l'état (ROLLUP)
Regroupez les données par méthode de requête et par état de requête. Les ensembles de regroupement incluent (request_method, status), (request_method, null) et (null, null). Calculez les PV pour chaque ensemble de regroupement.
Instruction de requête
* |
SELECT
request_method,
status,
count(*) AS PV
GROUP BY
ROLLUP (request_method, status)
Résultats de la requête : l'ensemble de résultats contient les colonnes request_method, status et PV et comporte 33 enregistrements. La fonction ROLLUP génère des lignes récapitulatives à chaque niveau de regroupement, où
nullindique que la colonne a été agrégée. Par exemple,GET / null / 189indique que le total des PV pour la méthode GET, tous codes d'état confondus, est de 189, etnull / null / 285indique que le total des PV pour toutes les méthodes et tous les codes d'état est de 285.
Exemple 7 : Regrouper automatiquement par plusieurs champs (GROUP BY ALL)
Calculez les PV par méthode de requête et par code d'état, et conservez uniquement les groupes comptant plus de 100 requêtes.
Instruction de requête
* |
SELECT
request_method,
status,
count(*) AS PV
GROUP BY ALL
HAVING count(*) > 100
ORDER BY PV DESC
Résultats de la requête : l'ensemble de résultats contient les colonnes request_method, status et PV. Seules les combinaisons comptant plus de 100 requêtes sont renvoyées, triées par PV dans l'ordre décroissant. Ce regroupement équivaut à
GROUP BY request_method, status.
Exemple 8 : Regrouper automatiquement par une expression (GROUP BY ALL)
Calculez les PV par méthode de requête avec une granularité de 5 minutes, sans répéter l'expression temporelle ni son alias.
Instruction de requête
* |
SELECT
__time__ - __time__ % 300 AS time,
request_method,
count(*) AS PV
GROUP BY ALL
ORDER BY time, request_method
LIMIT 1000
Résultats de la requête : l'ensemble de résultats contient les colonnes time, request_method et PV. Ce regroupement équivaut à
GROUP BY __time__ - __time__ % 300, request_method.
Exemple 9 : Classer les résultats groupés (GROUP BY ALL)
Calculez les PV pour chaque code d'état, puis classez les codes d'état par nombre de requêtes dans l'ordre décroissant.
Instruction de requête
* |
SELECT
status,
count(*) AS PV,
rank() OVER (ORDER BY count(*) DESC) AS ranking
GROUP BY ALL
ORDER BY ranking, status
Résultats de la requête : l'ensemble de résultats contient les colonnes status, PV et ranking. Seul
statusest utilisé comme clé de regroupement.count(*)effectue l'agrégation, etrank()classe les résultats agrégés sans participer au regroupement. Les codes d'état ayant le même nombre de requêtes obtiennent le même classement.