aboutsummaryrefslogtreecommitdiff
path: root/format/packfile/ingest/drain.go
diff options
context:
space:
mode:
authorGravatar Runxi Yu2026-03-26 09:17:14 +0000
committerGravatar Runxi Yu2026-03-26 09:18:30 +0000
commit3e884f5f3d42cbc4874a04da31dde10314b0cfad (patch)
treef5e1e325fd1a2a0801791c054010213214475d80 /format/packfile/ingest/drain.go
parentnetwork/receivepack: Rename from receivepack (diff)
signatureNo signature
format: Move commitgraph and packfile here
Diffstat (limited to 'format/packfile/ingest/drain.go')
-rw-r--r--format/packfile/ingest/drain.go68
1 files changed, 68 insertions, 0 deletions
diff --git a/format/packfile/ingest/drain.go b/format/packfile/ingest/drain.go
new file mode 100644
index 00000000..ed6ec821
--- /dev/null
+++ b/format/packfile/ingest/drain.go
@@ -0,0 +1,68 @@
+package ingest
+
+import (
+ "fmt"
+ "io"
+
+ "codeberg.org/lindenii/furgit/internal/compress/zlib"
+ objectheader "codeberg.org/lindenii/furgit/object/header"
+ objectid "codeberg.org/lindenii/furgit/object/id"
+ objecttype "codeberg.org/lindenii/furgit/object/type"
+ packfmt "codeberg.org/lindenii/furgit/format/packfile"
+)
+
+// drainEntryPayload inflates one entry payload from stream and returns
+// (inflatedLength, oidForBaseEntry).
+func drainEntryPayload(state *ingestState, record objectRecord) (int64, objectid.ObjectID, error) {
+ var zero objectid.ObjectID
+
+ reader, err := zlib.NewReader(state.stream)
+ if err != nil {
+ return 0, zero, &MalformedPackEntryError{Offset: record.offset, Reason: fmt.Sprintf("open zlib stream: %v", err)}
+ }
+
+ defer func() { _ = reader.Close() }()
+
+ var total int64
+
+ if packfmt.IsBaseObjectType(record.packedType) {
+ header, ok := objectheader.Encode(record.packedType, record.declaredSize)
+ if !ok {
+ return 0, zero, &MalformedPackEntryError{Offset: record.offset, Reason: "encode object header"}
+ }
+
+ hashImpl, err := state.algo.New()
+ if err != nil {
+ return 0, zero, err
+ }
+
+ _, _ = hashImpl.Write(header)
+
+ n, err := io.Copy(hashImpl, reader)
+ if err != nil {
+ return 0, zero, &MalformedPackEntryError{Offset: record.offset, Reason: fmt.Sprintf("inflate base object: %v", err)}
+ }
+
+ total = n
+
+ oid, err := objectid.FromBytes(state.algo, hashImpl.Sum(nil))
+ if err != nil {
+ return 0, zero, err
+ }
+
+ return total, oid, nil
+ }
+
+ if record.packedType == objecttype.TypeOfsDelta || record.packedType == objecttype.TypeRefDelta {
+ n, err := io.Copy(io.Discard, reader)
+ if err != nil {
+ return 0, zero, &MalformedPackEntryError{Offset: record.offset, Reason: fmt.Sprintf("inflate delta payload: %v", err)}
+ }
+
+ total = n
+
+ return total, zero, nil
+ }
+
+ return 0, zero, &MalformedPackEntryError{Offset: record.offset, Reason: "unsupported payload type"}
+}