Blog

Mühelose Verwaltung von GitHub-Konten: SSH-Agenten in WSL und Containern beherrschen

Marius Boden

Marius Boden

Aktualisiert Oktober 15, 2025
7 Minuten

Vor kurzem habe ich über die Verwendung des 1Password SSH-Agenten mit Windows und VSCode DevContainern geschrieben. Kurze Zeit später wurde ich mit dem Problem konfrontiert, mit 2 GitHub-Konten gleichzeitig zu arbeiten. Zurzeit erlaubt GitHub nicht die Verwendung desselben SSH-Schlüssels in mehreren Konten, so dass für jedes Konto ein eigener Schlüssel erstellt werden muss.

Dieser Artikel zeigt Ihnen, wie Sie Ihre Umgebung so einrichten, dass Sie mit 2 verschiedenen GitHub-Konten arbeiten können, indem Sie den 1Password SSH-Agenten in WSL und VSCode DevContainers verwenden.

SSH einrichten

Erstellen Sie zunächst die SSH-Authentifizierungs- und Signierschlüssel für das neue GitHub-Konto und machen Sie es über den 1Password SSH-Agenten verfügbar, wie im vorherigen Artikel beschrieben.

ssh-add -l
256 SHA256:sPS3deWzqfS8H8Iqa/k1lZ/1AFwf5551uwiSyj/TgAo Github Signing (ED25519)
4096 SHA256:QEzxxocaOsX19Hk2tSv/jeev7qrD8eaQK2eYBj7JvD4 Azure (RSA)
256 SHA256:gaFfPRLGjGotBULiUBUYP6/HMDXvnUbxlHjX2zrpNsM Github (ED25519)
256 SHA256:lviYy9axbmWN7NbOz4LsGgHu9jCX6fJVgnhk+lFVGh8 Github Signing Custom (ED25519)
256 SHA256:OO9rRRIrxGkPouVDy1mNYI/m0KZvS+gTtqWuzu4Zg/g Github Custom (ED25519)

Stellen Sie anschließend sicher, dass der SSH-Agent den richtigen Schlüssel für jedes Repository verwendet. Dies kann durch verschiedene SSH-Konfigurationen für denselben Host erreicht werden, die festlegen, welcher Schlüssel verwendet werden soll. Dazu müssen wir die öffentlichen SSH-Schlüssel exportieren, wie in den 1Password-Dokumenten beschrieben.

~/.ssh/pubkeys$ ll
total 20
drwxr-xr-x 2 marius marius 4096 Sep  4 14:58 ./
drwx------ 4 marius marius 4096 Sep  4 14:38 ../
-rw------- 1 marius marius  724 Aug 21 11:21 azdo.pub
-rw------- 1 marius marius   80 Aug 21 11:20 github.pub
-rw------- 1 marius marius   80 Sep  4 14:36 github_custom.pub

In der SSH-Konfiguration können Sie einen öffentlichen Schlüssel als IdentityFile konfigurieren. Da der SSH-Agent jedoch eine eigene Logik für die Auswahl des zu verwendenden Schlüssels hat, werden nur die entsprechenden privaten Schlüssel zur Liste der Schlüssel hinzugefügt, die für die SSH-Authentifizierung mit dem angegebenen Server in Frage kommen. Um sicherzustellen, dass nur der angegebene Schlüssel verwendet wird, aktivieren Sie die Einstellung IdentitiesOnly für den konfigurierten Host. Jetzt wird der Agent nur den privaten SSH-Schlüssel für den angegebenen öffentlichen Schlüssel berücksichtigen.

Host *
  ForwardAgent yes
  IdentityAgent /tmp/1password-agent.sock

Host github.com
  HostName github.com
  IdentityFile ~/.ssh/pubkeys/github.pub
  IdentitiesOnly yes

Host githubcustom
  HostName github.com
  IdentityFile ~/.ssh/pubkeys/github_custom.pub
  IdentitiesOnly yes

Host ssh.dev.azure.com
  Hostname ssh.dev.azure.com
  IdentityFile ~/.ssh/pubkeys/azdo.pub
  IdentitiesOnly yes

Git einrichten

Gut, jetzt haben wir verschiedene SSH-Hosts für github.com eingerichtet. Wenn wir jedoch ein Repository von github.com klonen, wird nur der erste ausgewählt, da der Server in der Klon-URL immer github.com ist.

Host github.com
  HostName github.com
  IdentityFile ~/.ssh/github.pub
  IdentitiesOnly yes

Host githubcustom
  HostName github.com
  IdentityFile ~/.ssh/github_custom.pub
  IdentitiesOnly yes

Also die Klon-URL

git@github.com:shrutikapoor08/devjoke.git

muss geändert werden in

git@githubcustom:shrutikapoor08/devjoke.git

Um dies in den Entwicklungsabläufen bequemer zu gestalten, erstellen wir einen Git-Alias für das Klonen von Repos im Namen des benutzerdefinierten Kontos.

# config alias
git config --global alias.clone-custom '!f() { git clone --config user.email='custommail@customdomain.com' --config user.signingkey='ssh-ssh-ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIKxhFVyilOVwuMW8AAmtHqemrJDzT7d14VAR4Rcj81u4' $(echo $1 | sed 's/git@github.com/git@githubcustom/g'); }; f'

# clone repo
git clone-custom git@github.com:shrutikapoor08/devjoke.git

Der Alias beginnt mit !, um einen komplexen Befehl in einer separaten Shell auszuführen. Danach definieren wir eine Funktion f zum Klonen und Konfigurieren des Repos. Schließlich wird die Funktion mit dem Argument des Alias-Befehls aufgerufen.

Um dies verständlicher zu machen, lassen Sie uns die Funktion ausschreiben.

# define function
f() {
  git clone 
  --config user.email='custommail@customdomain.com' 
  --config user.signingkey='ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIKxhFVyilOVwuMW8AAmtHqemrJDzT7d14VAR4Rcj81u4' 
  $(echo $1 | sed 's/git@github.com/git@githubcustom/g');
}

# call function
f git@github.com:shrutikapoor08/devjoke.git

Wie wir sehen können, ruft die Funktion f() git clone mit der Option --config auf, um die individuelle E-Mail und den Signierschlüssel des Benutzers zu konfigurieren. Die Klon-URL ist der Funktionsparameter, wobei github.com durch unser benutzerdefiniertes ssh-Ziel githubcustom ersetzt wird.

In der WSL laufen

Jetzt können wir wie gewohnt ein Repository mit unserem Standardkonto klonen.

# clone repo
git clone git@github.com:shrutikapoor08/devjoke.git devjokes-default
Cloning into 'devjokes-default'...
remote: Enumerating objects: 2441, done.
remote: Counting objects: 100% (234/234), done.
remote: Compressing objects: 100% (174/174), done.
remote: Total 2441 (delta 137), reused 149 (delta 60), pack-reused 2207
Receiving objects: 100% (2441/2441), 56.87 MiB | 6.24 MiB/s, done.
Resolving deltas: 100% (1251/1251), done.

# switch into repository
cd devjokes-default/

# display local git configuration
git config --local --list
core.repositoryformatversion=0
core.filemode=true
core.bare=false
core.logallrefupdates=true
remote.origin.url=git@github.com:shrutikapoor08/devjoke.git
remote.origin.fetch=+refs/heads/*:refs/remotes/origin/*
branch.master.remote=origin
branch.master.merge=refs/heads/master

# display git remotes
git remote -v
origin  git@github.com:shrutikapoor08/devjoke.git (fetch)
origin  git@github.com:shrutikapoor08/devjoke.git (push)

Wie wir sehen können, gibt es keine lokale Konfiguration für die E-Mail und den Signierschlüssel des Benutzers, so dass die gobale Konfiguration verwendet wird. Origin zeigt auf github.com, wie es für das Standardkonto sein sollte.

Aber wenn wir unseren neuen aliasbasierten Befehl verwenden, können wir das Repository klonen und für die Arbeit mit dem benutzerdefinierten Konto konfigurieren.

# clone custom
git clone-custom git@github.com:shrutikapoor08/devjoke.git devjokes-custom
Cloning into 'devjokes-custom'...
remote: Enumerating objects: 2441, done.
remote: Counting objects: 100% (234/234), done.
remote: Compressing objects: 100% (174/174), done.
remote: Total 2441 (delta 137), reused 149 (delta 60), pack-reused 2207
Receiving objects: 100% (2441/2441), 56.87 MiB | 6.49 MiB/s, done.
Resolving deltas: 100% (1251/1251), done.

# switch into repository
cd devjokes-custom/

# display local git configuration
git config --local --list
core.repositoryformatversion=0
core.filemode=true
core.bare=false
core.logallrefupdates=true
user.email=custommail@customdomain.com
user.signingkey=ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIKxhFVyilOVwuMW8AAmtHqemrJDzT7d14VAR4Rcj81u4
remote.origin.url=git@githubcustom:shrutikapoor08/devjoke.git
remote.origin.fetch=+refs/heads/*:refs/remotes/origin/*
branch.master.remote=origin
branch.master.merge=refs/heads/master

# display git remotes
git remote -v
origin  git@githubcustom:shrutikapoor08/devjoke.git (fetch)
origin  git@githubcustom:shrutikapoor08/devjoke.git (push)

Die lokale Konfiguration der E-Mail und des Signierschlüssels des Benutzers hat Vorrang vor der globalen Konfiguration und der Ursprung verweist auf das benutzerdefinierte ssh-Ziel.

In VSCode DevContainer ausführen

Die devcontainer-Erweiterung tut bereits viel, um die Arbeit mit Ihren Repositories innerhalb eines Containers so komfortabel wie möglich zu gestalten. Wir müssen uns zum Beispiel keine Gedanken darüber machen, wie wir unsere globale Git-Konfiguration in den Container bekommen.

The extension will automatically copy your local .gitconfig file into the container on startup so you should not need to do this in the container itself. https://code.visualstudio.com/remote/advancedcontainers/sharing-git-credentials

Das ist großartig, da wir innerhalb des Containers genauso mit Git arbeiten können wie außerhalb. In unserem speziellen Fall gibt es jedoch einige Probleme damit. Sie erinnern sich, dass wir in unserer ssh-Konfiguration ssh-Hosts und Identitätsdateien für unseren benutzerdefinierten github-Benutzer konfiguriert haben. Während die Erweiterungen die Git-Konfiguration mit dem Container teilen, gilt dies nicht für unsere ssh-Konfiguration. Eine Änderung unserer devcontainer.json zum Kopieren der Dateien würde nicht helfen, da der Container dann an eine bestimmte Systemkonfiguration gebunden wäre, was die Arbeit in einem Container unsinnig machen würde.

Meine Lösung für dieses Problem ist die Verwendung einer anderen Funktion von devcontainers: dotfiles Repositories. Indem ich ein Repository mit meiner ssh-Konfiguration und meinen öffentlichen Schlüsseldateien einrichte, kann ich sicherstellen, dass sie nach dem Start im Container vorhanden sind. Das Repository kann privat sein, muss aber für den Standardbenutzer von github zugänglich sein.

Im Repository gibt es ein Verzeichnis .ssh mit der ssh-Konfiguration und den öffentlichen Schlüsseln sowie ein Installationsskript install.sh.

~/repos/dotfiles$ tree -a
.
├── .ssh
│   ├── config
│   └── pubkeys
│       ├── azdo.pub
│       ├── github.pub
│       └── github_custom.pub
└── install.sh

Die ssh-Konfiguration ist fast identisch mit der von meinem Hostsystem, die ich zuvor gezeigt habe, bis auf die entfernte Konfiguration von ForwardAgent und IdentityAgent. Nur die Konfiguration der Hosts mit Identitätsdateien ist erforderlich.

Host github.com
  HostName github.com
  IdentityFile ~/.ssh/pubkeys/github.pub
  IdentitiesOnly yes

Host githubcustom
  HostName github.com
  IdentityFile ~/.ssh/pubkeys/github_custom.pub
  IdentitiesOnly yes

Host ssh.dev.azure.com
  Hostname ssh.dev.azure.com
  IdentityFile ~/.ssh/pubkeys/azdo.pub
  IdentitiesOnly yes

Das Skript install.sh beschränkt sich auf das Kopieren des Verzeichnisses .ssh in das Home-Verzeichnis des Containers.

#!/bin/bash

cp -r $(dirname $0)/.ssh ~/

Öffnen Sie vscode auf dem Host(auf dem kein Container läuft, da sonst die Konfigurationsoptionen nicht verfügbar sind), um die Einstellungen der devcontainer-Erweiterung für die Verwendung des Repositorys als dotfile-Repository zu konfigurieren.

Legen Sie das Repository, den Zielpfad und den Installationsbefehl fest, damit das Dotfile-Repository unter dem Traget-Pfad ausgecheckt und der Installationsbefehl innerhalb des Repositorys ausgeführt wird.

Starten Sie nun ein Projekt mit einem Devcontainer und überprüfen Sie die Einrichtung. Hinweis: Wenn der Container zuvor gebaut wurde, bauen Sie ihn neu auf, um das dotfile-Repository auszuchecken und das Skript beim Start auszuführen.

Wenn Sie alles richtig eingerichtet haben, sollten Sie jetzt in der Lage sein, mit Git zu arbeiten und Git-Commits mit den Schlüsseln des ssh-Agenten innerhalb eines Containers zu signieren

Verfasst von

Marius Boden

Marius Boden is passionate about technology and software development. Being a hybrid of developer, architect and DevOps consultant, he can keep track of the big picture and help teams at any point in the development lifecycle to get to the next level.

Contact

Let’s discuss how we can support your journey.