Tous les produits
Search
Centre de documentation

ApsaraDB for SelectDB:Profil de requête

Dernière mise à jour :Aug 11, 2026

Les profils de requête capturent les détails d'exécution par nœud pour chaque requête. Utilisez-les pour identifier les goulots d'étranglement et optimiser les performances.

Activer les profils de requête

Définissez la variable enable_profile pour lancer la collecte des profils :

SET enable_profile=true;
Remarque

Lorsque

enable_profile

est défini sur

true

, SelectDB génère un profil pour chaque requête exécutée. Chaque profil enregistre les détails d'exécution sur l'ensemble des nœuds.

Consulter les profils de requête

Important

L'instruction SHOW QUERY PROFILE est prise en charge uniquement pour les versions de SelectDB Core antérieures à V4.0.0. Pour SelectDB Core V4.0.0 et ultérieures, prévisualisez ou téléchargez les profils de requête depuis la console SelectDB, ou utilisez l'API HTTP. Pour plus de détails, reportez-vous à Utiliser la fonctionnalité d'audit de requête et Exporter les profils de requête.

Exécutez l'instruction suivante pour répertorier tous les profils stockés :

SHOW QUERY PROFILE "/"\G;

Chaque ligne du résultat correspond à un profil :

SHOW QUERY PROFILE "/"\G
*************************** 1. row ***************************
   Profile ID: c257c52f93e149ee-ace8ac14e8c9fef9
    Task Type: QUERY
   Start Time: 2021-04-08 11:30:50
     End Time: 2021-04-08 11:30:50
        Total: 9ms
   Task State: EOF
         User: root
   Default Db: default_cluster:db1
Sql Statement: select tbl1.k1, sum(tbl1.k2) from tbl1 join tbl2 on tbl1.k1 = tbl2.k1 group by tbl1.k1 order by tbl1.k1
Remarque

Dans les réponses de l'API HTTP, les champs

Query ID

et

query_id

font référence à l'ID du profil.

Analyser les profils de requête

Suivez ce processus en trois étapes pour localiser le goulot d'étranglement d'une requête. Chaque étape permet d'approfondir l'analyse d'un niveau dans la hiérarchie d'exécution.

Étape 1 : Identifier le fragment le plus lent

Objectif : Trouver le fragment qui constitue le goulot d'étranglement principal.

L'arborescence du plan d'exécution affiche la structure des fragments ainsi que leur temps d'exécution. La valeur MaxActiveTime de chaque nœud expéditeur correspond au temps d'exécution le plus long parmi toutes les unités d'exécution de ce fragment.

SHOW QUERY PROFILE "/<profile_id>"\G

Exemple de sortie :

SHOW QUERY PROFILE "/c257c52f93e149ee-ace8ac14e8c9fef9"\G
*************************** 1. row ***************************
Fragments:
             ┌──────────────────────┐
             │[-1: DataBufferSender]│
             │Fragment: 0           │
             │MaxActiveTime: 6.626 ms│
             └──────────────────────┘
                         │
               ┌──────────────────┐
               │[9: EXCHANGE_NODE]│
               │Fragment: 0       │
               └──────────────────┘
                         │
             ┌──────────────────────┐
             │[9: DataStreamSender] │
             │Fragment: 1           │
             │MaxActiveTime: 5.449 ms│
             └──────────────────────┘
                         │
                 ┌──────────────┐
                 │[4: SORT_NODE]│
                 │Fragment: 1   │
                 └──────────────┘
                        ┌┘
             ┌─────────────────────┐
             │[8: AGGREGATION_NODE]│
             │Fragment: 1          │
             └─────────────────────┘
                        └┐
               ┌──────────────────┐
               │[7: EXCHANGE_NODE]│
               │Fragment: 1       │
               └──────────────────┘
                         │
             ┌──────────────────────┐
             │[7: DataStreamSender] │
             │Fragment: 2           │
             │MaxActiveTime: 3.505 ms│
             └──────────────────────┘
                        ┌┘
             ┌─────────────────────┐
             │[3: AGGREGATION_NODE]│
             │Fragment: 2 │
             └─────────────────────┘
                        │
              ┌───────────────────┐
              │[2: HASH_JOIN_NODE]│
              │Fragment: 2        │
              └───────────────────┘
           ┌────────────┴────────────┐
 ┌──────────────────┐      ┌──────────────────┐
 │[5: EXCHANGE_NODE]│      │[6: EXCHANGE_NODE]│
 │Fragment: 2       │      │Fragment: 2       │
 └──────────────────┘      └──────────────────┘
           │                         │
┌─────────────────────┐ ┌────────────────────────┐
│[5: DataStreamSender]│ │[6: DataStreamSender] │
│Fragment: 4          │ │Fragment: 3             │
│MaxActiveTime: 1.87 ms│ │MaxActiveTime: 636.767 us│
└─────────────────────┘ └────────────────────────┘
           │                        ┌┘
 ┌───────────────────┐    ┌───────────────────┐
 │[0: OLAP_SCAN_NODE]│    │[1: OLAP_SCAN_NODE]│
 │Fragment: 4        │    │Fragment: 3        │
 └──────────────────┘      └──────────────────┘
           │                        │
    ┌─────────────┐          ┌─────────────┐
    │[OlapScanner]│          │[OlapScanner]│
    │Fragment: 4  │          │Fragment: 3  │
    └─────────────┘          └─────────────┘
           │                        │
  ┌─────────────────┐      ┌─────────────────┐
  │[SegmentIterator]│      │[SegmentIterator]│
  │Fragment: 4      │      │Fragment: 3      │
  └─────────────────┘      └─────────────────┘

1 row in set (0.02 sec)

Dans cet exemple, le Fragment 1 présente la valeur MaxActiveTime la plus élevée (5,449 ms) ; il s'agit donc du goulot d'étranglement principal. Passez à l'étape 2 en analysant le Fragment 1.

Étape 2 : Identifier l'unité d'exécution la plus lente

Objectif : Déterminer quelle instance de nœud, au sein du fragment identifié, consomme le plus de temps.

Une fois le fragment le plus lent identifié, listez toutes les unités d'exécution (instances) qu'il contient :

SHOW QUERY PROFILE "/<profile_id>/<fragment_id>";

Exemple de sortie pour le Fragment 1 :

SHOW QUERY PROFILE "/c257c52f93e149ee-ace8ac14e8c9fef9/1";
+-----------------------------------+-------------------+------------+
| Instances                         | Host              | ActiveTime |
+-----------------------------------+-------------------+------------+
| c257c52f93e149ee-ace8ac14e8c9ff03 | 10.200.00.01:9060 | 5.449ms    |
| c257c52f93e149ee-ace8ac14e8c9ff05 | 10.200.00.02:9060 | 5.367ms    |
| c257c52f93e149ee-ace8ac14e8c9ff04 | 10.200.00.03:9060 | 5.358ms    |
+-----------------------------------+-------------------+------------+

L'instance affichant la valeur ActiveTime la plus élevée sera votre cible pour l'étape 3.

Étape 3 : Inspecter les métriques par opérateur

Objectif : Déterminer quel opérateur consomme le plus de temps et de ressources sur l'unité d'exécution cible.

SHOW QUERY PROFILE "/<profile_id>/<fragment_id>/<instance_id>"\G

Exemple de sortie pour l'instance c257c52f93e149ee-ace8ac14e8c9ff03 du Fragment 1 :

SHOW QUERY PROFILE "/c257c52f93e149ee-ace8ac14e8c9fef9/1/c257c52f93e149ee-ace8ac14e8c9ff03"\G
*************************** 1. row ***************************
Instance:
 ┌───────────────────────────────────────┐
 │[9: DataStreamSender]                  │
 │(Active: 37.222 us, non-child: 0.40)    │
 │  - Counters:                          │
 │      - BytesSent: 0.00                │
 │      - IgnoreRows: 0                  │
 │      - OverallThroughput: 0.0 /sec    │
 │      - PeakMemoryUsage: 8.00 KB       │
 │      - SerializeBatchTime: 0ns        │
 │      - UncompressedRowBatchSize: 0.00 │
 └───────────────────────────────────────┘
                     └┐
                      │
    ┌──────────────────────────────────┐
    │[4: SORT_NODE]                    │
    │(Active: 5.421 ms, non-child: 0.71)│
    │  - Counters:                     │
    │      - PeakMemoryUsage: 12.00 KB │
    │ - RowsReturned: 0 │
    │      - RowsReturnedRate: 0       │
    └──────────────────────────────────┘
                     ┌┘
                     │
   ┌───────────────────────────────────┐
   │[8: AGGREGATION_NODE]              │
   │(Active: 5.355 ms, non-child: 10.68)│
   │  - Counters:                      │
   │      - BuildTime: 3.701us         │
   │      - GetResultsTime: 0 ns        │
   │      - HTResize: 0                │
   │      - HTResizeTime: 1.211 us      │
   │      - HashBuckets: 0             │
   │      - HashCollisions: 0          │
   │      - HashFailedProbe: 0         │
   │      - HashFilledBuckets: 0       │
   │      - HashProbe: 0               │
   │      - HashTravelLength: 0        │
   │      - LargestPartitionPercent: 0 │
   │      - MaxPartitionLevel: 0       │
   │      - NumRepartitions: 0         │
   │      - PartitionsCreated: 16      │
   │      - PeakMemoryUsage: 34.02 MB  │
   │      - RowsProcessed: 0           │
   │      - RowsRepartitioned: 0       │
   │      - RowsReturned: 0            │
   │      - RowsReturnedRate: 0        │
   │      - SpilledPartitions: 0       │
   └───────────────────────────────────┘
                     └┐
                      │
┌──────────────────────────────────────────┐
│[7: EXCHANGE_NODE]                        │
│(Active: 4.360 ms, non-child: 46.84)       │
│  - Counters:                             │
│      - BytesReceived: 0.00               │
│      - ConvertRowBatchTime: 387 ns        │
│      - DataArrivalWaitTime: 4.357 ms      │
│      - DeserializeRowBatchTimer: 0 ns     │
│      - FirstBatchArrivalWaitTime: 4.356 ms│
│      - PeakMemoryUsage: 0.00             │
│      - RowsReturned: 0                   │
│      - RowsReturnedRate: 0               │
│      - SendersBlockedTotalTimer(*): 0 ns  │
└──────────────────────────────────────────┘

Un pourcentage Active élevé associé à un pourcentage non-child important sur un nœud indique que ce nœud est lui-même le goulot d'étranglement (et non un opérateur enfant). Concentrez vos efforts d'optimisation sur ce point.

Exporter les profils de requête

Important

L'exportation des profils de requête nécessite SelectDB Core V3.0.4 ou version ultérieure.

Exportez un profil vers un fichier pour une analyse hors ligne ou pour le partager.

  1. Activez les profils de requête.

    SET enable_profile=true;
  2. Exécutez la requête à profiler.

    -- Run your target query. SelectDB generates a profile for it.
    SELECT count(1) FROM test_table LIMIT 10;
  3. Récupérez l'ID du profil.

    Versions SelectDB 4.0.x

    Envoyez une requête HTTP pour obtenir les informations de requête. Le champ Query ID dans la réponse correspond à l'ID du profil.

    curl -u'<userName>:<userPassword>' \
      "http://<selectdbAddress>:<httpPort>/rest/v2/manager/query/query_info?is_all_node=true"

    Exemple de réponse :

    {
      "msg": "success",
      "code": 0,
      "data": {
        "column_names": [
          "Query ID",
          "FE Node",
          "Query User",
          "Execution Database",
          "Sql",
          "Query Type",
          "Start Time",
          "End Time",
          "Execution Duration",
          "Status"
        ],
        "rows": [
          [
            ...
          ]
        ]
      },
      "count": 0
    }

    Versions SelectDB 3.0.x

    L'exemple suivant montre comment procéder avec SelectDB 3.0 :

    SHOW QUERY PROFILE "/";

    Exemple de sortie :

    +-----------------------------------+-----------+---------------------+---------------------+-------+------------+-------+------------------------------------+-------------------------------+
    | Profile ID                        | Task Type | Start Time          | End Time            | Total | Task State | User  | Default Db                         | Sql Statement                 |
    +-----------------------------------+-----------+---------------------+---------------------+-------+------------+-------+------------------------------------+-------------------------------+
    | b9c9ba063d9d4365-97878361371e757a | QUERY     | 2024-02-07 17:40:04 | 2024-02-07 17:40:04 | 32ms  | EOF        | admin | default_cluster:information_schema | select * from user_privileges |
    | 8800c306137e4072-9bb1ed419f4ac9f2 | QUERY     | 2024-02-07 17:40:00 | 2024-02-07 17:40:00 | 3ms   | ERR        | admin | default_cluster:information_schema | select * from user_priveleges |
    | e2efdd1a996c4de2-ab939ad49b409990 | QUERY     | 2024-02-07 17:39:51 | 2024-02-07 17:39:51 | 13ms  | EOF        | admin |                                    | SELECT DATABASE()             |
    +-----------------------------------+-----------+---------------------+---------------------+-------+------------+-------+------------------------------------+-------------------------------+
  4. Exportez le profil à l'aide de son ID.

    Espace réservé Description Valeur par défaut
    <userName> Nom d'utilisateur pour accéder à l'instance SelectDB
    <userPassword> Mot de passe pour accéder à l'instance SelectDB
    <selectdbAddress> Endpoint de l'instance SelectDB
    <httpPort> Numéro de port HTTP 8080
    <query_id> ID du profil obtenu à l'étape 3
    curl -u'<userName>:<userPassword>' \
      "http://<selectdbAddress>:<httpPort>/api/profile?query_id=<query_id>"

    Pour enregistrer la sortie dans un fichier, redirigez la réponse :

    curl -u'<userName>:<userPassword>' \
      "http://<selectdbAddress>:<httpPort>/api/profile?query_id=<query_id>" > res.txt

    Remplacez les espaces réservés suivants par vos valeurs réelles :

  5. (Facultatif) Formatez le fichier exporté pour en améliorer la lisibilité.

    sudo sed -r 's/\\n/\n/g' res.txt | sed -r 's/\\t/\t/g' > new.txt

Référence des paramètres de profil

Les tableaux suivants décrivent l'ensemble des paramètres collectés dans un profil de requête.

Fragment

Paramètre Description
AverageThreadTokens Nombre de threads utilisés pour l'exécution du fragment, hors utilisation du pool de threads.
Buffer Pool PeakReservation Utilisation mémoire maximale du buffer pool.
MemoryLimit Limite de mémoire allouée à la requête.
PeakMemoryUsage Consommation mémoire maximale d'une unité d'exécution durant la requête.
RowsProduced Nombre de lignes dont les colonnes ont été traitées.

BlockMgr

Paramètre Description
BlocksCreated Nombre de blocs créés par le BlockManager.
BlocksRecycled Nombre de blocs réutilisés.
BytesWritten Taille totale des données écrites sur disque.
MaxBlockSize Taille d'un bloc unique.
TotalReadBlockTime Temps total consacré à la lecture des blocs.

DataStreamSender

Paramètre Description
BytesSent Taille totale des données envoyées. Calcul : nombre de destinataires × taille des données envoyées.
IgnoreRows Nombre de lignes filtrées.
LocalBytesSent Volume de données transmises par le nœud local et reçues par ce même nœud lors de l'échange de données.
OverallThroughput Débit global. Calcul : BytesSent / temps d'exécution.
SerializeBatchTime Temps nécessaire à la sérialisation des données avant envoi.
UncompressedRowBatchSize Taille des données RowBatch envoyées avant compression.

ODBC_TABLE_SINK

Paramètre Description
NumSentRows Nombre total de lignes écrites dans une table externe.
TupleConvertTime Temps consacré à la sérialisation des données envoyées sous forme d'instructions INSERT.
ResultSendTime Temps consacré à l'écriture des données via le pilote Open Database Connectivity (ODBC).

EXCHANGE_NODE

Paramètre Description
BytesReceived Volume de données reçues via le réseau.
MergeGetNext Si un tri est effectué sur le nœud enfant, le nœud d'échange réalise une fusion et un tri unifiés. Cette métrique représente le temps total de cette opération, y compris MergeGetNextBatch.
MergeGetNextBatch Temps nécessaire au nœud de fusion pour récupérer les données. Pour une fusion et un tri à un seul niveau, les données proviennent d'une file d'attente réseau. Pour une fusion et un tri multiniveaux, elles proviennent d'un fusionneur enfant.
ChildMergeGetNext Lorsque de nombreux expéditeurs transmettent des données, la fusion monothread devient un goulot d'étranglement. ApsaraDB for SelectDB lance alors plusieurs threads sur le nœud de fusion enfant pour effectuer la fusion et le tri en parallèle. Cette valeur cumule le temps de tous les threads.
ChildMergeGetNextBatch Temps nécessaire au nœud de fusion enfant pour récupérer les données. Des valeurs élevées peuvent signaler des goulots d'étranglement au niveau du nœud d'envoi enfant.
DataArrivalWaitTime Temps d'attente total pour la réception des données depuis l'expéditeur.
FirstBatchArrivalWaitTime Délai d'attente avant la réception du premier lot de données de l'expéditeur.
DeserializeRowBatchTimer Temps consacré à la désérialisation des données réseau.
SendersBlockedTotalTimer(*) Temps d'attente cumulé côté expéditeur lorsque la mémoire de la file DataStreamRecv est saturée.
ConvertRowBatchTime Temps nécessaire pour convertir les données reçues en RowBatch.
RowsReturned Nombre de lignes reçues.
RowsReturnedRate Taux de réception des lignes.

SORT_NODE

Paramètre Description
InMemorySortTime Temps consacré au tri en mémoire.
InitialRunsCreated Nombre d'initialisations du tri. La valeur est 1 pour un tri en mémoire.
SortDataSize Taille totale des données triées.
MergeGetNext Temps nécessaire à MergeSort pour obtenir le lot suivant à partir de plusieurs séquences triées. Mesuré uniquement lors de l'écriture sur disque.
MergeGetNextBatch Temps nécessaire à MergeSort pour extraire le lot de la prochaine séquence triée. Mesuré uniquement lors de l'écriture sur disque.
TotalMergesPerformed Nombre de fusions externes effectuées.

AGGREGATION_NODE

Paramètre Description
PartitionsCreated Nombre de partitions générées par la division de la requête d'agrégation.
GetResultsTime Temps nécessaire pour récupérer les résultats d'agrégation depuis les partitions.
HTResizeTime Temps consacré au redimensionnement de la table de hachage.
HTResize Nombre de redimensionnements de la table de hachage.
HashBuckets Nombre de compartiments (buckets) dans la table de hachage.
HashBucketsWithDuplicate Nombre de compartiments contenant des nœuds dupliqués dans la table de hachage.
HashCollisions Nombre de collisions de hachage dans la table.
HashDuplicateNodes Nombre de nœuds dupliqués appartenant au même compartiment dans la table de hachage.
HashFailedProbe Nombre d'opérations de sondage échouées sur la table de hachage.
HashFilledBuckets Nombre de compartiments remplis de données dans la table de hachage.
HashProbe Nombre de requêtes effectuées sur la table de hachage.
HashTravelLength Nombre de déplacements effectués lors d'une requête sur la table de hachage.

HASH_JOIN_NODE

Paramètre Description
ExecOption Méthode de construction de la table de hachage pour le nœud enfant droit : synchrone ou asynchrone.
BuildBuckets Nombre de compartiments dans la table de hachage.
BuildRows Nombre de lignes dans la table de hachage.
BuildTime Temps consacré à la construction de la table de hachage.
LoadFactor Facteur de charge de la table de hachage, indiquant le nombre de compartiments non vides.
ProbeRows Nombre de lignes sur lesquelles l'opération de sondage de hachage est effectuée après le parcours des nœuds enfants gauches.
ProbeTime Temps consacré au parcours des nœuds enfants gauches pour le sondage de hachage, hors temps d'appel à GetNext sur RowBatch depuis le nœud enfant gauche.
PushDownComputeTime Temps consacré au calcul des conditions de pushdown de prédicats.
PushDownTime Temps total consacré au pushdown de prédicats. Les requêtes JOIN sur les nœuds enfants droits qui satisfont aux conditions sont converties en requêtes IN sur les nœuds enfants gauches.

CROSS_JOIN_NODE

Paramètre Description
ExecOption Méthode de construction de la RowBatchList pour le nœud enfant droit : synchrone ou asynchrone.
BuildRows Nombre de lignes de la RowBatchList (lignes du nœud enfant droit).
BuildTime Temps consacré à la construction de la RowBatchList.
LeftChildRows Nombre de lignes dans le nœud enfant gauche.
LeftChildTime Temps consacré au parcours des nœuds enfants gauche et droit pour générer le produit cartésien, hors temps d'appel à GetNext sur RowBatch depuis le nœud enfant gauche.

UNION_NODE

Paramètre Description
MaterializeExprsEvaluateTime Temps consacré à l'évaluation des expressions de conversion de type et à la matérialisation des résultats lorsque les types de champs diffèrent de part et d'autre d'un UNION.

ANALYTIC_EVAL_NODE

Paramètre Description
EvaluationTime Temps total consacré au calcul des fonctions analytiques (fonctions de fenêtrage).
GetNewBlockTime Temps consacré à l'allocation d'un nouveau bloc lors de l'initialisation. Ce bloc met en cache la fenêtre Rows ou une partition entière pour le calcul de la fonction analytique.
PinTime Temps consacré à l'allocation d'un nouveau bloc ou à la relecture en mémoire d'un bloc précédemment écrit sur disque.
UnpinTime Temps consacré à l'écriture des données d'un bloc sur disque lorsque celui-ci n'est plus nécessaire ou lorsque l'opérateur actuel subit une forte pression mémoire.

OLAP_SCAN_NODE

OLAP_SCAN_NODE gère les tâches de balayage des données. Il crée un ou plusieurs scanners OLAP, chacun étant responsable du balayage d'une partie des données. Le profil s'organise en trois couches reflétant la hiérarchie des appels : OLAP_SCAN_NODE -> OlapScanner -> SegmentIterator.

Certaines ou toutes les conditions de prédicat sont transmises à OLAP_SCAN_NODE. Les conditions pouvant exploiter les index du moteur de stockage sont transmises plus loin à ce dernier pour filtrage ; les autres sont évaluées directement dans OLAP_SCAN_NODE.

Remarque

Certaines valeurs de métriques varient selon le format de stockage (V1 ou V2).

L'exemple suivant illustre un profil OLAP_SCAN_NODE typique :

OLAP_SCAN_NODE (id=0):(Active: 1.2ms, % non-child: 0.00%)
  - BytesRead: 265.00 B                 # Size of data read from data files. For example, 10 x 32-bit integers = 40 bytes. This reflects data fully loaded into memory, not raw I/O size.
  - NumDiskAccess: 1                    # Number of disks accessed by the ScanNode.
  - NumScanners: 20                     # Number of scanners created by the ScanNode.
  - PeakMemoryUsage: 0.00               # Peak memory usage during the query.
  - RowsRead: 7                         # Rows returned from the storage engine to the scanner, excluding rows filtered by the scanner.
  - RowsReturned: 7                     # Rows returned from the ScanNode to the parent node.
  - RowsReturnedRate: 6.979K /sec       # RowsReturned / ActiveTime.
  - TabletCount: 20                     # Number of tablets accessed by the ScanNode.
  - TotalReadThroughput: 74.70 KB/sec   # BytesRead divided by total execution time. For I/O-bound queries, this approaches total disk throughput.
  - ScannerBatchWaitTime: 426.886us     # Time for the transfer thread to wait for the scanner thread to return RowBatch data.
  - ScannerWorkerWaitTime: 17.745us     # Time for the scanner thread to wait for available worker threads in the thread pool.
  OlapScanner:
    - BlockConvertTime: 8.941us         # Time to convert a vectorized block to a row-structured RowBlock. The vectorized block is VectorizedRowBatch (V1) or RowBlockV2 (V2).
    - BlockFetchTime: 468.974us         # Time for the rowset reader to get blocks.
    - ReaderInitTime: 5.475ms           # Time for the OLAP scanner to initialize readers. Includes MergeHeap creation time (V1) and the time to generate all iterator levels and read the first block group (V2).
    - RowsDelFiltered: 0                # Rows filtered based on DELETE information in the tablet and rows marked for deletion in the Unique Key model.
    - RowsPushedCondFiltered: 0         # Rows filtered by predicates pushed down from a join operation (e.g., from BuildTable to ProbeTable). This value is approximate; filtering may be skipped if the effect is poor.
    - ScanTime: 39.24us                 # Time for data to travel from ScanNode to the parent node.
    - ShowHintsTime_V1: 0ns             # V1 only: time to read some data for ScanRange splitting.
    SegmentIterator:
      - BitmapIndexFilterTimer: 779ns   # Time to filter data using bitmap indexes.
      - BlockLoadTime: 415.925us        # Time for the segment reader (V1) or segment iterator (V2) to get blocks.
      - BlockSeekCount: 12              # Number of block seeks during segment reading.
      - BlockSeekTime: 222.556us        # Time consumed for block seeks during segment reading.
      - BlocksLoad: 6                   # Number of blocks read.
      - CachedPagesNum: 30              # V2 only: number of pages that hit the page cache.
      - CompressedBytesRead: 0.00       # V1: size of data before decompression read from file. V2: size of pages before compression that did not hit the page cache.
      - DecompressorTimer: 0ns          # Time consumed for data decompression.
      - IOTimer: 0ns                    # Actual I/O time for reading data from the operating system.
      - IndexLoadTime_V1: 0ns           # V1 only: time to read index streams.
      - NumSegmentFiltered: 0           # Number of segments completely filtered out based on column statistics and query conditions.
      - NumSegmentTotal: 6              # Total number of segments involved in the query.
      - RawRowsRead: 7                  # Source data rows read from the storage engine after all preceding filtering.
      - RowsBitmapIndexFiltered: 0      # V2 only: rows filtered using bitmap indexes.
      - RowsBloomFilterFiltered: 0      # V2 only: rows filtered using BloomFilter indexes.
      - RowsKeyRangeFiltered: 0         # V2 only: rows filtered using SortkeyIndex indexes.
      - RowsStatsFiltered: 0            # V2: rows filtered using ZoneMap indexes, including delete conditions. V1: includes rows filtered using BloomFilter indexes.
      - RowsConditionsFiltered: 0       # V2 only: rows filtered by all column indexes combined.
      - RowsVectorPredFiltered: 0       # Rows filtered by vectorized condition operations.
      - TotalPagesNum: 30               # V2 only: total number of pages read.
      - UncompressedBytesRead: 0.00     # V1: size of data after decompression (or file size if not compressed). V2: size of pages that did not hit the page cache after decompression (or page size if not compressed).
      - VectorPredEvalTime: 0ns         # Time to perform filtering by vectorized condition.
      - ShortPredEvalTime: 0ns          # Time to perform filtering by short-circuit predicate.
      - PredColumnReadTime: 0ns         # Time consumed for predicate column reading.
      - LazyReadTime: 0ns               # Time consumed to read non-predicate columns.
      - OutputColumnTime: 0ns           # Time consumed for column materialization.

Relations entre les métriques de filtrage

Les métriques de comptage de lignes d'un profil OLAP_SCAN_NODE révèlent l'efficacité avec laquelle les prédicats et les index réduisent le volume de données à chaque étape. Ce qui suit décrit la séquence de filtrage au format V2. Les métriques du format V1 ont des significations légèrement différentes.

Phase d'initialisation

Le filtrage s'effectue dans l'ordre suivant :

  1. SortkeyIndex — Si la requête comporte des plages de clés (plages de clés préfixées), les données sont filtrées en premier. Les lignes éliminées sont comptabilisées dans RowsKeyRangeFiltered.

  2. Index Bitmap — Un filtrage précis par colonne est appliqué pour les conditions correspondant aux index bitmap. Les lignes éliminées sont comptabilisées dans RowsBitmapIndexFiltered.

  3. Index BloomFilter — Les conditions d'égalité (=, IN, IS) sont filtrées à l'aide des index BloomFilter. Les lignes éliminées sont comptabilisées dans RowsBloomFilterFiltered.

    Remarque

    RowsBloomFilterFiltered

    est calculé comme le nombre total de lignes du segment moins les lignes restantes après le filtrage BloomFilter. Un chevauchement avec les lignes déjà éliminées par les index bitmap est possible.

  4. Index ZoneMap — Les données sont filtrées selon les conditions de requête et de suppression. Les lignes éliminées sont comptabilisées dans RowsStatsFiltered.

  5. RowsConditionsFiltered correspond au total des lignes filtrées par l'ensemble des index combinés, y compris RowsBloomFilterFiltered et RowsStatsFiltered.

Phase suivante

Après l'initialisation, les données restantes passent par plusieurs étapes supplémentaires :

  • RowsDelFiltered : Lignes éliminées par les conditions de suppression. Elles sont également comptabilisées dans RowsStatsFiltered.

  • RawRowsRead : Lignes restantes après tous les filtrages précédents.

  • RowsRead : Lignes renvoyées par le moteur de stockage au scanner. Cette valeur est généralement inférieure à RawRowsRead car le moteur de stockage peut agréger des lignes. Un écart important entre RawRowsRead et RowsRead signale une agrégation intensive, ce qui peut impacter les performances.

  • RowsReturned : Lignes finalement renvoyées par ScanNode au nœud parent. Cette valeur est généralement inférieure à RowsRead car les prédicats non transmis au moteur de stockage sont appliqués au niveau du scanner. Un écart important entre RowsRead et RowsReturned signifie que de nombreux prédicats à haute sélectivité n'atteignent pas le moteur de stockage, où le filtrage serait pourtant plus efficace.

Prises ensemble, les métriques Rows***Filtered permettent d'évaluer si les prédicats de requête sont bien transmis au moteur de stockage et de mesurer l'efficacité de chaque type d'index.

Autres métriques

  • Les métriques situées sous OlapScanner — telles que IOTimer et BlockFetchTime — sont cumulatives sur l'ensemble des threads du scanner. Comme ces threads lisent les données de manière asynchrone, ces valeurs accumulées reflètent le temps de travail total des scanners, et non le temps horloge murale du ScanNode. Le pourcentage Active enregistre la proportion réelle du temps pendant lequel ScanNode a contribué au plan d'exécution global. Il est normal d'observer un IOTimer de plusieurs dizaines de secondes alors que Active ne dépasse pas quelques secondes, pour deux raisons :

    • IOTimer cumule le temps de nombreux scanners fonctionnant en parallèle.

    • Si le nœud parent est lent (par exemple 100 secondes), ScanNode (10 secondes) termine rapidement et prépare les données en arrière-plan. Le parent récupère ensuite les données préparées, ce qui explique pourquoi le temps Active de ScanNode est court.

  • NumScanners correspond au nombre de tâches soumises par le scanner au pool de threads, géré par RuntimeState. Les paramètres doris_scanner_thread_pool_thread_num et doris_scanner_thread_pool_queue_size contrôlent respectivement la taille du pool de threads et la longueur de la file d'attente. Un nombre de threads excessif ou insuffisant affecte l'efficacité de la requête. Vous pouvez également diviser certaines métriques par le nombre de threads pour estimer approximativement le temps consommé par chaque thread.

  • TabletCount indique le nombre de tablettes à balayer. Un nombre élevé implique davantage de lectures aléatoires et d'opérations de fusion de données.

  • UncompressedBytesRead reflète le volume de données lu. Une valeur élevée peut indiquer une charge E/S importante.

  • Comparez CachedPagesNum à TotalPagesNum pour évaluer le taux de réussite du cache de pages. Un taux plus élevé réduit à la fois les E/S et la surcharge de décompression.

Buffer pool

Paramètre Description
AllocTime Temps consacré à l'allocation mémoire.
CumulativeAllocationBytes Taille cumulée de la mémoire allouée.
CumulativeAllocations Nombre cumulé d'allocations mémoire.
PeakReservation Taille maximale de réservation.
PeakUnpinnedBytes Taille des données mémoire non épinglées (unpinned).
PeakUsedReservation Utilisation mémoire des réservations.
ReservationLimit Limite de réservation dans le buffer pool.

Étapes suivantes