Site icon

grep vs ripgrep : comparatif complet pour développeurs et sysadmins Linux

grep vs ripgrep comparatif complet pour developpeurs et sysadmins Linux

Comparatif grep vs ripgrep : performances, fonctionnalités et cas d'usage concrets sous Linux

Introduction

Linux · Performance · Outils CLI

Chercher du texte dans des fichiers, c’est le pain quotidien du sysadmin et du développeur. grep règne depuis 1974, mais ripgrep (rg) a révolutionné la vitesse de recherche. Ce comparatif couvre les benchmarks réels, les différences de comportement et les cas d’usage concrets pour choisir le bon outil.

grep vs ripgrep — deux philosophies pour la recherche de texte sous Linux

grep vs ripgrep : les fondamentaux

grep — l’incontournable depuis 1974

Écrit par Ken Thompson en 1974, grep (Global Regular Expression Print) est un pilier d’Unix. Présent dans tout système POSIX (Linux, BSD, macOS, conteneurs Alpine, BusyBox), il est garanti disponible partout. GNU grep, la version standard sur Linux, utilise le moteur regex PCRE (ou POSIX étendu par défaut) et supporte les options classiques : -r (récursif), -n (numéros de ligne), -l (noms de fichiers), -E (extended regex).

ℹ️ Info — Philosophie POSIX

grep suit la philosophie Unix : faire une chose, la faire bien. Il lit depuis stdin ou des fichiers, respecte les conventions POSIX, et s’intègre dans n’importe quel pipeline. C’est pour ça qu’on le retrouve dans les Dockerfiles, les scripts de CI et les crons depuis 50 ans.

ripgrep — la recherche réinventée en Rust

ripgrep (rg), créé par Andrew Gallant (BurntSushi) en 2016, est un outil de recherche récursif écrit en Rust. Il vise à remplacer grep pour la recherche de code avec plusieurs innovations majeures :

Disponible via apt install ripgrep, dnf install ripgrep ou cargo install ripgrep.

Table comparative détaillée

Critère grep ripgrep (rg)
Première version 1974 2016
Langage C Rust
Parallélisme Non (mono-thread) Oui (multi-thread auto)
Moteur regex POSIX / PCRE Rust regex (DFA/SIMD)
.gitignore respect Non Oui (par défaut)
Ignore les binaires Non (option -I) Oui (par défaut)
Ignore les fichiers cachés Non Oui (par défaut)
Coloration par défaut Non (alias) Oui
Filtrage par type de fichier --include/--exclude -t / -g (plus expressif)
Portabilité Universelle (POSIX) Linux, macOS, Windows
Numéros de ligne -n Par défaut

Benchmarks : performances réelles

Les benchmarks ont été effectués sur les sources du noyau Linux v6.12 (~80 000 fichiers, ~1.2 Go). Machine : 8 cœurs, 16 Go RAM, SSD NVMe, Debian 13.

# Recherche simple : "CONFIG_NET"
$ time grep -r "CONFIG_NET" linux-6.12/ 2>/dev/null | wc -l
42713

real    0m3.842s
user    0m3.214s
sys     0m0.628s

$ time rg "CONFIG_NET" linux-6.12/ | wc -l
42713

real    0m0.187s
user    0m1.412s
sys     0m0.234s

# Recherche avec contexte : "Kconfig" + 2 lignes avant/après
$ time grep -rn -C2 "source \"arch" linux-6.12/ 2>/dev/null | wc -l
482

real    0m4.216s

$ time rg -C2 "source \"arch" linux-6.12/ | wc -l
482

real    0m0.098s

# Regex complexe : adresses email
$ time grep -rE "[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}" linux-6.12/ 2>/dev/null | wc -l
842

real    0m5.127s

$ time rg -e "[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}" linux-6.12/ | wc -l
842

real    0m0.314s
Test grep ripgrep Speedup
Recherche simple 3.84s 0.19s ~20×
Recherche + contexte 4.22s 0.10s ~42×
Regex complexe 5.13s 0.31s ~16×

💡 Astuce — Consommation mémoire

ripgrep utilise le memory-mapping (mmap) quand c'est possible, ce qui délègue la gestion mémoire au noyau. Résultat : la consommation RSS reste faible (~15-30 Mo) même sur des codebases de plusieurs Go, là où grep charge les fichiers en userspace.

Moteurs regex : POSIX vs Rust

La différence de performance entre grep et ripgrep ne vient pas que du parallélisme. Le moteur regex lui-même est fondamentalement différent.

GNU grep — PCRE avec backtracking

GNU grep utilise un moteur hybride : il tente d'abord un algorithme DFA (déterministe) pour les patterns simples, et bascule vers un NFA avec backtracking pour les expressions complexes (lookaheads, backreferences). Le problème : le backtracking peut être exponentiel sur certains patterns pathologiques (ReDoS).

ripgrep — moteur Rust regex

Le crate regex de Rust utilise un moteur DFA/SIMD très optimisé. Il compile le pattern en un automate déterministe quand c'est possible, et utilise des instructions SIMD (AVX2/SSE4.2) pour accélérer la recherche littérale. Conséquence : temps de recherche O(n) garanti, pas de backtracking catastrophique.

# Pattern pathologique (ReDoS) — arrêt après 10s pour grep
$ timeout 10 grep -rE '(a+)+$' /tmp/test-reDos/ 2>/dev/null
# Bloqué, timeout atteint

$ rg '(a+)+$' /tmp/test-reDos/
# Résultat instantané — pas de backtracking

⚠️ Attention — Limitation du moteur Rust

Le moteur regex de Rust ne supporte pas les backreferences (\1) ni les lookarounds. Pour ces cas, ripgrep propose le flag --pcre2 (si la lib pcre2 est disponible à la compilation) qui bascule vers le moteur PCRE2 — au prix d'une perte de performance.

Cas d'usage avancés

Respect du .gitignore

ripgrep ignore automatiquement les fichiers listés dans .gitignore, .ignore, .rgignore et les règles globales de git. grep, lui, cherche partout — y compris dans node_modules/, vendor/, .git/ et les fichiers build.

# grep cherche PARTOUT (y compris node_modules, .git...)
$ grep -r "import React" mon-projet/
# Résultats noyés dans le bruit

# rg respecte .gitignore — résultats propres
$ rg "import React" mon-projet/
# Seuls les fichiers sources pertinents

# Forcer rg à ignorer le .gitignore
$ rg --no-ignore "import React" mon-projet/

Filtrage par type de fichier

# Chercher uniquement dans les fichiers Python
$ rg "def process" -t py

# Chercher partout sauf dans les fichiers JSON
$ rg "config" -g '!*.json'

# grep équivalent
$ grep -rn --include='*.py' "def process" .
$ grep -rn --exclude='*.json' "config" .

Contexte et multiline

# 3 lignes avant et après le match
$ rg -C3 "error" -t log /var/log/

# Multiline : chercher un pattern sur plusieurs lignes
$ rg -U "class\n\s+def" -t py .
# grep équivalent : grep -Pz "class\n\s+def"

Format de sortie JSON

# Sortie JSON pour scripting
$ rg --json "TODO" src/ | head -20
{"type":"begin","data":{"path":{"text":"src/main.rs"}}}
{"type":"match","data":{"path":{"text":"src/main.rs"},"lines":{"text":"// TODO: refactor this\n"},"line_number":42,"absolute_offset":1234,"submatches":[{"match":{"text":"TODO"},"start":3,"end":7}]}}
{"type":"end","data":{"path":{"text":"src/main.rs"},"binary_offset":null,"stats":{"elapsed":{"secs":0,"nanos":234567},"searches":1,"searches_with_match":1,"bytes_searched":45321,"bytes_printed":128,"matched_lines":1,"matches":1}}}

Quand utiliser grep

🖥️ Scripts universels

grep est garanti sur tout système POSIX. Pour les scripts de monitoring, les crons, les Dockerfiles minimalistes (Alpine, BusyBox) : pas de dépendance supplémentaire.

🔧 Pipelines système

journalctl | grep error, dmesg | grep oom, ps aux | grep nginx. Pour le filtrage de flux en temps réel, grep reste le plus simple.

🐳 Conteneurs légers

Dans un Dockerfile Alpine de 5 Mo, grep est présent. ripgrep pèse ~5 Mo de plus — pas négligeable pour les images de production.

📄 PCRE avancé

Backreferences, lookaheads, lookbehinds : grep -P (PCRE) supporte tout. ripgrep nécessite --pcre2 compilé.

Quand utiliser ripgrep

⚡ Dev au quotidien

Chercher dans un gros monorepo, un projet node_modules, un kernel : ripgrep est 10-40× plus rapide. Gain de temps mesurable chaque jour.

🔍 Code review & audit

Trouver toutes les occurrences d'une fonction, un TODO, une clé hardcodée : le filtrage par type (-t py) et le format JSON simplifient les scripts d'audit.

🗂️ Projets avec .gitignore

Pas besoin d'exclure manuellement node_modules, vendor, build. rg le fait automatiquement. Moins de bruit, résultats plus pertinents.

🤖 Scripting avancé

Sortie JSON (--json), stats détaillées (--stats), remplacement (--replace) : ripgrep offre des capacités de scripting supérieures à grep.

Pattern fallback : grep/rg interchangeable

Pour les scripts destinés à tourner sur des environnements hétérogènes, un pattern simple de fallback est recommandé :

#!/bin/bash
# Fallback pattern : rg si disponible, sinon grep

SEARCHER=""
if command -v rg &>/dev/null; then
    SEARCHER="rg"
else
    SEARCHER="grep -rn"
fi

# Utilisation
$SEARCHER "$1" "${2:-.}"

✅ Checklist — Script portable

✓ Détecter rg avec command -v
✓ Fallback vers grep -rn (le -n matche le comportement par défaut de rg)
✓ Ne pas utiliser les flags spécifiques à rg (-t, -g) dans le fallback
✓ Tester le script dans un conteneur Alpine sans ripgrep
✓ Documenter la dépendance optionnelle dans le README

Pièges courants

⚠️ Piège n°1 — rg ignore les fichiers cachés par défaut

rg "pattern" ne cherche pas dans les fichiers/dossiers commençant par . (dotfiles, .env, .bashrc). Solution : rg --hidden "pattern" ou rg ".+" --hidden.

⚠️ Piège n°2 — Sensibilité à la casse différente

grep est sensible à la casse par défaut. ripgrep est aussi sensible par défaut, mais les alias courants de rg incluent --smart-case. Résultat : un même pattern peut matcher différemment selon l'alias configuré.

⚠️ Piège n°3 — Sortie binaire tronquée

grep affiche Binary file foo matches sans montrer le contenu. rg affiche les lignes matchées même dans les binaires (avec --binary). Ce comportement asymétrique peut surprendre lors de la migration.

⚠️ Piège n°4 — Pas d'équivalent exact pour grep -P

Les lookaheads/lookbehinds de PCRE ne sont pas supportés par le moteur regex par défaut de rg. Il faut rg --pcre2, qui n'est pas toujours compilé. Vérifier avec rg --pcre2-version.

FAQ

▶ ripgrep remplace-t-il complètement grep ?

Non. ripgrep est un outil de recherche de code optimisé. grep reste indispensable pour les pipelines système, les conteneurs minimalistes et les environnements où il est le seul outil disponible. Les deux ont leur place dans la boîte à outils d'un sysadmin.

▶ Comment installer ripgrep ?

Debian/Ubuntu : sudo apt install ripgrep. RHEL/Fedora : sudo dnf install ripgrep. macOS : brew install ripgrep. Ou via Cargo : cargo install ripgrep. Voir le repo GitHub pour les autres plateformes.

▶ ripgrep est-il sûr pour la production ?

Oui, ripgrep est stable (v14+), audité, et utilisé dans VS Code, Sublime Text et de nombreux IDE. Mais pour les scripts de production qui doivent tourner partout sans dépendance, grep reste le choix le plus sûr.

▶ Peut-on utiliser ripgrep dans des scripts CI/CD ?

Oui, si l'image Docker inclut ripgrep. La sortie JSON (--json) est particulièrement pratique pour le parsing automatisé. Sinon, utiliser le pattern fallback décrit plus haut.

▶ rg est plus rapide, mais grep avec -P est plus puissant ?

C'est correct en partie. grep -P (PCRE) supporte les backreferences et lookarounds que le moteur par défaut de rg ne gère pas. Mais rg peut utiliser PCRE2 via --pcre2 si compilé avec. Vérifier : rg --pcre2-version.

▶ Comment désactiver le respect du .gitignore dans rg ?

rg --no-ignore "pattern" cherche partout, comme grep. Ou rg -u "pattern" (raccourci pour --no-ignore --hidden).

▶ Existe-t-il un équivalent ripgrep pour macOS/BSD ?

ripgrep est multi-plateforme et fonctionne nativement sur macOS et Windows. Sur macOS, brew install ripgrep. Le grep BSD natif de macOS est moins performant que GNU grep — ripgrep est un upgrade encore plus significatif dans ce cas.

▶ Quelles sont les alternatives à ripgrep ?

ag (the_silver_searcher), ack (orienté Perl), fd (pour la recherche de fichiers), fzf (recherche fuzzy interactive). ripgrep reste le plus rapide et le plus complet pour la recherche de texte dans du code.

Conclusion

Le comparatif grep vs ripgrep n'est pas un match à somme nulle. Les deux outils excellent dans leur domaine :

Le bon choix dépend du contexte. En production et dans les scripts portables : grep. Sur ta workstation, dans ton IDE, sur un monorepo : ripgrep. Et pour les scripts partagés, le pattern fallback te donne le meilleur des deux mondes.

Besoin d'optimiser ton infrastructure Linux ou d'automatiser tes opérations ?

Linux-Man accompagne les TPE et PME en hébergement, infogérance et conseil DevOps.

Contactez-nous →


Sources : man grep · GNU grep manual · ripgrep GitHub · ripgrep User Guide

Quitter la version mobile