2

I want to calculate git SHA hash without using the git hash object function, that is I want to use the shasum function to calculate it.

I know that for the following case

    body="tree 491e9405120eaaa57cce3938fd38508d85a5e08b 
parent 8550f0f1a7e32fb1bb0933b0294c116a8dbe6dce 
author user <me@example.com> 1390718030 +0000 
committer user <me@example.com> 1390718030 +0000 
This is a test"

echo $body | git hash-object -w --stdin #755481b921f13bcfd731d74287a0c5847519ee81

l=`expr ${#body} + 1`
echo -e 'blob $l\0$body' | shasum #755481b921f13bcfd731d74287a0c5847519ee81

hashes are the same. But if I use -t commit option in hash-object I get a different Hash. How can I calculate the commit hash using shasum?

git hash-object -t commit --stdin <<< "$body" #b4c45adbbe35d3d3c73de48d039a8e3038f5ec54
Ram G Athreya
  • 4,892
  • 6
  • 25
  • 57

1 Answers1

2

You changed the type of the object you wrote the hash with.
From git hash-object

-t <type>

    Specify the type (default: "blob").

You went from the default blob to commit.

And the object actually written start with the object type, which is part of what the sha1 has to compute.
See:

Git calculates the SHA1 for a file (or, in Git terms, a "blob"):

sha1("blob " + filesize + "\0" + data)

That changes the content of what is taken into account by the sha1.
With -t commit, you modify that prefix (it is no longer 'blob'), and since the content is different, the sha1 is also different.

You can do a:

python -c "import zlib,sys;print repr(zlib.decompress(sys.stdin.read()))" < .git/objects/02/b365d4af3ef6f74b0b1f18c41507c82b3ee571: 

The first word will be the type of the content

For further reference check How Git Works

VonC
  • 1,262,500
  • 529
  • 4,410
  • 5,250
  • Ok. Is there a way to find out what that content will be so that I can do it with SHA1??? That is make it work for the commit option as well by adding the additional content? – Ram G Athreya Jan 26 '14 at 09:08
  • @RamGAthreya as shown in http://slidetocode.com/2013/08/25/how-git-works/, you can do a: `python -c "import zlib,sys;print repr(zlib.decompress(sys.stdin.read()))" < .git/objects/02/b365d4af3ef6f74b0b1f18c41507c82b3ee571`: the first word will be the type of the content. – VonC Jan 26 '14 at 10:33
  • @RamGAthreya I have included your edit (http://stackoverflow.com/review/suggested-edits/3905058) which was incorrectly rejected. – VonC Jan 27 '14 at 06:40
  • Yea I think the final link really nails most of how the internals work which was very interesting read. Thanks for the link – Ram G Athreya Jan 27 '14 at 06:43
  • @matt Thank you for the feedback. I have restored the last link in this answer. – VonC Jan 12 '23 at 06:45