To end the chapter with something you can read, we format a tree the way git cat-file -p does: mode, type, id, and name, one entry per line. This also surfaces where Git pads the mode for display.
Format a tree's entries as human-readable lines matching git cat-file -p.
Now the trees are readable. For display, Git pads the mode to six digits, so
the directory mode we store as 40000 prints as 040000, while 100644 is
already six digits and is unchanged. Note the split: the mode on disk (inside the
hashed tree body) has no leading zero, but the mode Git shows you does. Mixing
these up is a classic source of confusion, and pinning both keeps them straight.
The type is derived, not stored: an entry with mode 40000 points at a tree,
anything else at a blob. Lay it out as mode, type, id, a tab, then the name, and
you have reproduced git cat-file -p for trees. Run that command against your
root tree id and the output matches line for line, entries in the same sorted
order. That is the whole chapter proven at once: your trees are real Git trees.
// mode padded left with zeros to width 6; type from modetyp := "blob"if e.Mode == "40000" { typ = "tree" }line := fmt.Sprintf("%06s %s %s\t%s", e.Mode, typ, e.Id, e.Name)