In Git, how do git add -A, git add -u, and git add . differ?
answer
- two questions, not three commands
- one of them never adds new files
- one of them cares where you are standing
- deletions count as changes in modern Git
basics
~20 sIn modern Git, add -A stages new, modified and deleted paths across the whole working tree; add -u stages modifications and deletions for already-tracked paths only, never new files; add . does what -A does but limited to the current directory and below.
solid answer
~50 sAll three stage changes; they differ on **scope** and on **whether untracked files count**. - `git add -A` (`--all`) stages every change in the whole working tree, regardless of your current directory: new files, modified files and deletions. - `git add -u` (`--update`) restricts itself to paths Git already tracks. Modifications and deletions are staged; brand-new untracked files are ignored. It is the safe choice when your tree contains build output you have not ignored yet. - `git add .` passes the pathspec `.`, meaning the current directory and everything under it. Within that subtree it behaves like `-A`, staging new, modified and deleted paths alike. So the real contrast is `-u` versus the other two on untracked files, and `.` versus `-A` on directory scope. You can combine them: `git add -A .` limits the all-changes behaviour to the current subtree.
code
console · 8 lines$ cd src
$ git status --short
M src/app.js
D docs/old.md
?? src/scratch.txt
$ git add . # stages src/app.js and src/scratch.txt only
$ git add -u # stages tracked edits and docs/old.md, no scratch.txt
$ git add -A # stages all three, from anywhere in the treego deeper
Be able to state the two differences crisply: -u never stages untracked files, and . is limited to the current directory while -A covers the whole tree.
Explain the two axes (untracked-or-not, scope) and the Git 2.0 change to deletion handling, and show that you check git status --short before any blanket add.
Demonstrate the habit behind the command: blanket adds only after the untracked list is clean, ignore rules fixed at the source, and mixed work split rather than swept into one commit.
Own the guardrails — ignore rules, secret scanning before push, and review norms — so an accidental blanket add is caught by process rather than by an individual's vigilance.
## Two independent axes Candidates usually memorise three commands and get them confused because they are really two questions asked at once. **Axis one — do untracked files count?** `-u` says no: only paths that already have an index entry are considered, so modifications and deletions are staged and a newly created file is left alone. `-A` and a plain pathspec both say yes: new files are added along with everything else. **Axis two — how much of the tree?** `-A` with no pathspec covers the entire working tree no matter where you are standing. `.` is a pathspec meaning the current directory and below, so running it from a subdirectory quietly ignores changes elsewhere in the repository. `-u` with no pathspec also covers the whole tree in modern Git. Once you see the two axes, the combinations are obvious: `git add -A .` is all-changes limited to this subtree, and `git add -u src/` is tracked-only limited to `src/`. ## The deletion trap and its history The classic confusion is whether these commands notice a file you deleted with `rm`. In Git 2.x they all do within their scope — a deletion is just another change to stage. This was not always true: older Git treated `git add .` as "add and update", silently skipping removals, which is why so much folklore still insists you must use `-A`. If you find advice claiming `git add .` misses deletions, it predates Git 2.0. Running against an old Git, or writing a script that must behave identically everywhere, is the one case where spelling out `git add -A` is worth the keystrokes. ## Choosing in practice Blanket staging is convenient and occasionally embarrassing. Two habits keep it safe. First, run `git status --short` before any blanket add and read the `??` lines. Those are the untracked files that `-A` and `.` will sweep in — a `node_modules` directory, a local dump file, an editor scratch file. If you see them, fix the ignore rules rather than reaching for `-u` as a workaround; `-u` hides the problem from this commit but not from the next person. Second, remember that these commands say nothing about what *belongs* in the commit. Staging everything at once is the opposite of composing a commit: it produces a diff with several intents in it, which reviewers and later bisects both pay for. For a mixed working tree, hunk-level staging is the tool; blanket adds are for when you have already checked that everything on the list is one change. ## Related spellings `git commit -a` is roughly `git add -u` followed by a commit — tracked modifications and deletions only, no new files. That is why a new file you forgot to add keeps missing your commits. Pathspec magic gives finer control: `git add :/` stages from the repository root regardless of your current directory, and `git add ':(exclude)*.log'` stages everything but the matching paths. Both are useful when a blanket add is nearly right but not quite.
- Does git add . stage a file you deleted with rm?Yes, in Git 2.x — provided the deleted path is inside the current directory subtree. A deletion is just another change to that path. Older Git skipped removals for a plain pathspec, which is the origin of the widespread advice to always use -A; that advice predates Git 2.0.
- What does git commit -a stage, and why does it keep missing your new files?It stages modifications and deletions for already-tracked paths, roughly `git add -u` followed by a commit. Untracked files have no index entry, so they are never included and a newly created file silently misses every commit until you `git add` it explicitly once.
- You are in a subdirectory and want to stage everything in the repository. What do you run?`git add -A` with no pathspec covers the whole working tree from anywhere, and `git add :/` does the same by naming the repository root as the pathspec. Plain `git add .` would stage only the current directory and below.
saying these in an interview costs you the question
- Says git add . still ignores deletions in modern Git
- Thinks -u also picks up brand-new files
- Believes -A and . differ on deletions rather than scope
- Cannot say what changes when run from a subdirectory