Swift target
Use the Swift target for Apple-platform apps and Swift services that need generated model types with JSON/YAML load and save helpers. Typra emits a ready-to-build SwiftPM package.
emit-targets: - type: Swift output-dir: "generated/swift" test-dir: "generated/swift/tests" package-name: "TypraFixtures" protocol-scaffolds: "compile-only"| Option | Why it matters |
|---|---|
output-dir | Where the generated SwiftPM package is written. |
test-dir | Where generated Swift tests are written (enables the test target). |
package-name | Swift module and package name. Defaults to the root namespace when unset. |
format | Boolean toggle (default true). Runs swiftformat on emitted files when available. |
protocol-scaffolds | Emits compile-only test scaffolds for generated protocols. |
native-serialization | Defaults to none. Set to codable to emit explicit Typra-backed Codable conformance for generated models. |
Swift does not use import-path, namespace, or enum-parsing.
Generated surface
Section titled “Generated surface”Typra emits a complete SwiftPM package:
- A
Package.swiftmanifest targetingswift-tools-version5.9, platforms macOS 12 and iOS 15, with a Yams dependency (from: "5.1.3") for YAML support. - One Swift source file per model under
Sources/<Module>/, plus a sharedTypraRuntime.swift. - Generated
XCTestfiles underTests/<Module>Tests/whentest-diris set.
Every generated model conforms to the TypraModel protocol and exposes the same helper set:
public struct FixtureRoot: TypraModel { public var name: String = "" public var description: String? = nil public var tags: [String] = [] public var owner: FixtureOwner = FixtureOwner()
public static func load(_ data: Any, context: LoadContext = LoadContext()) throws -> FixtureRoot { /* ... */ } public func save(_ context: SaveContext = SaveContext()) throws -> [String: Any] { /* ... */ }
public static func fromJSON(_ json: String, context: LoadContext = LoadContext()) throws -> FixtureRoot { /* ... */ } public func toJSON(_ context: SaveContext = SaveContext()) throws -> String { /* ... */ } public static func fromYAML(_ yaml: String, context: LoadContext = LoadContext()) throws -> FixtureRoot { /* ... */ } public func toYAML(_ context: SaveContext = SaveContext()) throws -> String { /* ... */ }}Typical usage shape
Section titled “Typical usage shape”import TypraFixtures
let root = try FixtureRoot.fromJSON(jsonText)let saved = try root.toJSON()Load and save also accept already-parsed values through load(_:) and save(_:), so you can bridge from other decoders without re-serializing to text.
Native Codable mode
Section titled “Native Codable mode”Set native-serialization: "codable" to make generated Swift models conform to Codable. The conformance is explicit and delegates through Typra load and save, so JSONEncoder and JSONDecoder follow the same wire names, discriminator dispatch, raw fallback preservation, defaults, and optional omission rules as the normal Typra path instead of relying on synthesized Swift behavior.
Scalar coercion
Section titled “Scalar coercion”Models with a @@coerce rule accept scalar shorthand directly. The generated load and fromJSON helpers detect a scalar input and expand it into the object shape:
let reference = try FixtureReference.fromJSON("\"ref-coerced\"")// reference.id == "ref-coerced", reference.label == "coerced reference"Factories and polymorphism
Section titled “Factories and polymorphism”@@factory adds named constructors, and discriminated hierarchies lower to a Swift enum with associated values:
let named = FixtureReference.named(id: "ref-1", label: "Primary")
let content = try FixtureContent.fromJSON(payload)switch content {case .textContent(let text): print(text.text)case .imageContent(let image): print(image.url)case .unknown(let raw): print(raw)}Provider wire names
Section titled “Provider wire names”@@knownAs mappings emit a toWire(_:) helper that renames canonical fields for a target provider:
let wire = try options.toWire("openai")// maxOutputTokens is emitted as "max_completion_tokens"Callable stubs
Section titled “Callable stubs”TypeSpec-native interface/op callables emit throwing stubs that must be
completed by hand-authored extension code. Operation decorators such as @sync
shape the emitted Swift signature. Until implemented, stubs throw
TypraRuntimeError.unsupported, so generated code compiles while keeping domain
behavior in the consuming app.
Validation coverage
Section titled “Validation coverage”Swift generation is part of the fixture suite. When a Swift toolchain is available, fixture validation runs swift build and swift test against the generated package. If Swift is unavailable, the Swift checks skip with a warning unless CI_SWIFT_REQUIRED=1 is set, which promotes a missing toolchain to a hard failure.
npm run generate:fixtures --workspace @typra/emitternpm run validate:fixtures --workspace @typra/emitter