Grundsätzlich versuche ich einen Alias:
git files 9fa3
... um den Befehl auszuführen:
git diff --name-status 9fa3^ 9fa3
aber git scheint keine Positionsparameter an den Alias-Befehl zu übergeben. Ich habe versucht:
[alias]
files = "!git diff --name-status $1^ $1"
files = "!git diff --name-status {1}^ {1}"
... und ein paar andere, aber die haben nicht funktioniert.
Der entartete Fall wäre:
$ git echo_reverse_these_params a b c d e
e d c b a
... wie kann ich das zum Laufen bringen?
$1
sollte funktionieren).Antworten:
Der naheliegendste Weg ist die Verwendung einer Shell-Funktion:
Ein Alias ohne
!
wird als Git-Befehl behandelt. zBcommit-all = commit -a
.Mit dem
!
wird es als eigener Befehl in der Shell ausgeführt, sodass Sie so stärkere Magie einsetzen können.UPD
Da Befehle im Stammverzeichnis des Repositorys ausgeführt werden, können Sie
${GIT_PREFIX}
Variablen verwenden, wenn Sie auf die Dateinamen in Befehlen verweisenquelle
!
wird als Git-Befehl behandelt. zBcommit-all = commit -a
. Mit dem!
wird es als eigener Befehl in der Shell ausgeführt, sodass Sie so stärkere Magie einsetzen können.!
wird im Stammverzeichnis des Repositorys ausgeführt. Wenn Sie also beim Aufrufen Ihres Alias relative Pfade verwenden, erhalten Sie nicht die erwarteten Ergebnisse.Sie können auch
sh
direkt referenzieren (anstatt eine Funktion zu erstellen):(Beachten Sie den Bindestrich am Ende der Zeile - das brauchen Sie.)
quelle
sh
, da dies an sich eine Shell ist und auf den meisten Systemen verfügbar ist. Die Verwendung der Standard-Shell funktioniert nur, wenn der Befehl für alle Shells wie geschrieben funktioniert.--
,-
da es vertrauter ist und weniger wahrscheinlich ist, dass es irgendwann versehentlich stdin bedeutet. ("Ein Argument von - ist gleichbedeutend mit -" in Bash (1) ist unauslöschlich)sh -c
) ist ebenfalls nicht erforderlich. Siehe meine Antwort für eine Alternative.Der gesuchte Alias lautet:
Mit Argumentvalidierung:
Das Finale
#
ist wichtig - es verhindert, dass alle vom Benutzer angegebenen Argumente von der Shell verarbeitet werden (es kommentiert sie aus).Hinweis:
git
Platziert alle vom Benutzer angegebenen Argumente am Ende der Befehlszeile. Um dies in Aktion zu sehen, versuchen Sie:GIT_TRACE=2 git files a b c d
Die maskierten Anführungszeichen (aufgrund von Verschachtelungen) sind wichtig für Dateinamen, die Leerzeichen enthalten, oder
"; rm -rf --no-preserve-root /;
)quelle
!
impliziertsh -c
dies bereits (wird beim Voranstellen angezeigtGIT_TRACE=2
), sodass keine weitere Unter-Shell ausgeführt werden muss. Welche Probleme sehen Sie in komplizierteren Fällen?fp = "! 1=${1:-$(git headBranch)}; 2=${2:-up}; git fetch -fu $2 pull/$1/head:$1; git checkout $1; git branch -u $2 #"
. Dies funktioniert ohne die ersten beiden Anweisungen hervorragend, fällt jedoch herunter, wenn Sie sie verwenden. (Ich habeheadBranch = symbolic-ref --short HEAD
auch).fp = "! a=${1:-$(git headBranch)}; b=${2:-up}; git fetch -fu $b pull/$a/head:$a; git checkout $a; git branch -u $b #"
."
Anführungszeichen erforderlich?Verwenden Sie GIT_TRACE = 1, das auf der Git-Manpage beschrieben ist, um die Alias-Verarbeitung transparent zu machen:
Ihre ursprünglichen Befehle funktionieren mit der Git-Version 1.8.3.4 (Eimantas hat festgestellt, dass sich dies in 1.8.2.1 geändert hat).
Die Optionen
sh -c '..' --
undf() {..}; f
behandeln die "$ @" -Parameter auf unterschiedliche Weise sauber (siehe mit GIT_TRACE). Das Anhängen von "#" an einen Alias würde auch Positionsparameter zulassen, ohne die nachfolgenden zu belassen.quelle
files = "!git diff --name-status $1^ $1 #"
files = "!git diff --name-status $1^"
Wie von Drealmer oben angegeben :
GIT_PREFIX
Wenn Sie von git auf das Unterverzeichnis gesetzt werden, in dem Sie sich befinden, können Sie dies umgehen, indem Sie zuerst das Verzeichnis ändern:quelle
cd ${GIT_PREFIX:-.} &&.
" (Quelle: stackoverflow.com/a/21929373/266309 )!cd "${GIT_PREFIX:-.}" && ls -al
Ich wollte dies mit einem Alias tun, der dies tut:
Am Ende habe ich ein Shell-Skript namens git-m erstellt , das diesen Inhalt hat:
Dies hat den Vorteil, dass es viel besser lesbar ist, da es sich um mehrere Zeilen handelt. Außerdem mag ich es, mit
-x
und bash anrufen zu könnenset -e
. Sie können das Ganze wahrscheinlich als Alias machen, aber es wäre super hässlich und schwer zu pflegen.Da die Datei benannt ist
git-m
, können Sie sie folgendermaßen ausführen:git m foo bar
quelle
'!f() { : git branch ; ... }; f'
Der Alias wird automatisch als Zweig vervollständigt, was sehr praktisch ist..bashrc
Datei ist, die ich als Quelle habe. Aber ich glaube nicht, dass ich die Art und Weise, wie ich Argumente für ein Skript automatisch vervollständige, so sehr ändere wie das Skript selbst, und das nur während der Entwicklung.Ich bin gerade auf etwas Ähnliches gestoßen; Ich hoffe, es ist OK, meine Notizen zu posten. Eine Sache, die mich über
git
Aliase mit Argumenten verwirrt , kommt wahrscheinlich vongit help config
(ich habe Git-Version 1.7.9.5):So wie ich es sehe - wenn ein Alias "als Shell-Befehl behandelt wird", wenn ein Ausrufezeichen vorangestellt wird - warum sollte ich eine Funktion oder
sh -c
Argumente verwenden müssen? Warum schreibst du meinen Befehl nicht einfach so wie er ist?Ich weiß die Antwort immer noch nicht - aber ich denke tatsächlich, dass es einen kleinen Unterschied im Ergebnis gibt. Hier ist ein kleiner Test - werfen Sie diesen in Ihren
.git/config
oder Ihren~/.gitconfig
:Folgendes bekomme ich, um diese Aliase auszuführen:
... oder: Wenn Sie einen "einfachen" Befehl nach dem
!
"wie besehen " in einemgit
Aliasgit
verwenden, wird die Argumentliste automatisch an diesen Befehl angehängt! Eine Möglichkeit, dies zu vermeiden, besteht darin, Ihr Skript entweder als Funktion oder als Argument für aufzurufensh -c
.Eine andere interessante Sache hier (für mich) ist, dass man in einem Shell-Skript normalerweise erwartet, dass die automatische Variable
$0
der Dateiname des Skripts ist. Bei einergit
Alias-Funktion ist das$0
Argument im Grunde genommen der Inhalt der gesamten Zeichenfolge, die diesen Befehl angibt (wie in der Konfigurationsdatei eingegeben).Aus diesem Grund, denke ich, wenn Sie zufällig falsch zitieren - im folgenden Fall würde dies den äußeren doppelten Anführungszeichen entgehen:
... - dann
git
würde mit (zumindest für mich) etwas kryptischer Nachricht scheitern:Ich denke, da
git
eine ganze Zeichenfolge nur als ein Argument "gesehen" wurde!
, wurde versucht, sie als ausführbare Datei auszuführen. und dementsprechend konnte es nicht"echo 'A' 'B'"
als Datei gefunden werden.In jedem Fall
git help config
würde ich im Zusammenhang mit dem obigen Zitat spekulieren, dass es genauer ist, Folgendes anzugeben : " ... der Aufruf" git new "entspricht dem Ausführen des Shell-Befehls" gitk --all --not ORIG_HEAD " $ @ ", wobei $ @ die Argumente sind, die zur Laufzeit von der Befehlszeile an den git-Befehlsalias übergeben werden. ... ". Ich denke, das würde auch erklären, warum der "direkte" Ansatz in OP nicht mit Positionsparametern funktioniert.quelle
fail
versucht, einen Befehl namens "echo 'A' 'B" (dh 10 Zeichen lang) auszuführen. Gleicher Fehlersh -c "'echo a b'"
und gleiche Ursache, zu viele Anführungszeichen