如何获取Git待提交Commit的哈希值(而非HEAD)?
Great question—this is a common gotcha with Git, and the short answer is: you can't directly get the final commit hash before creating the commit, and here's why:
Git calculates commit hashes based on the full content of the commit object, which includes:
- The tree hash (representing all staged files, including your
VERSIONfile) - The parent commit hash
- Author/committer metadata (name, email, timestamp)
- Your commit message
Since your VERSION file is supposed to contain the commit's own hash, you end up with a circular dependency: the commit hash depends on VERSION's content, but VERSION's content depends on the commit hash. Git can't compute that hash until the commit (and its included VERSION file) exists.
That said, there are a few workarounds to achieve what you want:
Workaround 1: Commit first, then update VERSION and amend the commit
This is the most straightforward way to get the correct hash into your VERSION file without extra tooling:
- Stage all your files (including a placeholder
VERSIONif needed) and make an initial commit:git add . git commit -m 'updated version' - Grab the hash of this new commit and write it to
VERSION:git rev-parse HEAD > VERSION - Stage the updated
VERSIONfile and amend your commit (this replaces the initial commit with a new one that includes the correct hash):git add VERSION git commit --amend --no-edit - Push the amended commit (note: if you've already pushed the initial commit, you'll need to force push with
git push --force, which can disrupt collaborators—only do this if you're working on a feature branch that no one else is using):git push
The final commit will have its own hash stored in VERSION, since the amend operation creates a new commit that includes the updated file.
Workaround 2: Generate VERSION at build/publish time (don't commit it)
If you only need the VERSION file for built artifacts (not for tracking in Git), skip committing it entirely. Instead, generate it as part of your build or release process:
For example, in a Makefile, CI pipeline, or build script:
# Generate VERSION with the current commit hash git rev-parse HEAD > VERSION # Include VERSION in your build output # ... rest of your build steps ...
You can add VERSION to your .gitignore to avoid accidentally committing it. This avoids the circular dependency entirely, since the hash is only computed after the commit exists (when you run the build).
Workaround 3: Use git describe for human-readable version strings
If you don't need the full raw commit hash, git describe generates a more user-friendly version string based on your tags and commit history. For example, it might output something like v1.2.3-5-gabc123 (meaning 5 commits after tag v1.2.3, with short hash abc123).
You can write this to VERSION and commit it without circular issues:
git describe --tags > VERSION git add VERSION git commit -m 'updated version' git push
This works because the git describe output depends on existing tags and commits, not the commit you're about to create. It's a great option if you want version information that's more meaningful than a raw hash.
内容的提问来源于stack exchange,提问作者christophmegusta

