RustToMetal opened a new pull request, #4355: URL: https://github.com/apache/iggy/pull/4355
The protocol layer: the consensus frame every request and reply travels in, the session state that hands out request ids, one request encoder per command code, one reply decoder per reply shape, and the message batch format that send bodies and poll replies share. Nothing here opens a socket; the TCP and TLS client that drives this layer is the next PR. Fourth of nine stacked PRs for the Swift SDK; builds on #4190, #4306, and #4335. ## Which issue does this PR address? Relates to #4001 ## Rationale The client, producer, and consumer are thin over this layer, and the wire rules are the part most likely to diverge from the server. Landing them on their own lets every header, encoder, and decoder be reviewed next to the golden vector the Rust crates produced for it, before any networking is involved. ## What changed? `VSRFrame` ports `core/binary_protocol/src/consensus/header.rs`: the 256-byte header offsets, the command and eviction discriminants, `encodeRequest` (which stamps the request checksum for the operations the server's client table deduplicates and leaves it zero for partition and non-replicated operations, like the Rust SDK), and `decodeReply`, which applies the fixed order of frame discriminant, declared size, pre-commit denial status, then the committed result section. Eviction reasons map to the same errors as `eviction_reason_to_error` in `core/common`. `ConsensusSession` ports `core/sdk/src/session.rs`: an ephemeral client id, the session fence, and monotonic request ids for replicated operations. `ConsensusOperation` and `CommandCode` mirror the Rust enums, with the metadata, partition, and result-framed bands. `Requests` has one encoder per command, with the username, password, and name bounds applied before encoding so a length prefix can never desync. `Responses` has one decoder per reply shape, mapping codec failures to `invalidCommand` like the Rust client. `Batch` ports `batch.rs`: the 256-byte batch header, the 48-byte message frame, and the XXH3 checksums over frames and batch. Every length read from the wire is bounded as a `UInt32` before it becomes an `Int` (frame size, result-section count, prefixed blocks, message payload and header lengths), so a hostile frame cannot trap a 32-bit platform. The byte codec gains the helpers this layer needs: `readPrefixedBytes`, `skip`, `rest`, `writeZeros`, `overwrite`, and the checksum error cases with their `IggyError` mapping. Tests: `WireVectorTests` compares every request encoder and consensus header against the Rust bytes in `golden.json`, `ResponseVectorTests` does the same for every reply decoder, and `ProtocolTests` covers the session rules, result-section handling, denial ordering, duplicate sends, and eviction mapping. ## Local Execution - Passed: `swift build -Xswiftc -warnings-as-errors`, `swift test` (105 tests), `swift format lint --strict`, hawkeye license check - Pre-commit: `prek run --from-ref upstream/master --to-ref HEAD` passed ## AI Usage 1. **Which tools?** Claude Code (Claude). 2. **Scope of usage?** The port and the tests were drafted with it from `core/binary_protocol`, `core/sdk/src/vsr.rs`, and `core/sdk/src/session.rs` as the reference, reviewed and directed by me. 3. **How did you verify the generated code works correctly?** Every header, request, and reply is checked byte for byte against vectors the Rust crates produced, and the full chain was run end to end against a real `iggy-server` (35 end-to-end tests) plus the 9 BDD scenarios. 4. **Can you explain every line of the code if asked?** Yes. -- This is an automated message from the Apache Git Service. To respond to the message, please log on to GitHub and use the URL above to go to the specific comment. To unsubscribe, e-mail: [email protected] For queries about this service, please contact Infrastructure at: [email protected]
