Git walked up the directory tree and found no .git. Wrong directory, a missing/bare .git, or HOME/ENV pointing elsewhere — three checks identify which.
The cwd is outside any directory containing .git. git rev-parse --show-toplevel (in the repo) vs pwd confirms. Subshells and scripts often cd elsewhere first — the classic silent killer.
Interrupted clones, partial restores, or a .git that's a gitdir-pointer file (worktrees/submodules) whose target moved. ls -la .git — a valid repo has HEAD, objects/, refs/; a pointer file must resolve.
Exported GIT_DIR from a previous command points git at a nonexistent repo. env | grep GIT finds it in seconds — cron/CI contexts often have stale env or different HOME.
pwd ; ls -a | head -5 ; git -C /path/to/repo status # -C targets the repo explicitly
ls .git/HEAD .git/objects .git/refs 2>&1 ; cat .git 2>/dev/null # pointer file for worktrees
env | grep -i '^GIT' ; unset GIT_DIR GIT_WORK_TREE
git init # in an existing repo dir with damaged .git: repairs structure (commits intact if objects survive)
git -C <path> sidesteps every 'wrong directory' failure in scripts: it errors explicitly instead of guessing from cwd. Re-init (git init) over a damaged repo is non-destructive: it rebuilds the metadata; whether data survived depends on .git/objects.
Check the .git dir still exists and you didn't move the whole tree (mv breaks relative worktree pointers). ls -a is faster than any theory — if .git is gone or gutted, restore from your remote/backup.
CI clones into a different path (or hasn't cloned yet) and may carry GIT_* env vars. Print pwd + env | grep GIT in the pipeline and compare to your local reality.
Our most-documented failures, packaged as ready-to-ship starter kits: Docker, Kubernetes, and Terraform.
Browse the template store →One-time. Yours to modify. Instant download from the NinjaOps template store.