Tasks 3.1 and 3.3 of novox/hq ADR 0116. One fixture directory, read by every implementation's own runner rather than copied into each — a fixture copied twice is two fixtures, and two fixtures drift. The README settles what ADR 0074's byte-for-byte can and cannot mean. The envelope is exact: the subject, the required headers, each name and format, because those are what two implementations get wrong invisibly. The body is not: it is the module's payload, and Go sorts a map's keys where JavaScript keeps insertion order, so demanding identical bytes would commit every implementation to a canonical JSON encoder to buy a property the mesh never uses. Said plainly, because read strictly it would have sent somebody writing one.
Conformance fixtures
What two implementations of the mesh's module protocol may not disagree about (novox/hq ADR 0074, design 19). A fixture is data, not prose: every implementation produces it and consumes it, and an implementation that passes the fixtures for a capability claims that capability.
What "byte-for-byte" means, and what it cannot
ADR 0074 says the fixtures must match byte for byte. Taken literally that is more than the mesh needs and more than two languages can give:
- The envelope is exact. The subject, the set of required headers, each header's name, and the format of each value. This is what an implementation can get wrong in a way that makes two meshes silently ignore each other, so this is what is pinned.
- The body is not. It is the module's own payload, opaque to the mesh, and its serialisation
is the language's. Go's
encoding/jsonsorts a map's keys; JavaScript'sJSON.stringifykeeps insertion order. Demanding identical bytes there would mean committing every implementation to a canonical JSON encoder — a large promise, bought for a property the mesh never uses. The fixture pins that the body round-trips: what goes in comes out equal.
So: exact where disagreement is invisible, semantic where it is not. Stated here because "byte-for-byte" read strictly would have sent somebody implementing a canonical encoder.
Running them
The TypeScript implementation: node conformance/run.mjs (against a NATS server; see the file).
The Go implementations read this directory by sibling path, the way the lab finds its siblings.
Layout
events/ one emitted event, and what it must look like on the wire