Conformance

How Connect-Ktor tracks the Connect protocol conformance suite.

Conformance

Connect-Ktor runs the official connectrpc/conformance suite against a dedicated server under conformance/. The matrix below is the contract: ✅ means exercised and expected to pass (aside from pinned known-failing / known-flaky cases).

What each axis means is defined by the Connect protocol and the conformance project — this page only records how far connect-ktor implements them.

Support matrix

FeatureOptionCIONetty
ProtocolPROTOCOL_CONNECT✅✅
PROTOCOL_GRPC❌❌
PROTOCOL_GRPC_WEB❌❌
HTTP versionHTTP_VERSION_1✅✅
HTTP_VERSION_2❌✅
HTTP_VERSION_3❌❌
CodecCODEC_PROTO✅✅
CODEC_JSON✅✅
CompressionCOMPRESSION_IDENTITY✅✅
COMPRESSION_GZIP✅✅
BR / ZSTD / DEFLATE / SNAPPY❌❌
Stream typeUnary✅✅
Client stream✅✅
Server stream✅✅
Half-duplex bidi✅✅
Full-duplex bidi (HTTP/2)❌✅
TLSTLS❌✅
mTLS❌✅
TrailersUnary trailers + streaming end-frame metadata✅✅
Connect GETIdempotent unary GET✅*✅
Message receive limitUnary / streaming✅✅

* CIO passes Connect GET except cases that send duplicate request headers. CIO collapses those headers upstream — the same limitation as the Duplicate Metadata / Basic pins in conformance/known-failing-cio.txt.

Both engines currently fail gzip client-stream, server-stream, and bidi-stream cases because per-message streaming compression is unimplemented (pinned as known-failing / known-flaky). All streaming harness routes apply the requested per-message payload limit and pass the identity-compression Server Message Size cases. Unary routes use connectBodyLimit, which caps the whole request body. Streaming routes stay outside that plugin so envelope prefixes and other messages do not count toward the per-message limit, and full-duplex exchanges do not buffer until EOF. Generated streaming routes use a default 4 MiB per-message limit.

Engines

EngineNotes
CIOHTTP/1.1 plaintext only. No HTTPS, no HTTP/2. Prefer a TLS terminator in front if needed.
NettyHTTP/1.1 + HTTP/2 (h2c / h2), TLS, and mTLS. Prefer this when those matter.

Known-failing and known-flaky case lists are checked in as:

  • conformance/known-failing-cio.txt / known-failing-netty.txt
  • conformance/known-flaky-cio.txt / known-flaky-netty.txt

Run locally

mise run conformance

That builds :conformance, installs connectconformance, and runs the suite once per engine using config-<engine>.yaml plus the known-failing / known-flaky pins.

CI runs the same task on every pull request. When the matrix changes, update the table here and the pin files together — a green suite with a stale docs page is still a lie.