Skip to content

Build1 publisher3 min readPublished

Stop trying to remember your Git email: includeIf makes identity a property of the directory

A dev.to walkthrough revives a Git conditional include that has shipped since 2017. The useful part is not the trick but the two ways it fails without telling you.

The Engineer · Build desk

Drafted by a language model from the sources cited here and checked against its claim ledger before publication. How we use AISend a correction

What happened

  • Developers with more than one GitHub account commonly push a commit with the wrong email; Git did not warn and GitHub did not warn, and the mistake is typically found later in the commit history.
  • Git 2.13 introduced includeIf in 2017; it lets you apply different configurations based on which directory you are in.
  • The standard fix is to run git config user.email in each repo; it works but relies on remembering to do it every single time, which the author says you will not do consistently, especially mid-fix when you just want to commit and move on.
  • The author describes having more than two identities: work, personal, side projects, client work and experiments, each tied to its own GitHub account, email and SSH key, with the odds of pushing under the wrong one rising as repo and identity counts grow.
  • Setup is done once in ~/.gitconfig with entries such as [includeIf "gitdir:/home/you/dev/work/"] path = ~/.config/git-persona/profiles/work.gitconfig, so any repo under ~/dev/work/ automatically uses the work identity and any repo under ~/dev/personal/ uses the personal one, with no per-repo config.

Compiled by The EngineerSomething wrong?How this is made

Why it matters

Anyone running more than one GitHub account has probably pushed a commit under the wrong email, and neither Git nor GitHub raises an objection at the time [1]. A post on dev.to argues that the durable fix is not discipline but configuration: `includeIf`, a conditional include that has been in Git since version 2.13 in 2017 [2].

The usual remedy is to run `git config user.email` inside each repository. It works, and it depends on you remembering to do it every time, which the author is blunt about not doing consistently while mid-fix and wanting to commit [3]. That is the interesting property of the failure: it is not a knowledge gap, it is a recall gap, and recall gaps scale badly. The author describes identities multiplying past two into work, personal, side projects and client work, each with its own email and SSH key, so the odds of a wrong push rise with the count [4].

`includeIf` moves the decision from memory to the filesystem. In `~/.gitconfig` you declare a `gitdir:` condition per tree and point it at a profile file, so repos under `~/dev/work/` load one config and repos under `~/dev/personal/` load another [5]. The profile is an ordinary Git config: a `[user]` block with name and email, plus a `core.sshCommand` that pins a specific key with `IdentitiesOnly=yes` [6]. Set once, evaluated on every command.

The footguns are worth more attention than the syntax, because both are silent. Trailing slashes matter: `gitdir:/home/you/dev/work` matches by prefix, so it also claims `/home/you/dev/workplace`, while the trailing slash narrows the match to repos inside that directory [7]. And relative paths in `includeIf` resolve against the config file's location, not your working directory, which the author notes is documented but easy to misread [8]. Put those together and you have traded many small chances of a per-commit mistake for one chance of a setup-time mistake that then applies itself consistently and invisibly [14].

The SSH side has a matching trap. GitHub refuses the same key on two accounts, rejecting it with "Key is already in use" [9]. But with several keys loaded in `ssh-agent`, SSH may offer the wrong one first, and GitHub authenticates you as the owner of whichever key it accepted [10]. `IdentitiesOnly=yes` is what forces SSH to use only the key named for that identity and ignore the agent [11]. That is the part most hand-rolled setups miss, and it explains commits that carry the right email but land through the wrong account.

The author also ships a bash script, `git-persona`, which takes one command per identity to generate the key, write the profile, add the `includeIf` rule and print the public key for GitHub, plus subcommands to show the current identity, list identities and override for one repo [12]. Their pitch is auditability rather than features: no dependencies, no runtime, no daemon, roughly 600 lines of bash meant to be read in ten minutes, on the argument that anything managing your SSH keys should be verifiable [13].

Worth checking before you trust it: a repo cloned outside every configured prefix matches no condition and quietly falls back to your global identity, which is exactly the case that used to bite you [15]. Verify inside a fresh clone rather than assuming, and check `core.sshCommand` as well as `user.email`.

Loading claim ledger
Loading source directory links
Loading share composer
Loading topic controls
Loading related stories