# Git Write a tree GoLang

**URL:** <https://forum.codecrafters.io/t/git-write-a-tree-golang/3742>\
**Category:** Challenges\
**Tags:** challenge:git\
**Created:** [December 27, 2024, 10:11pm UTC](https://forum.codecrafters.io/t/git-write-a-tree-golang/3742 "2024-12-27T22:11:41Z")\
**Posts on this page:** 5\
**Page:** 1

<div class="post-metadata">

**Author:** ![NotLucxs](https://yyz1.discourse-cdn.com/flex003/user_avatar/forum.codecrafters.io/notlucxs/32/3770_2.png) [@NotLucxs](https://forum.codecrafters.io/u/NotLucxs)\
**Post date:** [December 27, 2024, 10:11pm UTC](https://forum.codecrafters.io/t/git-write-a-tree-golang/3742/1 "2024-12-27T22:11:41Z")

</div>

I’m stuck on Stage Write a tree object

My hashed output is clearly wrong but looking at the examples I’m not sure where I’m going wrong

Here are my logs:

```auto
Expected (bytes 0-100), hexadecimal: | ASCII:
[tester::#FE4] 74 72 65 65 20 39 38 00 34 30 30 30 30 20 64 6f 6f 62 79 00 | tree 98.40000 dooby.
[tester::#FE4] d3 f5 e9 63 90 73 4c 7d f6 45 51 57 3d 39 4e 76 74 79 22 19| ...c.sL}.EQW=9Nvty".
[tester::#FE4] 31 30 30 36 34 34 20 68 6f 72 73 65 79 00 ad 53 ca 5b 29 5b | 100644 horsey..S.[)[
[tester::#FE4] 2a b8 16 6f a9 e5 7d 7e 1c 84 d0 da e1 85 34 30 30 30 30 20 | *..o..}~......40000 
[tester::#FE4] 79 69 6b 65 73 00 46 42 ce ab dd 64 3c df 12 ea 0d 63 d4 b4 | yikes.FB...d<....c..

[tester::#FE4] Actual (bytes 0-100), hexadecimal: | ASCII:
[tester::#FE4] 74 72 65 65 20 39 38 00 34 30 30 30 30 20 64 6f 6f 62 79 00 | tree 98.40000 dooby.
[tester::#FE4] e8 26 da a5 e8 80 85 a2 0f 7b 97 db 58 1f af 7d 9c 9c 5d 43| .&.......{..X..}..]C
[tester::#FE4] 31 30 30 36 34 34 20 68 6f 72 73 65 79 00 ad 53 ca 5b 29 5b | 100644 horsey..S.[)[
[tester::#FE4] 2a b8 16 6f a9 e5 7d 7e 1c 84 d0 da e1 85 34 30 30 30 30 20 | *..o..}~......40000 
[tester::#FE4] 79 69 6b 65 73 00 ad a5 98 70 4c 05 c3 54 4a b6 64 a0 7d b7 | yikes....pL..TJ.d.}.

```

And here’s a snippet of my code:

```golang
func writeTreeObject(location string) string {
	entries, _ := os.ReadDir(location)
	tree := ""
	for _, entry := range entries {
		if entry.Name() == ".git" {
			continue
		}
		if !entry.IsDir() {
			// This is a file
			hash := createGitObject(location + "/" + entry.Name())
			s := fmt.Sprintf("100644 %s\x00%s", entry.Name(), hash)
			tree += s
		} else {
			// This is a dir
			encodedHash := writeTreeObject(location + entry.Name())
			hash, _ := hex.DecodeString(encodedHash)
			s := fmt.Sprintf("40000 %s\x00%s", entry.Name(), hash)
			tree += s
		}
	}

	treeHeader := fmt.Sprintf("tree %d\x00", len(tree))
	encodedFilename := hex.EncodeToString(hashContents(tree))
	finalTree := []byte(treeHeader + tree)

	os.MkdirAll(".git/objects/"+encodedFilename[:2], os.ModePerm)
	path := fmt.Sprintf(".git/objects/%v/%v", encodedFilename[:2], encodedFilename[2:])

	var b bytes.Buffer
	w := zlib.NewWriter(&b)
	w.Write(finalTree)
	w.Close()

	os.WriteFile(path, b.Bytes(), 0777)
	return encodedFilename
}
func hashContents(contents string) []byte {
	h := sha1.New()
	h.Write([]byte(contents))

	return h.Sum(nil)
}

func createGitObject(filename string) []byte {
	data, err := os.ReadFile(filename)
	if err != nil {
		fmt.Println(err)
	}

	content := []byte("blob " + strconv.Itoa(len(data)) + "\x00" + string(data))

	// Get hash file name
	hashedFilename := hashContents(string(content))
	encodedFilename := hex.EncodeToString(hashedFilename)

	path := fmt.Sprintf(".git/objects/%v/%v", encodedFilename[:2], encodedFilename[2:])

	var b bytes.Buffer
	w := zlib.NewWriter(&b)
	w.Write(content)
	w.Close()

	os.MkdirAll(".git/objects/"+encodedFilename[:2], os.ModePerm)

	err = os.WriteFile(path, b.Bytes(), 0777)

	if err != nil {
		fmt.Println(err)
	}

	return hashedFilename
}

```

---

<div class="post-metadata">

**Author:** ![andy1li](https://yyz1.discourse-cdn.com/flex003/user_avatar/forum.codecrafters.io/andy1li/32/10_2.png) [@andy1li](https://forum.codecrafters.io/u/andy1li)\
**Post date:** [December 27, 2024, 11:02pm UTC](https://forum.codecrafters.io/t/git-write-a-tree-golang/3742/2 "2024-12-27T23:02:23Z")

</div>

I’ll take a look shortly.

---

<div class="post-metadata">

**Author:** ![andy1li](https://yyz1.discourse-cdn.com/flex003/user_avatar/forum.codecrafters.io/andy1li/32/10_2.png) [@andy1li](https://forum.codecrafters.io/u/andy1li)\
**Post date:** [December 28, 2024, 3:18am UTC](https://forum.codecrafters.io/t/git-write-a-tree-golang/3742/3 "2024-12-28T03:18:14Z")

</div>

Hi @NotLucxs, the bug is here:

```auto
func writeTreeObject(location string) string {
	...

	firstLine := fmt.Sprintf("tree %d\x00", len(tree))
	encodedFilename := hex.EncodeToString(hashContents(tree))
	finalTree := []byte(firstLine + tree)

```

The hash should be computed from `finalTree` instead of `tree`.

---

<div class="post-metadata">

**Author:** ![NotLucxs](https://yyz1.discourse-cdn.com/flex003/user_avatar/forum.codecrafters.io/notlucxs/32/3770_2.png) [@NotLucxs](https://forum.codecrafters.io/u/NotLucxs)\
**Post date:** [December 28, 2024, 7:38pm UTC](https://forum.codecrafters.io/t/git-write-a-tree-golang/3742/4 "2024-12-28T19:38:43Z")

</div>

Hi @andy1li  
Thank you!  
I had a feeling something simple was escaping me, a good spot from you

---

<div class="post-metadata">

**Author:** ![system](https://canada1.discourse-cdn.com/flex003/uploads/codecrafters/original/3X/7/0/700657133935c15703e22c7c8870394f6e6dc27d.svg) [@system](https://forum.codecrafters.io/u/system)\
**Post date:** [January 2, 2025, 7:39pm UTC](https://forum.codecrafters.io/t/git-write-a-tree-golang/3742/5 "2025-01-02T19:39:25Z")

</div>

Closed on January 2, 2025, 7:39pm UTC

This topic was automatically closed 5 days after the last reply. New replies are no longer allowed.
