Skip to content

rosstaco/git-personas

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

3 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Git Personas

Manage multiple Git identities (name, email, signing key) with automatic configuration based on repository URL patterns. Designed to work seamlessly with VS Code Dev Containers and SSH agent forwarding.

The Problem

When working with multiple Git identities (personal, work, client projects), you need:

  • Different user.name and user.email per repository
  • SSH commit signing with different keys
  • Everything to work inside devcontainers where your host SSH keys live

Git Personas solves this by letting you define personas once, then automatically configuring repositories based on URL patterns—including inside devcontainers where VS Code forwards your SSH agent.

Features

  • 🔄 URL pattern matching - automatically select persona based on remote URL
  • 🪝 Git hooks - configure repos at clone time (config written to .git/config)
  • 🔐 SSH commit signing - uses your SSH keys via agent forwarding
  • Single config - ~/.git-personas.yml as source of truth
  • 🐳 Dev Container ready - works via SSH agent socket forwarding

Installation

# Install globally (recommended)
uv tool install git+https://github.com/rosstaco/git-personas

# Or for development
git clone https://github.com/rosstaco/git-personas.git
cd git-personas
uv sync

Quick Start

# 1. Initialize config and install Git hooks
git-personas init

# 2. Add a persona (interactive - generates SSH key if needed)
git-personas add

# 3. Apply to existing repositories
git-personas apply ~/repos

# 4. Validate your setup
git-personas validate

How It Works

Git Personas provides two approaches that work together:

1. Git Hooks (Recommended for Devcontainers)

When you clone a repo, a post-checkout hook:

  1. Reads the remote URL
  2. Matches it to a persona's URL patterns
  3. Writes identity config directly to .git/config

Why this matters for devcontainers:

  • Config is stored in .git/config, which is inside the repo
  • When you open the repo in a devcontainer, the config comes with it
  • VS Code automatically forwards your SSH agent socket
  • Your private signing keys remain on your host—commits just work

2. Git includeIf (Fallback for Local)

The sync command generates:

  • ~/.gitconfig.d/<persona> files with inlined public keys
  • includeIf rules using hasconfig:remote.*.url

This is useful for repos cloned before hooks were installed.

Configuration

Config file: ~/.git-personas.yml

settings:
  gpg_format: ssh          # Use SSH keys for signing
  sign_commits: true       # Enable commit signing by default

personas:
  # Work GitHub org (more specific patterns first)
  github-work:
    name: "Your Name"
    email: "you@company.com"
    signing_key: "~/.ssh/id_ed25519_work"
    patterns:
      - "https://github.com/my-company/**"
      - "git@github.com:my-company/**"

  # Personal GitHub (catch-all, lowest priority)
  github-personal:
    name: "Your Name"
    email: "personal@example.com"
    signing_key: "~/.ssh/id_ed25519_personal"
    patterns:
      - "https://github.com/**"
      - "git@github.com:**"

  # Azure DevOps (no SSH signing support)
  azdo-work:
    name: "Your Name"
    email: "you@company.com"
    signing_key: "~/.ssh/id_ed25519_azdo"
    sign_commits: false    # AzDO doesn't support SSH signature verification
    patterns:
      - "https://dev.azure.com/myorg/**"
      - "git@ssh.dev.azure.com:v3/myorg/**"

Pattern rules:

  • Use ** to match across path separators
  • More specific patterns should come before catch-all patterns
  • Both HTTPS and SSH URL formats are supported

Commands

Setup

git-personas init

Create a new configuration file and install clone hooks.

git-personas init                    # Create ~/.git-personas.yml + install hooks
git-personas init --path ./config.yml  # Custom path
git-personas init --force            # Overwrite existing
git-personas init --no-hook          # Skip hook installation

Options:

  • -p, --path PATH - Path for config file (default: ~/.git-personas.yml)
  • -f, --force - Overwrite existing config file
  • --no-hook - Skip installing the post-checkout hook

git-personas sync

Generate gitconfig files from YAML configuration (for includeIf approach).

git-personas sync              # Apply changes
git-personas sync --dry-run    # Preview without changes
git-personas sync --yes        # Skip confirmation prompts

Options:

  • -c, --config PATH - Path to config file
  • -n, --dry-run - Show what would be done without making changes
  • -y, --yes - Automatically confirm prompts

What it does:

  1. Detects and offers to remove conflicting global user.name/user.email settings
  2. Generates ~/.gitconfig.d/<persona> files with inlined public keys
  3. Updates ~/.gitconfig with includeIf rules

Personas

git-personas list

Show all configured personas in a table.

git-personas list

git-personas add

Interactively add a new persona.

git-personas add

Features:

  • Prompts for persona name, display name, email
  • Supports GitHub, Azure DevOps, GitLab, Bitbucket patterns
  • Guides you through SSH signing key setup
  • Shows upload instructions for each Git service

git-personas show <name>

Show details for a specific persona.

git-personas show github-personal

git-personas delete <name>

Remove a persona from configuration.

git-personas delete old-persona
git-personas delete old-persona --force  # Skip confirmation

Repositories

git-personas which

Show which persona would be used for the current repository.

git-personas which                    # Check current repo
git-personas which --url git@github.com:org/repo  # Test a URL

Output:

  • Current git config (with source: repo or global)
  • Matched persona details
  • Whether repo is configured

git-personas configure-repo

Configure the current repository based on its remote URL.

git-personas configure-repo           # Configure current repo
git-personas configure-repo --repo /path/to/repo  # Specific repo

This is what the hooks call automatically, but you can run it manually.


git-personas apply <path>

Apply persona config to all git repositories in a directory.

git-personas apply ~/repos           # Configure all repos
git-personas apply ~/repos --dry-run # Preview what would happen
git-personas apply ~/repos --force   # Re-configure even if already done

Options:

  • -n, --dry-run - Show what would be configured without making changes
  • -f, --force - Re-configure repos even if already configured
  • -c, --config PATH - Path to config file

Hooks

git-personas install-hook

Install the post-checkout hook for automatic repo configuration.

git-personas install-hook

The hook is installed to ~/.git-templates/hooks/ and Git's init.templateDir is configured. New clones will automatically get the hook.

How it works:

  • post-checkout hook: Configures new clones automatically
  • post-merge hook: Configures old repos on first pull

git-personas uninstall-hook

Remove the git-personas hooks.

git-personas uninstall-hook

Utilities

git-personas validate

Check configuration and SSH agent status.

git-personas validate

Checks:

  • Public key files exist and are readable
  • Keys are loaded in SSH agent
  • URL patterns are defined

git-personas preview

Preview the generated gitconfig includeIf section.

git-personas preview

Global Options

git-personas --version   # Show version
git-personas --help      # Show help

Dev Container Support

Git Personas is designed with devcontainers in mind. Here's how it works:

How SSH Signing Works in Devcontainers

  1. Your SSH keys stay on your host machine - never copied into containers
  2. VS Code forwards your SSH agent socket - the SSH_AUTH_SOCK environment variable points to a socket that communicates with your host's SSH agent
  3. Git hooks write config to .git/config - this travels with the repo into the container
  4. Commits are signed via the forwarded agent - Git uses the socket to request signatures from your host's keys

Setup

On your host machine:

# Install git-personas and set up hooks
git-personas init
git-personas add  # Add your personas

# Make sure your signing keys are in the SSH agent
ssh-add ~/.ssh/id_ed25519_work
ssh-add ~/.ssh/id_ed25519_personal

That's it! When you clone repos on your host, the hook configures .git/config. When you open in a devcontainer, the config is there and SSH agent forwarding handles signing.

Verifying It Works

Inside a devcontainer:

# Check agent forwarding is working
ssh-add -l

# Check which persona is configured
git-personas which

# Test commit signing
echo "test" >> test.txt && git commit -am "test signed commit"
git log --show-signature -1

If Using includeIf Approach

If you need the sync command's includeIf rules inside containers, mount the config directory:

{
  "mounts": [
    "source=${localEnv:HOME}/.gitconfig.d,target=/home/vscode/.gitconfig.d,type=bind,readonly"
  ]
}

URL Pattern Examples

Patterns use glob syntax where ** matches across path separators.

Pattern Matches
git@github.com:company/** GitHub org (SSH)
https://github.com/company/** GitHub org (HTTPS)
https://github.com/** Any GitHub URL (catch-all)
git@ssh.dev.azure.com:v3/org/** Azure DevOps (SSH)
https://dev.azure.com/org/** Azure DevOps (HTTPS)
git@gitlab.com:group/** GitLab group (SSH)
git@bitbucket.org:workspace/** Bitbucket workspace (SSH)

Tips:

  • Define specific patterns (org/company) before catch-all patterns
  • Both HTTPS and SSH URLs are normalized for matching
  • Use git-personas which --url <url> to test pattern matching

Troubleshooting

SSH agent not forwarding in devcontainer

# Inside the container, check if agent is available
echo $SSH_AUTH_SOCK
ssh-add -l

If no keys are listed, ensure:

  1. SSH agent is running on your host
  2. Keys are added: ssh-add ~/.ssh/id_ed25519_work
  3. VS Code's SSH agent forwarding is enabled (default)

Commits not being signed

# Check signing is configured
git config --local user.signingkey
git config --local commit.gpgsign

# Verify the key is in the agent
ssh-add -l

Wrong identity being used

# See which persona matches
git-personas which

# Check local config
git config --local user.email

# Re-run configuration
git-personas configure-repo

Hooks not running on clone

# Check hooks are installed
ls ~/.git-templates/hooks/
git config --global init.templateDir

# Reinstall if needed
git-personas install-hook

Global settings overriding personas

# Check for global user settings
git config --global user.email

# Run sync to fix (it will prompt to remove them)
git-personas sync

License

MIT

About

No description, website, or topics provided.

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors

Languages