ArkType
ArkType 2.1.28 and newer implements both Standard Schema and Standard JSON Schema on the type itself. Pass the type and nothing else.
import { type } from "arktype";import { decode, encode } from "@chichurita/shorn";
const Person = type({ name: "string", age: "number.integer >= 0", sex: "'M' | 'F' | 'X'",});
const person = { name: "Grace", age: 45, sex: "F" } as const;const bytes = encode(Person, person); // 8 bytesconst decoded = decode(Person, bytes);An equivalent Zod schema produces the same bytes and the same fingerprint. Use "number.integer >= 0" wherever a value cannot be negative: a signed integer uses ZigZag encoding and needs an extra byte at half the value an unsigned one would. Supported types maps every ArkType shape to its bytes.
Extra properties
Section titled “Extra properties”ArkType objects are open by default. Unknown properties pass validation, and ArkType does not emit additionalProperties: false, so shorn checks for extras during encoding and rejects them rather than dropping data. The codec itself still builds.
| Type | { name: "Grace", extra: true } |
|---|---|
type({ name: "string" }) | shorn throws Unknown object property "extra" |
type({ name: "string", "+": "delete" }) | encodes; ArkType strips extra |
type({ name: "string", "+": "reject" }) | ArkType throws extra must be removed |
Use "+": "delete" to strip extras you expect, or "+": "reject" to get ArkType’s own validation error. Leaving the object open works too, since shorn rejects the extras itself.
The fingerprint leaves out rejectUnknown, so equivalent ArkType and Zod schemas still agree even though they handle extra properties differently.
Rich types
Section titled “Rich types”Date and bigint encode natively:
const Event = type({ when: "Date", id: "bigint" });const codec = compile(Event); // 6 bytes for the DateJSON Schema has no keyword for either, so shorn’s conversion hook writes its own x-shorn keyword for them during ArkType’s conversion. An equivalent Zod schema produces the same bytes and the same fingerprint.
Set and Map are refused:
ArkType's Set carries no element type, so there is nothing to encode itsmembers as; convert it at the edgeBoth are keywords in ArkType, and neither says what type its members have. A format without type tags has nothing to write the members as, and encoding them as empty containers would silently drop data. Zod’s z.set(T) and Valibot’s v.set(T) name the element type and are supported. Any other prototype is refused too, as RegExp cannot be represented in JSON Schema.
ArkType has no format: "date-time" spelling either. "string.date.iso" converts to a pattern, so an ISO timestamp stays an ordinary string rather than becoming the 6 bytes z.iso.datetime() gets.
A morph is refused when its input and output produce different wire shapes, because shorn needs both sides to agree on the bytes. Standard Schema has no reverse operation, so shorn cannot run a morph backwards; see Date, BigInt, Map, Set.
Minimum version
Section titled “Minimum version”2.1.28 is the minimum. Earlier versions lack Standard JSON Schema, so encode throws provides validation but not structure. On those versions, pass the structure argument.