111 lines
4.4 KiB
Markdown
111 lines
4.4 KiB
Markdown
---
|
|
title: "Git — Per-Remote Identity with includeIf"
|
|
aliases: [git-includeif, git-multiple-identities, git-work-personal-email, git-conditional-config]
|
|
tags: [git, dotfiles, identity, ssh, bitbucket, github]
|
|
sources:
|
|
- "daily/2026-04-23.md"
|
|
created: 2026-04-23
|
|
updated: 2026-04-23
|
|
---
|
|
|
|
# Git — Per-Remote Identity with includeIf
|
|
|
|
Git's `includeIf` directive in `.gitconfig` applies a supplemental config file only when a condition matches. The `hasconfig:remote.*.url` variant matches on the remote URL of the current repository, making it possible to automatically switch git identities (email, signing key, etc.) based on whether a repo is hosted on GitHub vs Bitbucket or any other remote — without any per-repo manual config.
|
|
|
|
## Key Points
|
|
|
|
- **`includeIf "hasconfig:remote.*.url:*github.com*"`** matches any repo with a GitHub remote — applies a separate `.gitconfig-github` file automatically
|
|
- Eliminates the need to run `git config user.email` in every new personal repo — the correct identity is applied by remote URL
|
|
- The condition uses glob-style wildcards: `*github.com*` matches both `https://github.com/...` and `git@github.com:...`
|
|
- More robust than `includeIf "gitdir:~/projects/personal/"` (directory-based) — works regardless of where the repo is cloned
|
|
- Order matters: the included file is applied after the main config, so it overrides values in `.gitconfig`
|
|
|
|
## Details
|
|
|
|
### The Problem This Solves
|
|
|
|
Working with multiple git identities (work email for Bitbucket/Oliver repos, personal email for GitHub) previously required remembering to run `git config user.email` in each new personal repo. Forgetting resulted in commits to GitHub attributed to the work email. Remote-based `includeIf` makes this automatic and invisible.
|
|
|
|
### `.gitconfig` Setup
|
|
|
|
```ini
|
|
# ~/.gitconfig — main config (default = work identity)
|
|
[user]
|
|
name = Vadym Samoilenko
|
|
email = vadymsamoilenko@oliver.agency
|
|
|
|
# Override with personal identity for GitHub repos
|
|
[includeIf "hasconfig:remote.*.url:*github.com*"]
|
|
path = ~/.gitconfig-github
|
|
```
|
|
|
|
```ini
|
|
# ~/.gitconfig-github — personal identity
|
|
[user]
|
|
email = samoylenko.vadym@gmail.com
|
|
```
|
|
|
|
After this setup, any repo with a `github.com` remote automatically uses the personal email. Bitbucket, internal GitLab, and other remotes use the default work email.
|
|
|
|
### Verifying the Correct Identity
|
|
|
|
```bash
|
|
# In a GitHub repo
|
|
git config user.email
|
|
# → samoylenko.vadym@gmail.com
|
|
|
|
# In a Bitbucket/work repo
|
|
git config user.email
|
|
# → vadymsamoilenko@oliver.agency
|
|
```
|
|
|
|
### SSH Key Separation (Complementary)
|
|
|
|
`includeIf` handles commit identity (who authored the commit). SSH key selection (which credential is used to authenticate the push) is handled separately in `~/.ssh/config`:
|
|
|
|
```ssh
|
|
# ~/.ssh/config
|
|
Host github.com
|
|
HostName github.com
|
|
User git
|
|
IdentityFile ~/.ssh/id_ed25519_github
|
|
|
|
Host bitbucket.org
|
|
HostName bitbucket.org
|
|
User git
|
|
IdentityFile ~/.ssh/id_ed25519_bitbucket
|
|
```
|
|
|
|
Both pieces are needed: `includeIf` for commit metadata, `~/.ssh/config` for authentication.
|
|
|
|
### Alternative: Directory-Based includeIf
|
|
|
|
If the remote URL approach is too broad, a directory-based condition is more explicit:
|
|
|
|
```ini
|
|
[includeIf "gitdir:~/personal/"]
|
|
path = ~/.gitconfig-github
|
|
```
|
|
|
|
This applies the override only to repos inside `~/personal/`. The downside: repos cloned anywhere else won't get the override automatically.
|
|
|
|
### Migration: Adding includeIf to an Existing Config
|
|
|
|
When migrating from a single identity to multiple identities:
|
|
|
|
1. Set the work email as the default in `~/.gitconfig`
|
|
2. Create `~/.gitconfig-github` with the personal email
|
|
3. Add the `includeIf` block to `~/.gitconfig`
|
|
4. Verify in an existing GitHub repo: `git config user.email`
|
|
|
|
Past commits already made with the wrong email are not affected — `includeIf` only applies to future commits.
|
|
|
|
## Related Concepts
|
|
|
|
- [[wiki/concepts/fish-shell-path-config]] — SSH aliases as Fish functions complement this SSH config approach
|
|
- [[wiki/concepts/remote-server-dotfiles-bootstrap]] — dotfiles migration context where this pattern was configured
|
|
- [[wiki/concepts/bitbucket-mcp-atlassian]] — Bitbucket identity context (one of the two remotes managed by this config)
|
|
|
|
## Sources
|
|
|
|
- [[daily/2026-04-23.md]] — New workstation SSH/git migration session: git identity split required between `vadymsamoilenko@oliver.agency` (Bitbucket/work) and `samoylenko.vadym@gmail.com` (GitHub); `includeIf "hasconfig:remote.*.url:*github.com*"` selected as the mechanism
|