¿Es posible ejecutar git grep
dentro de todas las ramas de un proyecto de control de Git? ¿O hay otro comando para ejecutar?
¿Es posible ejecutar git grep
dentro de todas las ramas de un proyecto de control de Git? ¿O hay otro comando para ejecutar?
Respuestas:
La pregunta " ¿Cómo grep (buscar) el código comprometido en el historial de git? " Recomienda:
git grep <regexp> $(git rev-list --all)
Eso busca a través de todos los commits, que deben incluir todas las ramas.
Otra forma sería:
git rev-list --all | (
while read revision; do
git grep -F 'yourWord' $revision
done
)
Puedes encontrar aún más ejemplos en este artículo :
Intenté lo anterior en un proyecto lo suficientemente grande como para que git se quejara del tamaño del argumento, por lo que si se encuentra con este problema, haga algo como:
git rev-list --all | (while read rev; do git grep -e <regexp> $rev; done)
(vea una alternativa en la última sección de esta respuesta, a continuación)
No olvides esas configuraciones, si las quieres:
# Allow Extended Regular Expressions
git config --global grep.extendRegexp true
# Always Include Line Numbers
git config --global grep.lineNumber true
Este alias también puede ayudar:
git config --global alias.g "grep --break --heading --line-number"
Nota: chernjie sugirió que git rev-list --all
es una exageración.
Un comando más refinado puede ser:
git branch -a | tr -d \* | xargs git grep <regexp>
Lo que le permitirá buscar solo sucursales (incluidas las sucursales remotas)
Incluso puede crear un alias bash / zsh para ello:
alias grep_all="git branch -a | tr -d \* | xargs git grep"
grep_all <regexp>
Actualización de agosto de 2016: RM recomienda en los comentarios
Obtuve un "
fatal: bad flag '->' used after filename
" al probar lagit branch
versión. El error se asoció con unaHEAD
notación de alias.Lo resolví agregando un
sed '/->/d'
en la tubería, entre eltr
y losxargs
comandos.
git branch -a | tr -d \* | sed '/->/d' | xargs git grep <regexp>
Es decir:
alias grep_all="git branch -a | tr -d \* | sed '/->/d' | xargs git grep"
grep_all <regexp>
git branch
tr o sed; git branch
es un comando de porcelana destinado al consumo humano. Consulte stackoverflow.com/a/3847586/2562319 para conocer las alternativas preferidas.
git log
puede ser una forma más efectiva de buscar texto en todas las ramas, especialmente si hay muchas coincidencias y desea ver primero los cambios más recientes (relevantes).
git log -p --all -S 'search string'
git log -p --all -G 'match regular expression'
Estos comandos de registro enumeran confirmaciones que agregan o eliminan la cadena de búsqueda / expresión regular dada, (generalmente) más reciente primero. La -p
opción hace que la diferencia relevante se muestre donde se agregó o eliminó el patrón, por lo que puede verlo en contexto.
Después de encontrar una confirmación relevante que agregue el texto que estaba buscando (por ejemplo, 8beeff00d), busque las ramas que contienen la confirmación:
git branch -a --contains 8beeff00d
Encontré esto más útil:
git grep -i foo `git for-each-ref --format='%(refname)' refs/`
Tendría que ajustar los últimos argumentos dependiendo de si desea ver solo las ramas remotas frente a las locales, es decir:
git grep -i foo $(git for-each-ref --format='%(refname)' refs/remotes)
git grep -i foo $(git for-each-ref --format='%(refname)' refs/heads)
El alias que creé se ve así:
grep-refs = !sh -c 'git grep "$0" "$@" "$(git for-each-ref --format=\"%(refname)\"" refs/)'
git for-each-ref
con --sort=-committerdate --count=100
! Gracias por la idea original!
Es posible hacerlo de dos maneras comunes: alias Bash o Git
Aquí hay tres comandos:
git grep-branch
- Buscar en todas las sucursales locales y remotasgit grep-branch-local
- Buscar solo en sucursales localesgit grep-branch-remote
- Solo ramas remotasEl uso es el mismo que git grep
git grep-branch "find my text"
git grep-branch --some-grep-options "find my text"
Los comandos deben agregarse manualmente al ~/.gitconfig
archivo, porque git config --global alias
evalúa el código complejo que agregas y lo desordena.
[alias]
grep-branch = "!f(){ git branch -a | sed -e 's/[ \\*]*//' | grep -v -e '\\->' | xargs git grep $@; };f "
grep-branch-remote = "!f(){ git branch -a | sed -e 's/[ \\*]*//' | grep -v -e '\\->' | grep '^remotes' | xargs git grep $@; };f"
grep-branch-local = "!f(){ git branch -a | sed -e 's/[ \\*]*//' | grep -v -e '\\->' -e '^remotes' | xargs git grep $@; };f "
Nota: Cuando agrega alias y no se ejecutan, compruebe las barras diagonales inversas \
que pueden requerir un escape adicional \\
en comparación con los comandos bash .
git branch -a
- Mostrar todas las ramas;sed -e 's/[ \\*]*//'
- Recortar espacios (desde branch -a
) y * (el nombre de la rama activa lo tiene);grep -v -e '\\->'
- Ignorar nombres complejos como remotes/origin/HEAD -> origin/master
;grep '^remotes'
- Obtenga todas las ramas remotas;grep -v -e '^remotes'
- Obtener ramas excepto ramas remotas;git grep-branch-local -n getTastyCookies
-n
Prefije el número de línea a líneas coincidentes.
[user@pc project]$ git grep-branch-local -n getTastyCookies
dev:53:modules/factory/getters.php:function getTastyCookies($user);
master:50:modules/factory/getters.php:function getTastyCookies($user)
La estructura actual es:
:
- separador
dev
53
modules/factory/getters.php
function getTastyCookies($user)
Como debe saber: los comandos Bash deben almacenarse en .sh
scripts o ejecutarse en un shell.
git branch -a | sed -e 's/[ \*]*//' | grep -v -e '\->' -e '^remotes' | xargs git grep "TEXT"
git branch -a | sed -e 's/[ \*]*//' | grep -v -e '\->' | grep '^remotes' | xargs git grep "TEXT"
git branch -a | sed -e 's/[ \*]*//' | grep -v -e '\->' | xargs git grep "TEXT"
git grep-branch "find my text"
:fatal: ambiguous argument 'client': both revision and filename
-a
, que muestra todas las ramas? Sugeriría usar opciones para el git branch
comando para separar los braches. Al mirar las ramas locales, solo hay una sola *
, por lo que no es necesario escapar por sed. Entonces: solo git branch | sed -e 's/*/ /' | xargs git grep "TEXT"
para sucursales locales, solo git branch -r | grep -v -- "->" | xargs git grep "TEXT"
para sucursales remotas y git branch -a | grep -v -- "->" | xargs git grep "TEXT"
para todas las sucursales
Así es como lo hago:
git for-each-ref --format='%(*refname)' | xargs git grep SEARCHTERM