Git backed by object storage because you can't stop me
git object-storage kefka
10

Configure Feed

Select the types of activity you want to include in your feed.

feat: add git upload-archive support

Signed-off-by: Xe Iaso <me@xeiaso.net>

Xe Iaso (May 27, 2026, 10:04 PM EDT) 645661a6 ca89e095

+9 -14
+9 -14
cmd/objgitd/daemon.go
··· 33 33 allowPush bool 34 34 } 35 35 36 - // plainStorer hides the underlying storer's PackfileWriter implementation. 37 - // 38 - // transport.ReceivePack stores an incoming pack via packfile.UpdateObjectStorage, 39 - // which has two paths: a storer.PackfileWriter fast-path that copies the client 40 - // stream to EOF, and a parser fallback that reads exactly one self-delimiting 41 - // pack. A git:// client keeps the socket open after its pack, waiting for 42 - // report-status, so it never sends EOF and the fast-path copy deadlocks. By not 43 - // advertising PackfileWriter we take the parser path, which stops at the pack 44 - // trailer. Objects land as loose objects rather than a packfile. 45 - type plainStorer struct { 46 - storage.Storer 47 - } 48 - 49 36 // Serve accepts connections on l until ctx is cancelled or Accept fails. 50 37 func (d *daemon) Serve(ctx context.Context, l net.Listener) error { 51 38 go func() { ··· 114 101 GitProtocol: gitProtocol, 115 102 }) 116 103 104 + case transport.UploadArchiveService: 105 + st, err := d.loader.Load(&url.URL{Path: req.Pathname}) 106 + if err != nil { 107 + _, _ = pktline.WriteError(conn, fmt.Errorf("repository %q not found", req.Pathname)) 108 + return fmt.Errorf("loading %q: %w", req.Pathname, err) 109 + } 110 + return transport.UploadArchive(ctx, st, r, conn, &transport.UploadArchiveRequest{}) 111 + 117 112 case transport.ReceivePackService: 118 113 if !d.allowPush { 119 114 _, _ = pktline.WriteError(conn, fmt.Errorf("push is disabled on this server")) ··· 124 119 _, _ = pktline.WriteError(conn, fmt.Errorf("cannot open repository %q", req.Pathname)) 125 120 return fmt.Errorf("opening %q for push: %w", req.Pathname, err) 126 121 } 127 - return transport.ReceivePack(ctx, plainStorer{st}, r, conn, &transport.ReceivePackRequest{ 122 + return transport.ReceivePack(ctx, st, r, conn, &transport.ReceivePackRequest{ 128 123 GitProtocol: gitProtocol, 129 124 }) 130 125