Artifact 94a8cee17370f88ac21ed3f382fda20b7e918cc3193eb9fec1db5e689a44ba9d:
- File
internal/xfer/example_test.go
— part of check-in
[f1236bd031]
at
2026-07-23 13:54:08
on branch trunk
— xfer: select framing by Content-Type; bound clone rounds by client decode limit (#133)
* fix: select xfer framing by Content-Type (#106); bound clone rounds by the client's decode limit (#109)
seeing which parsed, which made a decompression failure indistinguishable from "wrong framing" (the root of #104). Select framing from the §4 Content-Type instead: application/x-fossil is the §4.1 compressed container, every other type (including application/x-fossil-uncompressed, used by clone-v3 replies) is plain card text — the same rule canonical fossil applies. Verified against fossil 2.28: pull replies arrive as the prefixed container, clone replies as plain text, and no reply is ever an unprefixed raw zlib stream. The former unprefixed-zlib framing, checked first on the unverified belief that fossil emits it, was removed along with the length-prefix/zlib-header aliasing guard that only existed to disambiguate the two compressed framings trial-dispatch conflated. A compressed body that fails to inflate is now reported as the fault it is, never re-fed to the card parser. xfer.Decode takes the Content-Type; byte-oriented callers with no header pass the compressed type explicitly.
crossing one whole, so a round carried budget + one whole artifact. When sub-budget filler preceded a large artifact, that sum exceeded what the client could decode (xfer.MaxDecompressedBytes) and the clone failed with a spurious "declared container length exceeds" error whose threshold depended on incidental filler size. The server now flushes the round and sends an over-bound artifact alone when adding it would cross the client's decode bound, so clonability is a property of the artifact alone. The 2*budget compile-time guard now certifies what it appears to.
* fix: reject unrecognized xfer Content-Type with 415 (#106)
A POST whose Content-Type was absent or unrecognized fell through to the plaintext card decoder, which is exactly the #104 failure shape: possibly- compressed binary fed to the card parser. Request bodies come from untrusted peers, so a body carrying no framing signal is rejected rather than guessed at. Real fossil always sets the header; no conforming peer is affected.
xfer.KnownContentType shares the media-type parsing with the framing check, so the server and Decode agree on what a type means.
Also runs the #109 filler subtests in parallel — serially they pushed internal/sync past the 120s per-package timeout CI uses. (user: [email protected], size: 789) [annotate] [blame] [check-ins using]
package xfer_test import ( "fmt" "github.com/danmestas/go-libfossil/internal/xfer" ) func ExampleMessage_Encode() { msg := &xfer.Message{ Cards: []xfer.Card{ &xfer.PushCard{ProjectCode: "abc123"}, &xfer.PullCard{ProjectCode: "abc123", ServerCode: "def456"}, &xfer.IGotCard{UUID: "aaf4c61ddcc5e8a2dabede0f3b482cd9aea9434d"}, }, } wire, err := msg.Encode() if err != nil { fmt.Println("error:", err) return } // Wire format is zlib-compressed xfer cards. fmt.Printf("compressed: %v\n", len(wire) > 0) // Decode round-trips back to a Message. decoded, err := xfer.Decode(wire, xfer.ContentTypeCompressed) if err != nil { fmt.Println("error:", err) return } fmt.Printf("cards: %d\n", len(decoded.Cards)) // Output: // compressed: true // cards: 3 }