Git and version control
Version control is a time machine for your files: every snapshot saved, nothing truly lost, and a clean way to work with others. Git is the one almost everyone uses. Here is the practical core, minus the folklore.
What version control is
Version control records the history of your project as a series of snapshots. Instead of final_v2_REALfinal.zip,
you get one folder with a complete, navigable timeline: see what changed and when, undo back to any point, and merge
work from several people without overwriting each other. Git is a distributed version control system,
meaning every copy of the project carries its full history, so you can work, commit, and review offline.
The mental model: four places your code lives
Almost everything in Git makes sense once you can picture four areas and the moves between them:
- Working tree, the actual files you edit.
- Staging area, a holding zone for the changes you want in your next snapshot. This in-between step is what trips up newcomers, and it is also what lets you commit some changes but not others.
- Local repository, the committed history on your machine.
- Remote, a shared copy (GitHub, GitLab) everyone pushes to and pulls from.
The everyday loop
Ninety percent of daily Git is one small cycle: edit, stage, commit, push.
git status # what changed, and what is staged git add file.js # stage one file for the next commit git add . # stage everything that changed git commit -m "message" # save a snapshot of the staged changes git push # send your commits to the remote (e.g. GitHub) git pull # fetch and merge everyone else's commits
A commit is one saved snapshot with a message describing the change. Good messages are the difference
between a history you can read and a wall of “stuff.” git push shares your commits;
git pull brings in everyone else’s.
Branches: work without breaking main
A branch is a parallel line of work. You branch off, build a feature in isolation, and merge it back when it is ready, so the main line always stays working. It is the core of how teams collaborate and how you try something risky without fear.
git switch -c new-feature # create a branch and move onto it # ...edit and commit on the branch, main stays untouched... git switch main # return to the main line git merge new-feature # fold the branch's work back into main
Which Git command does each job?
The gotchas that bite everyone
- .gitignore does not untrack what you already committed. Listing a file in
.gitignoreonly stops it being added in future. If you already committed.env, you must rungit rm --cached .envto stop tracking it (then commit). Add the ignore rule before the first commit. - Never commit secrets. Keys belong in
.env, and.envbelongs in.gitignorefrom day one. If a key ever lands in history, rotate it; removing it from the latest commit does not erase it from the past. - Merge conflicts are normal. When two people change the same lines, Git pauses and marks both versions for you to reconcile by hand. It is routine, not a disaster.
reset --hardandcheckout --discard work. They are the few Git commands that genuinely delete uncommitted changes. Pause before running them.
# .gitignore (one pattern per line) .env node_modules/ dist/
Why this matters more in the AI era
AI coding agents make many changes quickly, and occasionally the wrong ones. Git is your undo button and your safety net: commit before you let an agent loose, review its changes as a diff, and you can always roll back to a known-good snapshot. A clean commit you can return to is what makes it safe to move fast with AI-assisted coding and an agentic setup.