Zeigen Sie den Änderungsverlauf einer Datei mithilfe der Git-Versionierung an


3090

Wie kann ich den Änderungsverlauf einer einzelnen Datei in Git anzeigen und die Details mit den Änderungen vervollständigen?

Ich bin so weit gekommen:

git log -- [filename]

Das zeigt mir den Commit-Verlauf der Datei, aber wie komme ich zum Inhalt jeder Dateiänderung?

Ich versuche den Übergang von MS SourceSafe zu machen und das war früher ein einfaches right-clickshow history.


41
Der obige Link ist nicht mehr gültig. Dieser Link funktioniert heute: Git Community Book
Chris

1
Der obige Link (gepostet von Chris) ist nicht mehr gültig. Dieser Link funktioniert heute: git-scm.com/book/en/v2
Cog

Antworten:


2370

Dafür würde ich verwenden:

gitk [filename]

oder um Dateinamen nach Umbenennungen zu folgen

gitk --follow [filename]

28
Aber ich habe lieber sogar ein Tool, das das oben Genannte mit "Git-Schuld" kombiniert, mit dem ich die Quelle einer Datei durchsuchen kann, wenn sie sich im Laufe der Zeit ändert ...
Egon Willighagen

26
Leider folgt dies nicht dem Verlauf der Datei nach dem Umbenennen.
Dan Moulding

146
Ich habe auch nach dem Verlauf von Dateien gesucht, die zuvor umbenannt wurden, und diesen Thread zuerst gefunden. Die Lösung besteht darin, "git log --follow <Dateiname>" zu verwenden, wie Phil hier hervorhob .
Florian Gutmann

115
Der Autor suchte nach einem Kommandozeilen-Tool. Während gitk mit GIT geliefert wird, ist es weder eine Befehlszeilen-App noch eine besonders gute GUI.
Mikemaccana

72
War er auf der Suche nach einem Kommandozeilen-Tool? "Rechtsklick -> Verlauf anzeigen" impliziert dies sicherlich nicht.
HDGARROOD

2235

Sie können verwenden

git log -p filename

damit git die Patches für jeden Protokolleintrag generiert.

Sehen

git help log

für mehr Optionen - es kann tatsächlich eine Menge netter Dinge tun :) Um nur den Unterschied für ein bestimmtes Commit zu bekommen, können Sie

git show HEAD 

oder jede andere Überarbeitung nach Kennung. Oder verwenden

gitk

um die Änderungen visuell zu durchsuchen.


8
git show HEAD zeigt alle Dateien an. Wissen Sie, wie man eine einzelne Datei verfolgt (wie Richard es verlangt hat)?
Jonas Byström

5
Sie verwenden: git show <Revision> - Dateiname, der die Unterschiede für diese Revision anzeigt, falls eine vorhanden ist.
Marcos Oliveira

4
--stat ist auch hilfreich. Sie können es zusammen mit -p verwenden.
Raffi Khatchadourian

5
Das ist toll. gitk verhält sich nicht gut, wenn Pfade angegeben werden, die nicht mehr existieren. Ich habe git log -p - path verwendet.
Paulo Casaretto

6
Außerdem sieht Gitk so aus, als wäre es vom Boogie-Monster gebaut worden. Dies ist eine großartige Antwort und am besten auf die ursprüngliche Frage zugeschnitten.
Ghayes

1497

git log --follow -p -- path-to-file

Dies zeigt den gesamten Verlauf der Datei an (einschließlich des Verlaufs über das Umbenennen hinaus und mit Unterschieden für jede Änderung).

Mit anderen Worten, wenn die benannte Datei bareinmal benannt wurde foo, wird git log -p bar(ohne die --followOption) nur der Verlauf der Datei bis zu dem Punkt angezeigt, an dem sie umbenannt wurde. Der Verlauf der Datei wird dann nicht angezeigt, wenn sie als bekannt war foo. Mit git log --follow -p barwird der gesamte Verlauf der Datei angezeigt, einschließlich aller Änderungen an der Datei, als diese bekannt war foo. Die -pOption stellt sicher, dass bei jeder Änderung Unterschiede enthalten sind.


18
--stat ist auch hilfreich. Sie können es zusammen mit -p verwenden.
Raffi Khatchadourian

23
Ich bin damit einverstanden, dass dies die WIRKLICHE Antwort ist. (1.) --followstellt sicher, dass Sie die Umbenennung von Dateien sehen. (2.) -pstellt sicher, dass Sie sehen, wie die Datei geändert wird. (3.) Es handelt sich nur um eine Befehlszeile.
Trevor Boyd Smith

3
@NHDaly Ich bemerke, dass das --hinzugefügt wurde, aber ich weiß nicht, warum dies das Beste macht? Was macht es?
Benjohn

40
@Benjohn Die --Option teilt Git mit, dass das Ende der Optionen erreicht ist und dass alles, was folgt --, als Argument behandelt werden sollte. Für git logdas macht nur einen Unterschied , wenn Sie einen Pfadnamen haben, der mit einem beginnt Strich . Angenommen, Sie wollten den Verlauf einer Datei mit dem unglücklichen Namen "--follow" kennen:git log --follow -p -- --follow
Dan Moulding

10
@Benjohn: Normalerweise ist das --nützlich, weil es auch vor revisionNamen schützen kann , die mit dem von Ihnen eingegebenen Dateinamen übereinstimmen, was tatsächlich beängstigend sein kann. Beispiel: Wenn Sie sowohl einen Zweig als auch eine Datei mit dem Namen hätten foo, git log -p foowürde der Git-Protokollverlauf bis zu angezeigt foo, nicht der Verlauf für die Datei foo . Aber @DanMoulding ist richtig, da der --followBefehl nur einen einzigen Dateinamen als Argument verwendet, ist dies weniger notwendig, da es kein sein kann revision. Das habe ich gerade gelernt. Vielleicht hatten Sie Recht, es dann aus Ihrer Antwort herauszulassen; Ich bin mir nicht sicher.
NHDaly

172

Wenn Sie lieber textbasiert bleiben möchten, können Sie tig verwenden .

Schnellinstallation:

  • apt-get :# apt-get install tig
  • Homebrew (OS X) :$ brew install tig

Verwenden Sie diese Option, um den Verlauf einer einzelnen Datei anzuzeigen: tig [filename]
Oder durchsuchen Sie den detaillierten Repo-Verlauf:tig

Ähnlich, gitkaber textbasiert. Unterstützt Farben im Terminal!


23
Ausgezeichnetes textbasiertes Tool, gute Antwort. Ich bin ausgeflippt, als ich die Abhängigkeiten für die Installation von gitk auf meinem kopflosen Server sah. Würde wieder A +++
Tom McKenzie

Sie können auch bestimmte Dateien mit WIG betrachten, dhtig -- path/to/specific/file
Gloriphobie

110

git whatchanged -p filenameist auch git log -p filenamein diesem Fall gleichwertig .

Sie können auch sehen, wann eine bestimmte Codezeile in einer Datei mit geändert wurde git blame filename. Dadurch werden für jede Zeile in der Datei eine kurze Festschreibungs-ID, der Autor, der Zeitstempel und die vollständige Codezeile ausgedruckt. Dies ist sehr nützlich, nachdem Sie einen Fehler gefunden haben und wissen möchten, wann er eingeführt wurde (oder wer schuld daran war).


4
+1, filenameist aber im Befehl nicht optional git blame filename.
RockXrock

7
"Neue Benutzer werden aufgefordert, stattdessen git-log zu verwenden. (...) Der Befehl wird hauptsächlich aus historischen Gründen beibehalten."
Ciastek

105

SourceTree-Benutzer

Wenn Sie SourceTree verwenden, um Ihr Repository zu visualisieren (es ist kostenlos und recht gut), können Sie mit der rechten Maustaste auf eine Datei klicken und Ausgewähltes Protokoll auswählen

Geben Sie hier die Bildbeschreibung ein

Die Anzeige (unten) ist viel freundlicher als gitk und die meisten anderen aufgeführten Optionen. Leider gibt es (zu diesem Zeitpunkt) keine einfache Möglichkeit, diese Ansicht über die Befehlszeile zu starten. Die CLI von SourceTree öffnet derzeit nur Repos.

Geben Sie hier die Bildbeschreibung ein


1
Besonders gut gefällt mir die Option "Umbenannte Dateien folgen", mit der Sie sehen können, ob eine Datei umbenannt oder verschoben wurde.
Chris

aber wenn ich mich nicht irre (bitte lassen Sie es mich wissen!), kann man in der GUI nur zwei Versionen gleichzeitig vergleichen? Gibt es Clients mit einer eleganten Oberfläche, um mehrere verschiedene Versionen gleichzeitig zu unterscheiden? Möglicherweise mit einer Verkleinerungsansicht wie in Sublime Text? Das wäre wirklich nützlich, denke ich.
Sam Lewallen

@SamLewallen Wenn ich das richtig verstehe, möchten Sie drei verschiedene Commits vergleichen? Dies klingt ähnlich wie eine Drei-Wege-Zusammenführung (meine, Ihre, Basis). Normalerweise wird diese Strategie zur Lösung von Zusammenführungskonflikten verwendet, bei der nicht unbedingt drei beliebige Commits verglichen werden. Es gibt viele Tools, die Drei-Wege-Zusammenführungen unterstützen. Stackoverflow.com/questions/10998728/… aber der Trick besteht darin, diesen Tools die spezifischen Revisionen zuzuführen. Gitready.com/intermediate/2009/02/27/…
Mark Fox

Danke Mark Fox, das meine ich. Kennen Sie zufällig Anwendungen, die dies tun?
Sam Lewallen

1
@ MarnenLaibow-Koser Ich kann mich nicht erinnern, warum ich damals die SHA brauche. Ahaha.
AechoLiu

63

So zeigen Sie an, welche Revision und welcher Autor die einzelnen Zeilen einer Datei zuletzt geändert haben:

git blame filename

oder wenn Sie die leistungsstarke GUI für Schuldzuweisungen verwenden möchten:

git gui blame filename

49

Zusammenfassung anderer Antworten, nachdem Sie sie gelesen und ein wenig gespielt haben:

Der übliche Befehlszeilenbefehl wäre

git log --follow --all -p dir/file.c

Sie können aber auch entweder gitk (gui) oder tig (text-ui) verwenden, um eine viel besser lesbare Sichtweise zu ermöglichen.

gitk --follow --all -p dir/file.c

tig --follow --all -p dir/file.c

Unter debian / ubuntu lautet der Installationsbefehl für diese schönen Tools wie erwartet:

sudo apt-get install gitk tig

Und ich benutze derzeit:

alias gdf='gitk --follow --all -p'

so dass ich nur tippen kann gdf dir, um eine fokussierte Geschichte von allem im Unterverzeichnis zu erhalten dir.


2
Ich denke, das ist eine großartige Antwort. Vielleicht werden Sie auch nicht gewählt, weil Sie auf andere Weise (IMHO besser) antworten, um die Änderungen zu sehen, z. B. über gitk und tig zusätzlich zu git.
PopcornKing

Nur um zu antworten. Suchen Sie den Pfad (im Git-Bereich, bis zu dem noch im Repository vorhanden ist). Verwenden Sie dann den oben angegebenen Befehl "git log --follow --all -p <Ordnerpfad / Dateipfad>". Es kann vorkommen, dass die Datei / der Ordner über den Verlauf entfernt wurde. Suchen Sie daher den maximal noch vorhandenen Pfad und versuchen Sie, den Verlauf abzurufen. funktioniert!
Parasrish

2
--allist für alle Zweige, der Rest wird in @ Dans Antwort erklärt
Cregox

1
Oh man, nachdem ich so lange nach einer guten Lösung gesucht hatte, um Dateien jenseits von Umbenennungen zu verfolgen, fand ich sie schließlich hier. Funktioniert wie Charme! Vielen Dank!
xZero

25

Fügen Sie diesen Alias ​​zu Ihrer .gitconfig hinzu:

[alias]
    lg = log --all --graph --pretty=format:'%Cred%h%Creset -%C(yellow)%d%Creset %s %Cgreen(%cr) %C(bold blue)<%an>%Creset'\n--abbrev-commit --date=relative

Und verwenden Sie den Befehl wie folgt:

> git lg
> git lg -- filename

Die Ausgabe sieht fast genauso aus wie die Gitk-Ausgabe. Genießen.


Nachdem ich diese LG-Verknüpfung ausgeführt hatte, sagte ich (und ich zitiere) "Schön!". Beachten Sie jedoch, dass das "\ n" nach "--graph" ein Fehler ist.
Jmbeck

3
Kann auch verwendet werden git lg -p filename- es gibt einen schönen Unterschied der gesuchten Datei zurück.
Egel

22

In letzter Zeit habe ich es entdeckt tigund fand es sehr nützlich. Es gibt einige Fälle, in denen ich mir A oder B wünschte, aber die meiste Zeit ist es ziemlich ordentlich.

Für Ihren Fall tig <filename>könnte es das sein, wonach Sie suchen.

http://jonas.nitro.dk/tig/


auf centos yum install tig
zzapper

18

Sie können vscode mit GitLens verwenden , es ist ein sehr leistungsfähiges Tool. Gehen Sie nach der Installation von GitLens zur Registerkarte GitLens, wählen FILE HISTORYSie und Sie können sie durchsuchen.

Geben Sie hier die Bildbeschreibung ein


15

Ich habe Git-Playback genau für diesen Zweck geschrieben

pip install git-playback
git playback [filename]

Dies hat den Vorteil, dass sowohl die Ergebnisse in der Befehlszeile angezeigt werden (wie git log -p), als dass Sie jedes Commit mit den Pfeiltasten (wie gitk) durchlaufen können .



10

Sie können dies auch versuchen, indem die Commits aufgelistet werden, die einen bestimmten Teil einer Datei geändert haben (implementiert in Git 1.8.4).

Das zurückgegebene Ergebnis wäre die Liste der Commits, die diesen bestimmten Teil geändert haben. Befehl :

git log --pretty=short -u -L <upperLimit>,<lowerLimit>:<path_to_filename>

Dabei ist UpperLimit die Startnummer und LowerLimit die Endnummer der Datei.

Weitere Informationen finden Sie unter https://www.techpurohit.com/list-some-useful-git-commands


9

Wenn Sie die ganze Geschichte einer Datei sehen wollen, einschließlich auf allen anderen Zweigen verwenden:

gitk --all <filename>

7

Mit den hervorragenden Git-Erweiterungen gelangen Sie zu einem Punkt im Verlauf, an dem die Datei noch vorhanden war (wenn sie gelöscht wurde, andernfalls gehen Sie einfach zu HEAD), wechseln Sie zur File treeRegisterkarte, klicken Sie mit der rechten Maustaste auf die Datei und wählen Sie File history.

Standardmäßig folgt die Datei den Umbenennungen, und auf der BlameRegisterkarte wird der Name bei einer bestimmten Revision angezeigt .

Es hat einige kleinere Fallstricke, wie das Anzeigen fatal: Not a valid object nameauf der ViewRegisterkarte, wenn Sie auf die Löschrevision klicken, aber damit kann ich leben. :-)


Es ist erwähnenswert, dass dies nur Windows ist.
Evan Hahn

3
@EvanHahn nicht genau, über Mono kann man GitExtension auch unter Linux verwenden, wir verwenden es auf Ubuntu und sind ziemlich zufrieden damit. siehe git-extensions-documentation.readthedocs.org/en/latest/…
Shmil The Cat

7

Wenn Sie die Git-GUI (unter Windows) im Repository-Menü verwenden, können Sie "Master-Verlauf visualisieren" verwenden. Markieren Sie ein Commit im oberen Bereich und eine Datei unten rechts, und Sie sehen den Unterschied für dieses Commit unten links.


Wie beantwortet dies die Frage?
Jmbeck

3
Nun, OP hat keine Befehlszeile angegeben, und als wir von SourceSafe (einer GUI) weggingen, schien es relevant, darauf hinzuweisen, dass Sie so ziemlich das Gleiche tun können, was Sie in VSS in der Git-GUI unter Windows tun können.
Cori

6

SmartGit :

  1. Aktivieren Sie im Menü die Anzeige unveränderter Dateien: Unveränderte Dateien anzeigen / anzeigen
  2. Klicken Sie mit der rechten Maustaste auf die Datei und wählen Sie "Protokoll" oder drücken Sie "Strg-L".

4

Die Antwort, nach der ich gesucht habe und die nicht in diesem Thread enthalten ist, besteht darin, Änderungen in Dateien zu sehen, die ich für das Festschreiben bereitgestellt habe. dh

git diff --cached

1
Wenn Sie lokale (nicht bereitgestellte) Änderungen einbeziehen möchten, zeige ich häufig git diff origin/masterdie vollständigen Unterschiede zwischen Ihrem lokalen Zweig und dem Hauptzweig (der von Remote-Via aktualisiert werden kann git fetch)
Ghayes

4

Wenn Sie TortoiseGit verwenden, sollten Sie in der Lage sein, mit der rechten Maustaste auf die Datei zu klicken und dies zu tun TortoiseGit --> Show Log. Stellen Sie im folgenden Fenster Folgendes sicher:

  • Die Show Whole ProjectOption ' ' ist nicht aktiviert.

  • Die All BranchesOption ' ' ist aktiviert.


TortoiseGit (und auch Eclipse Git) verpasst irgendwie Revisionen der ausgewählten Datei, rechnen Sie nicht damit!
Noam Manos

@NoamManos, ich habe dieses Problem nicht festgestellt, daher kann ich nicht überprüfen, ob Ihre Aussage korrekt ist.
user3885927

Mein Fehler, es passiert nur in Eclipse, aber in TortoiseGit können Sie alle Revisionen einer Datei sehen, wenn Sie "Alle Projekte anzeigen" deaktivieren und "Alle Zweige" aktivieren (falls die Datei in einem anderen Zweig festgeschrieben wurde, bevor sie mit main zusammengeführt wurde Ast). Ich werde Ihre Antwort aktualisieren.
Noam Manos

3

git diff -U <filename> Geben Sie einen einheitlichen Unterschied.

Es sollte rot und grün gefärbt sein. Wenn nicht, führen Sie Folgendes aus: git config color.ui autozuerst.


2

Wenn Sie Eclipse mit dem Git-Plugin verwenden, bietet es eine hervorragende Vergleichsansicht mit dem Verlauf. Klicken Sie mit der rechten Maustaste auf die Datei und wählen Sie "Vergleichen mit" => "Verlauf".


Dadurch können Sie jedoch keine gelöschte Datei finden.
avgvstvs

Das Vergleichen von zwei Versionen einer Datei unterscheidet sich vom Anzeigen des Änderungsverlaufs einer Datei
Golimar

0

Ich bin wahrscheinlich in der Nähe des OP, als dies begann, und suche nach etwas Einfachem, mit dem ich git difftool mit vimdiff verwenden kann , um Änderungen an Dateien in meinem Repo ab einem bestimmten Commit zu überprüfen. Ich war nicht sehr glücklich mit Antworten , die ich finden war, so dass ich diese warf git inc remental rep Orter (gitincrep) Skript zusammen und es war nützlich für mich:

#!/usr/bin/env bash

STARTWITH="${1:-}"
shift 1

DFILES=( "$@" )

RunDiff()
{
        GIT1=$1
        GIT2=$2
        shift 2

        if [ "$(git diff $GIT1 $GIT2 "$@")" ]
        then
                git log ${GIT1}..${GIT2}
                git difftool --tool=vimdiff $GIT1 $GIT2 "$@"
        fi
}

OLDVERS=""
RUNDIFF=""

for NEWVERS in $(git log --format=format:%h  --reverse)
do
        if [ "$RUNDIFF" ]
        then
                RunDiff $OLDVERS $NEWVERS "${DFILES[@]}"
        elif [ "$OLDVERS" ]
        then
                if [ "$NEWVERS" = "${STARTWITH:=${NEWVERS}}" ]
                then
                        RUNDIFF=true
                        RunDiff $OLDVERS $NEWVERS "${DFILES[@]}"
                fi
        fi
        OLDVERS=$NEWVERS
done

Ohne Argumente aufgerufen, beginnt dies am Anfang des Repo-Verlaufs, andernfalls beginnt es mit dem von Ihnen angegebenen abgekürzten Commit-Hash und fährt mit der Gegenwart fort - Sie können jederzeit Strg-C drücken, um den Vorgang zu beenden. Alle Argumente nach dem ersten beschränken die Differenzberichte so, dass sie nur die Dateien enthalten, die unter diesen Argumenten aufgeführt sind (was meiner Meinung nach das OP wollte und ich würde es für alle außer winzigen Projekten empfehlen). Wenn Sie Änderungen an bestimmten Dateien überprüfen und von vorne beginnen möchten, müssen Sie eine leere Zeichenfolge für arg1 angeben. Wenn Sie kein vim-Benutzer sind, können Sie vimdiff durch Ihr bevorzugtes Diff-Tool ersetzen .

Das Verhalten besteht darin, die Commit-Kommentare auszugeben, wenn relevante Änderungen gefunden werden, und vimdiff- Läufe für jede geänderte Datei anzubieten (das ist git difftool- Verhalten, aber es funktioniert hier).

Dieser Ansatz ist wahrscheinlich ziemlich naiv, aber bei der Durchsicht vieler Lösungen hier und in einem verwandten Beitrag mussten viele neue Tools auf einem System installiert werden, auf das ich keinen Administratorzugriff habe, mit Schnittstellen, die ihre eigene Lernkurve hatten. Das obige Skript hat getan, was ich wollte, ohne mich damit zu befassen. Ich werde hier auf die vielen hervorragenden Vorschläge eingehen, wenn ich etwas Anspruchsvolleres brauche - aber ich denke, dies reagiert direkt auf das OP.


0

Ich habe eine sehr einfache Lösung gefunden, um den Verlauf der Datei schnell zu finden.

  1. Nehmen Sie eine zufällige Änderung in der Datei vor
  2. Es werden als nicht festgeschriebene Änderungen in Ihrem Quellenbaum angezeigt
  3. Klicken Sie mit der rechten Maustaste auf die Datei und wählen Sie "Protokoll ausgewählt".

Geben Sie hier die Bildbeschreibung ein

Es würde die Geschichte aller Commits zeigen.


Woher kommt diese GUI?
Colidyre

Sourcetree UI. Danke
savvyBrar
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.