FETCH FIRST Oracle : limiter les résultats SQL facilement

Apprenez à utiliser FETCH FIRST en Oracle SQL pour limiter vos résultats. Syntaxe, exemples pratiques et erreurs courantes expliqués clairement.

Illustration du tutoriel SQL Oracle : FETCH FIRST Oracle : limiter les résultats SQL facilement

FETCH FIRST en Oracle SQL : limiter le nombre de lignes retournées

La clause FETCH FIRST est une fonctionnalité introduite dans Oracle 12c qui permet de limiter facilement le nombre de lignes retournées par une requête SQL. Disponible depuis Oracle Database 12.1, elle remplace avantageusement les anciennes techniques basées sur ROWNUM. Que vous construisiez des classements, des tops produits ou une pagination, FETCH FIRST simplifie l’écriture de vos requêtes tout en améliorant leur lisibilité.

Publicité

Définition et utilisation de FETCH FIRST

La clause FETCH FIRST fait partie de la syntaxe de limitation de lignes (Row Limiting Clause) introduite dans le standard SQL:2008 et implémentée dans Oracle 12c. Elle s’utilise en combinaison avec la clause ORDER BY pour sélectionner un nombre précis de lignes en haut d’un jeu de résultats trié.

Pourquoi utiliser FETCH FIRST plutôt que ROWNUM ?

Avant Oracle 12c, la méthode classique pour limiter les résultats était d’utiliser ROWNUM dans une sous-requête, ce qui rendait le code verbeux et sujet à des erreurs subtiles. La clause FETCH FIRST offre une syntaxe plus claire, plus proche du langage naturel, et s’intègre directement dans la requête principale sans nécessiter d’imbrication.

Cas d’usage en entreprise

  • Top N produits : afficher les 10 articles les plus vendus d’un catalogue e-commerce.
  • Classements RH : récupérer les 5 employés avec les salaires les plus élevés.
  • Pagination : afficher la première page de résultats dans une interface utilisateur.
  • Monitoring : isoler les N dernières erreurs dans un journal d’événements.
  • Rapports financiers : extraire les 20 clients avec le chiffre d’affaires le plus important.

Syntaxe complète de FETCH FIRST

La syntaxe officielle de la clause de limitation de lignes avec FETCH FIRST en Oracle est la suivante :

SELECT colonnes
FROM table
[WHERE conditions]
[ORDER BY colonne [ASC | DESC]]
[OFFSET n ROWS]
FETCH { FIRST | NEXT } { n [PERCENT] } ROWS { ONLY | WITH TIES };

Explication des paramètres

ParamètreDescription
FETCH FIRSTIndique que l’on souhaite récupérer les premières lignes du résultat trié.
FETCH NEXTSynonyme de FETCH FIRST, utilisé pour la lisibilité avec OFFSET.
nLe nombre de lignes (ou le pourcentage) à retourner.
PERCENTSi présent, n représente un pourcentage du total des lignes.
ROWS ONLYRetourne exactement n lignes, sans exception.
ROWS WITH TIESRetourne n lignes minimum, mais inclut les lignes ex-æquo sur le dernier rang.
OFFSET n ROWSIgnore les n premières lignes avant d’appliquer FETCH FIRST (pagination).

Note importante : L’utilisation de FETCH FIRST sans ORDER BY est techniquement possible mais déconseillée, car l’ordre des lignes retournées serait indéterministe.

Exemples pratiques de FETCH FIRST en Oracle

Exemple 1 – Top 5 des employés les mieux payés

Contexte métier : Un responsable RH souhaite obtenir la liste des 5 employés percevant les salaires les plus élevés dans la table EMPLOYEES (schéma HR d’Oracle).

-- Sélection des 5 employés avec les salaires les plus élevés
SELECT
    employee_id,
    first_name || ' ' || last_name AS nom_complet,
    salary,
    department_id
FROM employees
ORDER BY salary DESC
FETCH FIRST 5 ROWS ONLY;

Résultat attendu : Les 5 lignes correspondant aux salaires les plus élevés, triées de manière décroissante. La clause ONLY garantit qu’exactement 5 lignes sont retournées, même si plusieurs employés ont le même salaire que le 5e.

Exemple 2 – Pagination avec OFFSET et FETCH FIRST

Contexte métier : Une application e-commerce affiche un catalogue de produits par pages de 10 articles. Pour afficher la 3e page, il faut ignorer les 20 premiers résultats et récupérer les 10 suivants.

-- Affichage de la 3e page d'un catalogue produits (10 articles par page)
-- Page 1 : OFFSET 0, Page 2 : OFFSET 10, Page 3 : OFFSET 20
SELECT
    product_id,
    product_name,
    list_price,
    category_id
FROM products
ORDER BY list_price ASC, product_id ASC
OFFSET 20 ROWS          -- On ignore les 20 premiers résultats
FETCH NEXT 10 ROWS ONLY; -- On récupère les 10 lignes suivantes

Explication : L’utilisation de FETCH NEXT à la place de FETCH FIRST est ici purement stylistique, mais améliore la lisibilité en indiquant clairement que l’on prend les lignes « suivantes » après l’offset. Le double critère de tri (list_price puis product_id) assure un ordre stable entre les pages.

Exemple bonus – Utilisation de WITH TIES

Contexte métier : On souhaite afficher les 3 meilleurs clients par chiffre d’affaires, en incluant tous les clients ex-æquo sur la 3e place.

-- Top 3 clients avec gestion des ex-æquo
SELECT
    client_id,
    client_name,
    chiffre_affaires
FROM clients
ORDER BY chiffre_affaires DESC
FETCH FIRST 3 ROWS WITH TIES;

Si deux clients partagent le 3e rang, la requête retournera 4 lignes (ou plus) au lieu de 3. C’est le comportement attendu avec WITH TIES.

Publicité

Erreurs courantes avec FETCH FIRST

Erreur : utiliser FETCH FIRST sans ORDER BY sur une colonne stable

Problème : De nombreux développeurs utilisent FETCH FIRST sans clause ORDER BY, ou avec un ordre non déterministe (ex : tri sur une colonne contenant des doublons sans discriminant secondaire). Cela peut produire des résultats incohérents d’une exécution à l’autre, notamment lors d’une pagination.

-- ❌ Requête incorrecte : tri non stable, résultats imprévisibles entre pages
SELECT product_id, product_name
FROM products
ORDER BY category_id  -- Plusieurs produits peuvent avoir le même category_id
OFFSET 10 ROWS
FETCH NEXT 10 ROWS ONLY;
-- ✅ Requête correcte : ajout d'un discriminant unique pour garantir l'ordre
SELECT product_id, product_name
FROM products
ORDER BY category_id, product_id  -- product_id est unique = ordre garanti
OFFSET 10 ROWS
FETCH NEXT 10 ROWS ONLY;

Solution : Ajoutez toujours une colonne unique (comme une clé primaire) comme critère de tri secondaire pour garantir un ordre stable et des pages de résultats cohérentes.

Note de compatibilité : La clause FETCH FIRST n’est disponible qu’à partir d’Oracle Database 12c (12.1). Sur les versions antérieures, il faut utiliser ROWNUM ou la fonction analytique ROW_NUMBER().

Résumé

Tableau récapitulatif des points clés

Point cléDétail
DisponibilitéOracle Database 12c (12.1) et versions supérieures
Objectif principalLimiter le nombre de lignes retournées par une requête
ROWS ONLYRetourne exactement N lignes
ROWS WITH TIESInclut les lignes ex-æquo sur le dernier rang
PERCENTLimite en pourcentage du total de lignes
OFFSETSaute les N premières lignes (pagination)
Alternative ancienneROWNUM ou ROW_NUMBER() pour Oracle < 12c

2 bonnes pratiques Oracle

  1. Toujours associer FETCH FIRST à un ORDER BY déterministe : utilisez systématiquement une colonne unique (clé primaire) comme critère de tri secondaire pour garantir des résultats reproductibles, surtout dans un contexte de pagination.
  2. Préférer FETCH FIRST à ROWNUM pour Oracle 12c+ : la clause de limitation de lignes est plus lisible, plus maintenable et moins sujette aux erreurs de sous-requête que l’ancienne méthode WHERE ROWNUM <= n. Elle exprime clairement l’intention du développeur.

Aller plus loin

Pour approfondir vos connaissances sur la gestion des résultats et le classement en Oracle SQL, découvrez ces sujets complémentaires :

Sur le même thème

Publicité

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée. Les champs obligatoires sont indiqués avec *

Publicité