Kann Git automatisch zwischen Leerzeichen und Tabulatoren wechseln?

196

Ich verwende Tabulatoren zum Einrücken in meinen Python-Programmen, möchte aber (mit Git) mit Personen zusammenarbeiten, die stattdessen Leerzeichen verwenden.

Gibt es eine Möglichkeit für git, beim Drücken / Abrufen automatisch zwischen Leerzeichen und Tabulatoren (z. B. 4 Leerzeichen = 1 Tabulator) zu konvertieren? (ähnlich der CR / LF-Umwandlung)

Olivier Verdier
quelle
33
PEP8 ist genau mein Problem. Jeder folgt ihm und ich stecke mit meinen Tabs fest. Ich denke zufällig, dass eine Einrückung = eine Registerkarte das Richtige ist (warum Leerzeichen? Warum 4 Leerzeichen? PEP8 erklärt das nicht ...). Wie auch immer, mit diesem Git-Trick kann ich gerne Tabs auf meinem Computer verwenden und meinen Code mit allen PEP8-Followern da draußen teilen.
Olivier Verdier
7
Oh! Ich verwende TextMate und kann zwischen Leerzeichen und Tabulatoren konvertieren. Die Sache ist, wenn ich auf Tab drücke, möchte ich, dass mein Editor ... Tab schreibt. Wenn ich also ein Python-Projekt mit Leerzeichen auschecke, füge ich alle Arten von Registerkarten ein. Ich muss manuell in Registerkarten konvertieren, aber wenn ich einchecke, sieht es nach 1000 Löschungen, 1000 Hinzufügungen aus, und meine Mitarbeiter werden nicht glücklich sein. :-)
Olivier Verdier
6
Der Grund, warum PEP8 Leerzeichen anstelle von Tabulatoren angibt, liegt in den Einrückungsregeln für die Fortsetzung. Es gibt zwei Möglichkeiten, eine überlange Zeile in einer Klammer fortzusetzen. Wenn Sie eine neue Zeile unmittelbar nach einer Klammer beginnen, rücken Sie einfach eine ein. Wenn Sie stattdessen einen Teil des Inhalts der Klammer in die erste Zeile setzen, müssen Sie die Klammer in der nächsten Zeile auf der Einrückungsstufe der öffnenden Klammer fortsetzen. Wenn Sie Registerkarten verwenden, funktioniert dies nicht.
John Christopher Jones
2
@JohnChristopherJones für diese Situation könnte man Tabulatoren verwenden, um den Einzug mit der vorherigen Zeile abzugleichen, dann Leerzeichen, um eine Position in der vorherigen Zeile abzugleichen. Dies kann leicht in Räume umgewandelt werden. Leider ist das Gegenteil nicht der Fall, da hier Einrückungsinformationen mit Ausrichtungsinformationen vermischt werden.
Patrick Parker

Antworten:

194

Hier ist die Komplettlösung:

Fügen Sie in Ihrem Repository eine Datei hinzu, .git/info/attributesdie Folgendes enthält:

*.py  filter=tabspace

Linux / Unix

Führen Sie nun die folgenden Befehle aus:

git config --global filter.tabspace.smudge 'unexpand --tabs=4 --first-only'
git config --global filter.tabspace.clean 'expand --tabs=4 --initial'

OS X.

Installieren Sie zuerst Coreutils mit Gebräu:

brew install coreutils

Führen Sie nun die folgenden Befehle aus:

git config --global filter.tabspace.smudge 'gunexpand --tabs=4 --first-only'
git config --global filter.tabspace.clean 'gexpand --tabs=4 --initial'

Alle Systeme

Sie können jetzt alle Dateien Ihres Projekts auschecken. Sie können das tun mit:

git checkout HEAD -- **

und alle Python-Dateien haben jetzt Tabulatoren anstelle von Leerzeichen.

Bearbeiten : Der Befehl zum erzwungenen Auschecken wurde geändert. Sie sollten Ihre Arbeit natürlich zuerst verpflichten.

Olivier Verdier
quelle
1
Der saubere Filter funktioniert bei mir nicht. Wenn ich git hinzufügen. Ich erhalte die Fehlermeldung "Fehler: Externer Filter expand --tabs = 4 --initial failed". Ich bin unter Windows. Macht das einen Unterschied?
Jeremy Hicks
2
@Jeremy: Erweitern / Nicht erweitern sind Unix-Befehle. Sie müssen entweder Windows-Ports / Äquivalente finden oder etwas wie Cygwin
Tim
1
Ich habe bast Arbeitsversion sourceforge.net/projects/gnuwin32/files/coreutils/5.3.0
hazzik
3
@ Marc-André Guter Punkt. Ich benutze tatsächlich die Coreutils-Versionen. (Installieren homebrewund dann ausführen brew install coreutils).
Olivier Verdier
2
Es scheint, dass dies nicht mehr funktioniert, die Filter tun nichts für mich. Nach dem Auschecken haben die Dateien noch Leerzeichen. Gibt es hierzu Neuigkeiten?
Philipp Ludwig
141

Ja, eine mögliche Lösung besteht darin, einen Git-Attributfiltertreiber (siehe auch GitPro-Buch ) zu verwenden, um einen Verschmutzungs- / Bereinigungsmechanismus zu definieren.

Alt-Text

Dieser Weg:

  • Jedes Mal, wenn Sie einige Dateien Ihres Repos auschecken, können Leerzeichen in Registerkarten konvertiert werden.
  • Wenn Sie jedoch einchecken (und pushen und veröffentlichen), werden dieselben Dateien nur mit Leerzeichen gespeichert.

Sie können diesen Filtertreiber (hier ' tabspace' genannt) im .git/info/attributes(für einen Filter, der auf alle Dateien im Git-Repo angewendet wird) mit folgendem Inhalt deklarieren :

*.py  filter=tabspace

Führen Sie nun die folgenden Befehle aus:

# local config for the current repo
git config filter.tabspace.smudge 'script_to_make_tabs'
git config filter.tabspace.clean 'script_to_make_spaces'

Siehe Olivier ‚s Antwort für ein konkretes Arbeitsbeispiel für eine solche wisch / sauber Reihe von Anweisungen.

VonC
quelle
Leider funktioniert es einfach nicht. Ich habe alle Anweisungen befolgt, aber Git wendet den Fiter nicht an. :-( Wenn ich auschecke, wird der Wischfilter nicht angewendet, und wenn ich einchecke, passiert auch nichts ... git ist manchmal so frustrierend ...
Olivier Verdier
@Olivier: Seltsam, ich hatte nie ein Problem damit, solange ich den Umfang des Attributfilters (auf einen bestimmten Teilbaum, nur für einen bestimmten Dateityp) sorgfältig beschränke, um das Auschecken / Auschecken nicht zu verlangsamen. in Bearbeitung. Siehe zum Beispiel stackoverflow.com/questions/62264/…
VonC
Vielen Dank! Jetzt gehts. Siehe die vollständige Lösung: stackoverflow.com/questions/2316677/…
Olivier Verdier
@Vonc: Vielleicht sollte man die --globalFlagge entfernen , da dies bedeuten würde, dass Sie Leerzeichen an jedes Kollaborationsprojekt senden ...
Willem Van Onsem
@CommuSoft nur zu den Projekten, die das Recht haben .gitattributes. Aber ja, es ist einfacher zu verstehen, ob die Konfiguration lokal im Repo gehalten wird. Ich habe die Antwort bearbeitet.
VonC
39

Sehr nützliche Informationen für alle, die GitHub (oder einen ähnlichen Dienst) verwenden.

~/.gitconfig

[filter "tabspace"]
    smudge = unexpand --tabs=4 --first-only
    clean = expand --tabs=4 --initial
[filter "tabspace2"]
    smudge = unexpand --tabs=2 --first-only
    clean = expand --tabs=2 --initial

Dann habe ich zwei Dateien: attributes

*.js  filter=tabspace
*.html  filter=tabspace
*.css  filter=tabspace
*.json  filter=tabspace

und attributes2

*.js  filter=tabspace2
*.html  filter=tabspace2
*.css  filter=tabspace2
*.json  filter=tabspace2

Arbeit an persönlichen Projekten

mkdir project
cd project
git init
cp ~/path/to/attributes .git/info/

Auf diese Weise sieht es in der Codeansicht, mit 8 space tabsder in allen Browsern das Standardverhalten verwendet wird, nicht albern aus, wenn Sie Ihre Arbeit auf Github endgültig vorantreiben .

Beiträge zu anderen Projekten

mkdir project
cd project
git init
cp ~/path/to/attributes2 .git/info/attributes
git remote add origin [email protected]:some/repo.git
git pull origin branch

Auf diese Weise können Sie mit normalen Registerkarten an 2 space indentedProjekten arbeiten.

Natürlich können Sie eine ähnliche Lösung für die Konvertierung schreiben. Dies 4 space to 2 spaceist der Fall, wenn Sie zu von mir veröffentlichten Projekten beitragen möchten und bei der Entwicklung in der Regel zwei Leerzeichen verwenden.

simo
quelle
2
Verwandte: Speichern der Git-Konfiguration als Teil des Repositorys ; Beachten Sie auch, dass Sie eine .gitattributesDatei in Ihrem Repo verwenden (und festschreiben) können
Tobias Kienzler
1

Wenn Sie unter Windows arbeiten, müssen Sie einige zusätzliche Schritte ausführen, damit die Lösung von @Olivier Verdier funktioniert.

  1. Laden Sie CoreUtils für Windows herunter
  2. Fügen Sie nach der Installation den Installationsort in Ihren PATH ein ( So fügen Sie eine Pfadvariable hinzu )
  3. Ich habe expand.exe in gexpand.exe umbenannt, da es bereits ein Windows-Erweiterungsdienstprogramm gibt.
odyth
quelle