-
1. Erste Schritte
- 1.1 Über Versionskontrolle
- 1.2 Eine kurze Geschichte von Git
- 1.3 Was ist Git?
- 1.4 Die Kommandozeile
- 1.5 Git installieren
- 1.6 Erstmalige Git-Einrichtung
- 1.7 Hilfe bekommen
- 1.8 Zusammenfassung
-
2. Git Grundlagen
-
3. Git Branching
- 3.1 Branches im Überblick
- 3.2 Grundlegendes Branching und Merging
- 3.3 Branch-Management
- 3.4 Branching-Workflows
- 3.5 Remote-Branches
- 3.6 Rebasing
- 3.7 Zusammenfassung
-
4. Git auf dem Server
- 4.1 Die Protokolle
- 4.2 Git auf einem Server einrichten
- 4.3 Generieren Ihres SSH-Public-Keys
- 4.4 Einrichten des Servers
- 4.5 Git Daemon
- 4.6 Smart HTTP
- 4.7 GitWeb
- 4.8 GitLab
- 4.9 Drittanbieter-Hosting-Optionen
- 4.10 Zusammenfassung
-
5. Verteiltes Git
-
6. GitHub
-
7. Git-Werkzeuge
- 7.1 Revisionsauswahl
- 7.2 Interaktives Staging
- 7.3 Stashing und Bereinigen
- 7.4 Ihre Arbeit signieren
- 7.5 Suchen
- 7.6 Historie umschreiben
- 7.7 Reset entmystifiziert
- 7.8 Fortgeschrittenes Merging
- 7.9 Rerere
- 7.10 Debugging mit Git
- 7.11 Submodule
- 7.12 Bundling
- 7.13 Ersetzen
- 7.14 Anmeldeinformationen speichern
- 7.15 Zusammenfassung
-
8. Git anpassen
-
9. Git und andere Systeme
- 9.1 Git als Client
- 9.2 Migration zu Git
- 9.3 Zusammenfassung
-
10. Git-Interna
- 10.1 Plumbing und Porcelain
- 10.2 Git-Objekte
- 10.3 Git-Referenzen
- 10.4 Packfiles
- 10.5 Die Refspec
- 10.6 Übertragungsprotokolle
- 10.7 Wartung und Datenwiederherstellung
- 10.8 Umgebungsvariablen
- 10.9 Zusammenfassung
-
Anhang A: Git in anderen Umgebungen
- A1.1 Grafische Oberflächen
- A1.2 Git in Visual Studio
- A1.3 Git in Visual Studio Code
- A1.4 Git in IntelliJ / PyCharm / WebStorm / PhpStorm / RubyMine
- A1.5 Git in Sublime Text
- A1.6 Git in Bash
- A1.7 Git in Zsh
- A1.8 Git in PowerShell
- A1.9 Zusammenfassung
-
Anhang B: Git in Ihre Anwendungen einbetten
- A2.1 Kommandozeilen-Git
- A2.2 Libgit2
- A2.3 JGit
- A2.4 go-git
- A2.5 Dulwich
-
Anhang C: Git-Befehle
- A3.1 Einrichtung und Konfiguration
- A3.2 Projekte abrufen und erstellen
- A3.3 Grundlegendes Snapshotting
- A3.4 Branching und Merging
- A3.5 Projekte teilen und aktualisieren
- A3.6 Inspektion und Vergleich
- A3.7 Debugging
- A3.8 Patching
- A3.9 E-Mail
- A3.10 Externe Systeme
- A3.11 Administration
- A3.12 Plumbing-Befehle
7.14 Git-Werkzeuge - Anmeldeinformationen speichern
Anmeldeinformationen speichern
Wenn Sie den SSH-Transport für die Verbindung zu Remotes verwenden, ist es möglich, einen Schlüssel ohne Passphrase zu haben, was Ihnen ermöglicht, Daten sicher zu übertragen, ohne Ihren Benutzernamen und Ihr Passwort eingeben zu müssen. Dies ist jedoch mit HTTP-Protokollen nicht möglich – jede Verbindung benötigt einen Benutzernamen und ein Passwort. Dies wird noch schwieriger für Systeme mit Zwei-Faktor-Authentifizierung, bei denen das Token, das Sie als Passwort verwenden, zufällig generiert und unaussprechlich ist.
Glücklicherweise verfügt Git über ein Anmeldeinformationssystem, das dabei helfen kann. Git bietet einige integrierte Optionen
-
Die Standardeinstellung ist, überhaupt nicht zu cachen. Jede Verbindung wird Sie nach Ihrem Benutzernamen und Passwort fragen.
-
Der „cache“-Modus speichert Anmeldeinformationen für eine bestimmte Zeit im Speicher. Keine der Passwörter werden jemals auf der Festplatte gespeichert und sie werden nach 15 Minuten aus dem Cache gelöscht.
-
Der „store“-Modus speichert die Anmeldeinformationen in einer Klartextdatei auf der Festplatte, und sie verfallen niemals. Das bedeutet, dass Sie Ihre Anmeldeinformationen nie wieder eingeben müssen, bis Sie Ihr Passwort für den Git-Host ändern. Der Nachteil dieses Ansatzes ist, dass Ihre Passwörter im Klartext in einer einfachen Datei in Ihrem Home-Verzeichnis gespeichert werden.
-
Wenn Sie macOS verwenden, wird Git mit dem Modus „osxkeychain“ geliefert, der Anmeldeinformationen im sicheren Schlüsselbund Ihres Systemkontos speichert. Diese Methode speichert die Anmeldeinformationen auf der Festplatte und sie verfallen niemals, aber sie werden mit demselben System verschlüsselt, das HTTPS-Zertifikate speichert und Safari automatisch ausfüllt.
-
Wenn Sie Windows verwenden, können Sie die Funktion **Git Credential Manager** aktivieren, wenn Sie Git for Windows installieren oder den neuesten GCM separat als eigenständigen Dienst installieren. Dies ähnelt dem oben beschriebenen „osxkeychain“-Helfer, verwendet jedoch den Windows Credential Store zur Verwaltung sensibler Informationen. Es kann auch Anmeldeinformationen für WSL1 oder WSL2 bereitstellen. Weitere Informationen finden Sie in den GCM-Installationsanweisungen.
Sie können eine dieser Methoden wählen, indem Sie einen Git-Konfigurationswert festlegen
$ git config --global credential.helper cache
Einige dieser Helfer haben Optionen. Der „store“-Helfer kann das Argument --file <path> annehmen, das den Speicherort der Klartextdatei anpasst (Standard ist ~/.git-credentials). Der „cache“-Helfer akzeptiert die Option --timeout <seconds>, die die Laufzeit seines Daemons ändert (Standard ist „900“ oder 15 Minuten). Hier ist ein Beispiel, wie Sie den „store“-Helfer mit einem benutzerdefinierten Dateinamen konfigurieren würden
$ git config --global credential.helper 'store --file ~/.my-credentials'
Git erlaubt Ihnen sogar, mehrere Helfer zu konfigurieren. Bei der Suche nach Anmeldeinformationen für einen bestimmten Host fragt Git diese in der Reihenfolge ab und stoppt, nachdem die erste Antwort gegeben wurde. Beim Speichern von Anmeldeinformationen sendet Git den Benutzernamen und das Passwort an **alle** Helfer in der Liste, und diese können entscheiden, was sie damit tun. So würde eine .gitconfig aussehen, wenn Sie eine Anmeldeinformationsdatei auf einem USB-Stick hätten, aber den In-Memory-Cache verwenden möchten, um Tipparbeit zu sparen, falls das Laufwerk nicht angeschlossen ist
[credential]
helper = store --file /mnt/thumbdrive/.git-credentials
helper = cache --timeout 30000
Hinter den Kulissen
Wie funktioniert das alles? Der Git-Root-Befehl für das Anmeldeinformations-Helper-System ist git credential, der einen Befehl als Argument entgegennimmt und dann weitere Eingaben über stdin erhält.
Dies lässt sich vielleicht leichter anhand eines Beispiels verstehen. Angenommen, ein Anmeldeinformations-Helfer wurde konfiguriert und hat Anmeldeinformationen für mygithost gespeichert. Hier ist eine Sitzung, die den „fill“-Befehl verwendet, der aufgerufen wird, wenn Git versucht, Anmeldeinformationen für einen Host zu finden
$ git credential fill (1)
protocol=https (2)
host=mygithost
(3)
protocol=https (4)
host=mygithost
username=bob
password=s3cre7
$ git credential fill (5)
protocol=https
host=unknownhost
Username for 'https://unknownhost': bob
Password for 'https://bob@unknownhost':
protocol=https
host=unknownhost
username=bob
password=s3cre7
-
Dies ist der Befehl, der die Interaktion initiiert.
-
Git-credential wartet dann auf Eingaben auf stdin. Wir geben ihm die Dinge, die wir wissen: das Protokoll und den Hostnamen.
-
Eine leere Zeile bedeutet, dass die Eingabe abgeschlossen ist und das Anmeldeinformationssystem mit dem antworten soll, was es weiß.
-
Git-credential übernimmt dann und schreibt auf stdout mit den Informationen, die es gefunden hat.
-
Wenn Anmeldeinformationen nicht gefunden werden, fragt Git den Benutzer nach dem Benutzernamen und dem Passwort und gibt sie an das aufrufende stdout zurück (hier sind sie an dieselbe Konsole angehängt).
Das Anmeldeinformationssystem ruft tatsächlich ein separates Programm von Git auf; welches und wie, hängt vom Konfigurationswert credential.helper ab. Es gibt mehrere Formen, die es annehmen kann
| Konfigurationswert | Verhalten |
|---|---|
|
Führt |
|
Führt |
|
Führt |
|
Code nach |
Die oben beschriebenen Helfer heißen also tatsächlich git-credential-cache, git-credential-store usw., und wir können sie so konfigurieren, dass sie Kommandozeilenargumente entgegennehmen. Die allgemeine Form dafür ist „git-credential-foo [args] <action>.“. Das stdin/stdout-Protokoll ist dasselbe wie bei git-credential, aber sie verwenden etwas andere Aktionen
-
getist eine Anfrage nach einem Benutzername/Passwort-Paar. -
storeist eine Anfrage, eine Reihe von Anmeldeinformationen in diesem Helfer-Speicher zu sichern. -
eraselöscht die Anmeldeinformationen für die gegebenen Eigenschaften aus diesem Helfer-Speicher.
Für die Aktionen store und erase ist keine Antwort erforderlich (Git ignoriert sie sowieso). Für die Aktion get ist Git jedoch sehr daran interessiert, was der Helfer zu sagen hat. Wenn der Helfer nichts Nützliches weiß, kann er einfach ohne Ausgabe beendet werden, aber wenn er etwas weiß, sollte er die bereitgestellten Informationen mit den gespeicherten Informationen ergänzen. Die Ausgabe wird wie eine Reihe von Zuweisungen behandelt; alles, was bereitgestellt wird, ersetzt, was Git bereits weiß.
Hier ist dasselbe Beispiel wie oben, aber wir überspringen git-credential und gehen direkt zu git-credential-store
$ git credential-store --file ~/git.store store (1)
protocol=https
host=mygithost
username=bob
password=s3cre7
$ git credential-store --file ~/git.store get (2)
protocol=https
host=mygithost
username=bob (3)
password=s3cre7
-
Hier weisen wir
git-credential-storean, einige Anmeldeinformationen zu speichern: Der Benutzername „bob“ und das Passwort „s3cre7“ sollen verwendet werden, wenn aufhttps://mygithostzugegriffen wird. -
Nun rufen wir diese Anmeldeinformationen ab. Wir stellen die Teile der Verbindung bereit, die wir bereits kennen (
https://mygithost), und eine leere Zeile. -
git-credential-storeantwortet mit dem oben gespeicherten Benutzernamen und Passwort.
So sieht die Datei ~/git.store aus
https://bob:s3cre7@mygithost
Es ist nur eine Reihe von Zeilen, die jeweils eine mit Anmeldeinformationen verschlüsselte URL enthalten. Die Helfer osxkeychain und wincred verwenden das native Format ihrer Backing Stores, während cache sein eigenes In-Memory-Format verwendet (das kein anderer Prozess lesen kann).
Ein benutzerdefinierter Anmeldeinformations-Cache
Da git-credential-store und seine Kollegen separate Programme von Git sind, ist es kein großer Sprung zu erkennen, dass *jedes* Programm ein Git-Anmeldeinformations-Helfer sein kann. Die von Git bereitgestellten Helfer decken viele gängige Anwendungsfälle ab, aber nicht alle. Nehmen wir zum Beispiel an, Ihr Team hat einige Anmeldeinformationen, die mit dem gesamten Team geteilt werden, vielleicht für die Bereitstellung. Diese werden in einem gemeinsamen Verzeichnis gespeichert, aber Sie möchten sie nicht in Ihren eigenen Anmeldeinformationsspeicher kopieren, da sie sich häufig ändern. Keiner der vorhandenen Helfer deckt diesen Fall ab. Sehen wir uns an, was erforderlich wäre, um unseren eigenen zu schreiben. Dieses Programm muss mehrere Schlüsselfunktionen haben
-
Die einzige Aktion, auf die wir achten müssen, ist
get;storeunderasesind Schreibvorgänge, also werden wir einfach sauber beenden, wenn sie empfangen werden. -
Das Dateiformat der Shared-Credential-Datei ist dasselbe wie das von
git-credential-storeverwendete. -
Der Speicherort dieser Datei ist ziemlich Standard, aber wir sollten dem Benutzer erlauben, einen benutzerdefinierten Pfad anzugeben, nur für den Fall.
Auch hier werden wir diese Erweiterung in Ruby schreiben, aber jede Sprache funktioniert, solange Git das fertige Produkt ausführen kann. Hier ist der vollständige Quellcode unseres neuen Anmeldeinformations-Helpers
#!/usr/bin/env ruby
require 'optparse'
path = File.expand_path '~/.git-credentials' # (1)
OptionParser.new do |opts|
opts.banner = 'USAGE: git-credential-read-only [options] <action>'
opts.on('-f', '--file PATH', 'Specify path for backing store') do |argpath|
path = File.expand_path argpath
end
end.parse!
exit(0) unless ARGV[0].downcase == 'get' # (2)
exit(0) unless File.exist? path
known = {} # (3)
while line = STDIN.gets
break if line.strip == ''
k,v = line.strip.split '=', 2
known[k] = v
end
File.readlines(path).each do |fileline| # (4)
prot,user,pass,host = fileline.scan(/^(.*?):\/\/(.*?):(.*?)@(.*)$/).first
if prot == known['protocol'] and host == known['host'] and user == known['username'] then
puts "protocol=#{prot}"
puts "host=#{host}"
puts "username=#{user}"
puts "password=#{pass}"
exit(0)
end
end
-
Hier parsen wir die Kommandozeilenoptionen und erlauben dem Benutzer, die Eingabedatei anzugeben. Der Standard ist
~/.git-credentials. -
Dieses Programm reagiert nur, wenn die Aktion
getist und die zugrunde liegende Speicherdatei existiert. -
Diese Schleife liest von stdin, bis die erste leere Zeile erreicht ist. Die Eingaben werden im
known-Hash zur späteren Referenz gespeichert. -
Diese Schleife liest den Inhalt der Speicherdatei und sucht nach Übereinstimmungen. Wenn Protokoll, Host und Benutzername aus
knownmit dieser Zeile übereinstimmen, gibt das Programm die Ergebnisse auf stdout aus und wird beendet.
Wir speichern unseren Helfer als git-credential-read-only, legen ihn irgendwo in unseren PATH und markieren ihn als ausführbar. So sieht eine interaktive Sitzung aus
$ git credential-read-only --file=/mnt/shared/creds get
protocol=https
host=mygithost
username=bob
protocol=https
host=mygithost
username=bob
password=s3cre7
Da sein Name mit „git-“ beginnt, können wir die einfache Syntax für den Konfigurationswert verwenden
$ git config --global credential.helper 'read-only --file /mnt/shared/creds'
Wie Sie sehen können, ist die Erweiterung dieses Systems ziemlich unkompliziert und kann einige häufige Probleme für Sie und Ihr Team lösen.