ref: 98e5a64ce72e81dcede7dbebc74e22576a1f5ab8
parent: b3b2d5057a55baf88cbaaa31234edd3fe5d30e7f
author: Runxi Yu <me@runxiyu.org>
date: Fri Feb 20 17:22:56 EST 2026
object: Use objectheader
--- a/object/blob_serialize.go
+++ b/object/blob_serialize.go
@@ -1,15 +1,27 @@
package object
-import "codeberg.org/lindenii/furgit/objecttype"
+import (
+ "codeberg.org/lindenii/furgit/internal/objectheader"
+ "codeberg.org/lindenii/furgit/objecttype"
+)
-// Serialize renders the raw object (header + body).
-func (blob *Blob) Serialize() ([]byte, error) {- header, err := headerForType(objecttype.TypeBlob, blob.Data)
+// SerializeWithoutHeader renders the raw blob body bytes.
+func (blob *Blob) SerializeWithoutHeader() ([]byte, error) {+ return append([]byte(nil), blob.Data...), nil
+}
+
+// SerializeWithHeader renders the raw object (header + body).
+func (blob *Blob) SerializeWithHeader() ([]byte, error) {+ body, err := blob.SerializeWithoutHeader()
if err != nil {return nil, err
}
- raw := make([]byte, len(header)+len(blob.Data))
+ header, ok := objectheader.Encode(objecttype.TypeBlob, int64(len(body)))
+ if !ok {+ return nil, ErrInvalidObject
+ }
+ raw := make([]byte, len(header)+len(body))
copy(raw, header)
- copy(raw[len(header):], blob.Data)
+ copy(raw[len(header):], body)
return raw, nil
}
--- a/object/blob_serialize_test.go
+++ b/object/blob_serialize_test.go
@@ -15,9 +15,9 @@
wantID := repo.HashObject(t, "blob", body)
blob := &object.Blob{Data: body}- rawObj, err := blob.Serialize()
+ rawObj, err := blob.SerializeWithHeader()
if err != nil {- t.Fatalf("Serialize: %v", err)+ t.Fatalf("SerializeWithHeader: %v", err)}
gotID := algo.Sum(rawObj)
if gotID != wantID {--- a/object/commit_serialize.go
+++ b/object/commit_serialize.go
@@ -4,10 +4,12 @@
"bytes"
"fmt"
+ "codeberg.org/lindenii/furgit/internal/objectheader"
"codeberg.org/lindenii/furgit/objecttype"
)
-func (commit *Commit) serialize() ([]byte, error) {+// SerializeWithoutHeader renders the raw commit body bytes.
+func (commit *Commit) SerializeWithoutHeader() ([]byte, error) {var buf bytes.Buffer
if commit.Tree.Size() == 0 {@@ -54,15 +56,15 @@
return buf.Bytes(), nil
}
-// Serialize renders the raw object (header + body).
-func (commit *Commit) Serialize() ([]byte, error) {- body, err := commit.serialize()
+// SerializeWithHeader renders the raw object (header + body).
+func (commit *Commit) SerializeWithHeader() ([]byte, error) {+ body, err := commit.SerializeWithoutHeader()
if err != nil {return nil, err
}
- header, err := headerForType(objecttype.TypeCommit, body)
- if err != nil {- return nil, err
+ header, ok := objectheader.Encode(objecttype.TypeCommit, int64(len(body)))
+ if !ok {+ return nil, ErrInvalidObject
}
raw := make([]byte, len(header)+len(body))
copy(raw, header)
--- a/object/commit_serialize_test.go
+++ b/object/commit_serialize_test.go
@@ -19,9 +19,9 @@
t.Fatalf("ParseCommit: %v", err)}
- rawObj, err := commit.Serialize()
+ rawObj, err := commit.SerializeWithHeader()
if err != nil {- t.Fatalf("Serialize: %v", err)+ t.Fatalf("SerializeWithHeader: %v", err)}
gotID := algo.Sum(rawObj)
if gotID != commitID {--- a/object/object.go
+++ b/object/object.go
@@ -2,9 +2,7 @@
package object
import (
- "bytes"
"errors"
- "strconv"
"codeberg.org/lindenii/furgit/objecttype"
)
@@ -19,20 +17,6 @@
// Object is a Git object that can serialize itself.
type Object interface {ObjectType() objecttype.Type
- Serialize() ([]byte, error)
-}
-
-func headerForType(ty objecttype.Type, body []byte) ([]byte, error) {- tyStr, ok := objecttype.Name(ty)
- if !ok {- return nil, ErrInvalidObject
- }
- size := strconv.Itoa(len(body))
- var buf bytes.Buffer
- buf.Grow(len(tyStr) + len(size) + 2)
- buf.WriteString(tyStr)
- buf.WriteByte(' ')- buf.WriteString(size)
- buf.WriteByte(0)
- return buf.Bytes(), nil
+ SerializeWithoutHeader() ([]byte, error)
+ SerializeWithHeader() ([]byte, error)
}
--- a/object/tag_serialize.go
+++ b/object/tag_serialize.go
@@ -4,10 +4,12 @@
"bytes"
"fmt"
+ "codeberg.org/lindenii/furgit/internal/objectheader"
"codeberg.org/lindenii/furgit/objecttype"
)
-func (tag *Tag) serialize() ([]byte, error) {+// SerializeWithoutHeader renders the raw tag body bytes.
+func (tag *Tag) SerializeWithoutHeader() ([]byte, error) { if tag.Target.Size() == 0 {return nil, ErrInvalidObject
}
@@ -42,15 +44,15 @@
return buf.Bytes(), nil
}
-// Serialize renders the raw object (header + body).
-func (tag *Tag) Serialize() ([]byte, error) {- body, err := tag.serialize()
+// SerializeWithHeader renders the raw object (header + body).
+func (tag *Tag) SerializeWithHeader() ([]byte, error) {+ body, err := tag.SerializeWithoutHeader()
if err != nil {return nil, err
}
- header, err := headerForType(objecttype.TypeTag, body)
- if err != nil {- return nil, err
+ header, ok := objectheader.Encode(objecttype.TypeTag, int64(len(body)))
+ if !ok {+ return nil, ErrInvalidObject
}
raw := make([]byte, len(header)+len(body))
copy(raw, header)
--- a/object/tag_serialize_test.go
+++ b/object/tag_serialize_test.go
@@ -20,9 +20,9 @@
t.Fatalf("ParseTag: %v", err)}
- rawObj, err := tag.Serialize()
+ rawObj, err := tag.SerializeWithHeader()
if err != nil {- t.Fatalf("Serialize: %v", err)+ t.Fatalf("SerializeWithHeader: %v", err)}
gotID := algo.Sum(rawObj)
if gotID != tagID {--- a/object/tree_serialize.go
+++ b/object/tree_serialize.go
@@ -3,10 +3,12 @@
import (
"strconv"
+ "codeberg.org/lindenii/furgit/internal/objectheader"
"codeberg.org/lindenii/furgit/objecttype"
)
-func (tree *Tree) serialize() []byte {+// SerializeWithoutHeader renders the raw tree body bytes.
+func (tree *Tree) SerializeWithoutHeader() ([]byte, error) {var bodyLen int
for _, entry := range tree.Entries {mode := strconv.FormatUint(uint64(entry.Mode), 8)
@@ -27,15 +29,18 @@
pos += copy(body[pos:], id)
}
- return body
+ return body, nil
}
-// Serialize renders the raw object (header + body).
-func (tree *Tree) Serialize() ([]byte, error) {- body := tree.serialize()
- header, err := headerForType(objecttype.TypeTree, body)
+// SerializeWithHeader renders the raw object (header + body).
+func (tree *Tree) SerializeWithHeader() ([]byte, error) {+ body, err := tree.SerializeWithoutHeader()
if err != nil {return nil, err
+ }
+ header, ok := objectheader.Encode(objecttype.TypeTree, int64(len(body)))
+ if !ok {+ return nil, ErrInvalidObject
}
raw := make([]byte, len(header)+len(body))
copy(raw, header)
--- a/object/tree_serialize_test.go
+++ b/object/tree_serialize_test.go
@@ -48,9 +48,9 @@
wantTreeID := repo.Mktree(t, buildGitMktreeInput(tree.Entries))
- rawObj, err := tree.Serialize()
+ rawObj, err := tree.SerializeWithHeader()
if err != nil {- t.Fatalf("Serialize: %v", err)+ t.Fatalf("SerializeWithHeader: %v", err)}
gotTreeID := algo.Sum(rawObj)
if gotTreeID != wantTreeID {--
⑨