@effected/schemastore 0.4.0 → 0.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/DocumentLint.js +2 -2
- package/KeywordFamilies.js +50 -9
- package/README.md +40 -11
- package/SchemaPipeline.js +91 -6
- package/SchemaValidator.js +8 -5
- package/SchemaVersioning.js +56 -0
- package/StoreDocument.js +61 -15
- package/index.d.ts +716 -540
- package/index.js +4 -5
- package/package.json +3 -3
- package/tsdoc-metadata.json +1 -1
- package/AnnotationCarriers.js +0 -137
package/index.d.ts
CHANGED
|
@@ -1,73 +1,4 @@
|
|
|
1
1
|
import { Context, Effect, FileSystem, Layer, Option, Order, Path, Result, Schema } from "effect";
|
|
2
|
-
//#region src/AnnotationCarriers.d.ts
|
|
3
|
-
declare const CarrierDepthExceededError_base: Schema.Class<CarrierDepthExceededError, Schema.TaggedStruct<"CarrierDepthExceededError", {
|
|
4
|
-
/** JSON pointer (in the lowered document's coordinates) where the cap was hit. */
|
|
5
|
-
readonly path: Schema.String;
|
|
6
|
-
/** The nesting cap that was exceeded. */
|
|
7
|
-
readonly maxDepth: Schema.Number;
|
|
8
|
-
}>, import("effect/Cause").YieldableError>;
|
|
9
|
-
/**
|
|
10
|
-
* Indicates that the carrier re-graft walk nested past the package's
|
|
11
|
-
* hardening cap (256 levels), which also intercepts cyclic inputs before
|
|
12
|
-
* they can recurse forever.
|
|
13
|
-
*
|
|
14
|
-
* Raised by {@link AnnotationCarriers.carry}.
|
|
15
|
-
*
|
|
16
|
-
* @public
|
|
17
|
-
*/
|
|
18
|
-
declare class CarrierDepthExceededError extends CarrierDepthExceededError_base {
|
|
19
|
-
get message(): string;
|
|
20
|
-
}
|
|
21
|
-
/**
|
|
22
|
-
* Re-grafts the declared non-standard keyword families
|
|
23
|
-
* ({@link KeywordFamilies}) from a Draft 2020-12 schema node onto its
|
|
24
|
-
* lowered Draft-07 counterpart.
|
|
25
|
-
*
|
|
26
|
-
* Why this exists: annotation keys admitted into the Draft 2020-12 document
|
|
27
|
-
* (core's `includeAnnotationKey`) are **dropped by core's Draft-07 lowering**,
|
|
28
|
-
* whose keyword walk copies a fixed subset — verified against the installed
|
|
29
|
-
* beta. Carrying `x-taplo`, `x-tombi-*`, `x-intellij-*` or the vscode set
|
|
30
|
-
* into an emitted SchemaStore document therefore requires this post-lowering
|
|
31
|
-
* step; it cannot ride `ToJsonSchemaOptions` alone.
|
|
32
|
-
*
|
|
33
|
-
* The walk mirrors the lowering's own structural rules, so every carrier
|
|
34
|
-
* lands on the node the annotation was attached to — including the one
|
|
35
|
-
* coordinate move the lowering makes (2020-12 `prefixItems[i]` → Draft-07
|
|
36
|
-
* `items[i]`, trailing `items` → `additionalItems`). Only declared-family
|
|
37
|
-
* keys are copied; nothing else about the target changes.
|
|
38
|
-
*
|
|
39
|
-
* `StoreDocument.fromSchema` applies this automatically to the root schema
|
|
40
|
-
* and every `$defs` pool entry — annotate a schema node
|
|
41
|
-
* (`Schema.String.annotate({ "x-taplo": { hidden: true } })`) and the key
|
|
42
|
-
* appears in the built document. Call this directly only when driving core's
|
|
43
|
-
* pipeline yourself.
|
|
44
|
-
*
|
|
45
|
-
* Know the boundary (core behavior, probed at the installed beta): an
|
|
46
|
-
* annotation must sit on the schema **definition** node. Annotating a
|
|
47
|
-
* hoisted (identifier-carrying) schema at its *usage* site — e.g.
|
|
48
|
-
* `Person.annotate({...})` inside a struct field — reaches neither the
|
|
49
|
-
* `$ref` node nor the pool entry, even in the 2020-12 document, so there is
|
|
50
|
-
* nothing to carry.
|
|
51
|
-
*
|
|
52
|
-
* @public
|
|
53
|
-
*/
|
|
54
|
-
declare class AnnotationCarriers {
|
|
55
|
-
private constructor();
|
|
56
|
-
/**
|
|
57
|
-
* Grafts declared-family keys from `source` (a Draft 2020-12 schema
|
|
58
|
-
* node) onto `target` (its lowered Draft-07 counterpart), returning a
|
|
59
|
-
* new node. Pure and synchronous — the primitive form;
|
|
60
|
-
* {@link AnnotationCarriers.carry} is the same walk behind a span.
|
|
61
|
-
*/
|
|
62
|
-
static carryResult(source: unknown, target: unknown): Result.Result<unknown, CarrierDepthExceededError>;
|
|
63
|
-
/**
|
|
64
|
-
* Effect form of {@link AnnotationCarriers.carryResult}, adding only the
|
|
65
|
-
* `AnnotationCarriers.carry` span. Defined in terms of the `Result`
|
|
66
|
-
* primitive — synchronous callers can use that variant directly.
|
|
67
|
-
*/
|
|
68
|
-
static readonly carry: (source: unknown, target: unknown) => Effect.Effect<unknown, CarrierDepthExceededError, never>;
|
|
69
|
-
}
|
|
70
|
-
//#endregion
|
|
71
2
|
//#region src/CanonicalJson.d.ts
|
|
72
3
|
declare const NonJsonValueError_base: Schema.Class<NonJsonValueError, Schema.TaggedStruct<"NonJsonValueError", {
|
|
73
4
|
/** JSON pointer to the offending value (`""` is the document root). */
|
|
@@ -87,7 +18,7 @@ declare const NonJsonValueError_base: Schema.Class<NonJsonValueError, Schema.Tag
|
|
|
87
18
|
*
|
|
88
19
|
* @public
|
|
89
20
|
*/
|
|
90
|
-
declare class NonJsonValueError extends NonJsonValueError_base {
|
|
21
|
+
export declare class NonJsonValueError extends NonJsonValueError_base {
|
|
91
22
|
get message(): string;
|
|
92
23
|
}
|
|
93
24
|
declare const JsonDepthExceededError_base: Schema.Class<JsonDepthExceededError, Schema.TaggedStruct<"JsonDepthExceededError", {
|
|
@@ -105,7 +36,7 @@ declare const JsonDepthExceededError_base: Schema.Class<JsonDepthExceededError,
|
|
|
105
36
|
*
|
|
106
37
|
* @public
|
|
107
38
|
*/
|
|
108
|
-
declare class JsonDepthExceededError extends JsonDepthExceededError_base {
|
|
39
|
+
export declare class JsonDepthExceededError extends JsonDepthExceededError_base {
|
|
109
40
|
get message(): string;
|
|
110
41
|
}
|
|
111
42
|
/**
|
|
@@ -149,7 +80,7 @@ interface CanonicalJsonOptions {
|
|
|
149
80
|
*
|
|
150
81
|
* @public
|
|
151
82
|
*/
|
|
152
|
-
declare class CanonicalJson {
|
|
83
|
+
export declare class CanonicalJson {
|
|
153
84
|
private constructor();
|
|
154
85
|
/**
|
|
155
86
|
* Serializes `value` to canonical JSON text. Pure and synchronous — the
|
|
@@ -165,201 +96,6 @@ declare class CanonicalJson {
|
|
|
165
96
|
static readonly serialize: (value: unknown, options?: CanonicalJsonOptions | undefined) => Effect.Effect<string, CanonicalJsonError, never>;
|
|
166
97
|
}
|
|
167
98
|
//#endregion
|
|
168
|
-
//#region src/SchemaVersioning.d.ts
|
|
169
|
-
declare const InvalidSchemaVersionError_base: Schema.Class<InvalidSchemaVersionError, Schema.TaggedStruct<"InvalidSchemaVersionError", {
|
|
170
|
-
/** The raw input string that failed to parse. */
|
|
171
|
-
readonly input: Schema.String;
|
|
172
|
-
}>, import("effect/Cause").YieldableError>;
|
|
173
|
-
/**
|
|
174
|
-
* Indicates that a string is not a valid SchemaStore version label.
|
|
175
|
-
*
|
|
176
|
-
* Raised by {@link SchemaVersioning.parse}.
|
|
177
|
-
*
|
|
178
|
-
* @public
|
|
179
|
-
*/
|
|
180
|
-
declare class InvalidSchemaVersionError extends InvalidSchemaVersionError_base {
|
|
181
|
-
get message(): string;
|
|
182
|
-
}
|
|
183
|
-
/**
|
|
184
|
-
* A schema version label: a branded string holding a **full three-component
|
|
185
|
-
* SemVer** — `major.minor.patch` with an optional prerelease, validated by
|
|
186
|
-
* `@effected/semver` itself. Build metadata is rejected (see below).
|
|
187
|
-
*
|
|
188
|
-
* `1.2` and `1` are NOT accepted, though SchemaStore's own corpus uses such
|
|
189
|
-
* labels: requiring all three components makes a label unambiguous to split
|
|
190
|
-
* back out of `<name>-<version>.json` or its URL, which is what consumers
|
|
191
|
-
* do with it. The file-name convention around the label stays SchemaStore's.
|
|
192
|
-
*
|
|
193
|
-
* The label round-trips verbatim into file names and catalog `versions`
|
|
194
|
-
* keys; ordering parses it directly (see {@link SchemaVersioning.Order}).
|
|
195
|
-
*
|
|
196
|
-
* @public
|
|
197
|
-
*/
|
|
198
|
-
declare const SchemaVersion: Schema.brand<Schema.String, "SchemaVersion">;
|
|
199
|
-
/**
|
|
200
|
-
* The type of a validated SchemaStore version label.
|
|
201
|
-
*
|
|
202
|
-
* @public
|
|
203
|
-
*/
|
|
204
|
-
type SchemaVersion = typeof SchemaVersion.Type;
|
|
205
|
-
/**
|
|
206
|
-
* The `url`/`versions` half of a catalog entry, as assembled by
|
|
207
|
-
* {@link SchemaVersioning.catalogUrls}.
|
|
208
|
-
*
|
|
209
|
-
* @public
|
|
210
|
-
*/
|
|
211
|
-
interface CatalogUrls {
|
|
212
|
-
/** The catalog `url` — the unversioned file, or the latest versioned file. */
|
|
213
|
-
readonly url: string;
|
|
214
|
-
/**
|
|
215
|
-
* The versioned catalog's `versions` map (label → url), inserted — and,
|
|
216
|
-
* since a three-component label can never be integer-like, enumerated
|
|
217
|
-
* and serialized — in ascending version order.
|
|
218
|
-
*/
|
|
219
|
-
readonly versions?: Readonly<Record<string, string>>;
|
|
220
|
-
}
|
|
221
|
-
/**
|
|
222
|
-
* Both SchemaStore catalog modes as pure derivations: unversioned (a plain
|
|
223
|
-
* `name.json` file, `url` only) and versioned (`name-<version>.json` files
|
|
224
|
-
* — SchemaStore's own suffix convention — a `versions` map, and `url`
|
|
225
|
-
* pointing at the latest version).
|
|
226
|
-
*
|
|
227
|
-
* Version labels are full three-component SemVer, so ordering is plain
|
|
228
|
-
* SemVer precedence: `1.10.0` above `1.9.0`, `2.0.0-beta` below `2.0.0`.
|
|
229
|
-
*
|
|
230
|
-
* @public
|
|
231
|
-
*/
|
|
232
|
-
declare class SchemaVersioning {
|
|
233
|
-
private constructor();
|
|
234
|
-
/**
|
|
235
|
-
* Parses a version label. Pure and synchronous — the primitive form;
|
|
236
|
-
* {@link SchemaVersioning.parse} is the same check behind a span.
|
|
237
|
-
*/
|
|
238
|
-
static parseResult(input: string): Result.Result<SchemaVersion, InvalidSchemaVersionError>;
|
|
239
|
-
/**
|
|
240
|
-
* Effect form of {@link SchemaVersioning.parseResult}, adding only the
|
|
241
|
-
* `SchemaVersioning.parse` span. Defined in terms of the `Result`
|
|
242
|
-
* primitive — synchronous callers can use that variant directly.
|
|
243
|
-
*/
|
|
244
|
-
static readonly parse: (input: string) => Effect.Effect<string & import("effect/Brand").Brand<"SchemaVersion">, InvalidSchemaVersionError, never>;
|
|
245
|
-
/**
|
|
246
|
-
* `Order` instance over version labels: plain SemVer precedence.
|
|
247
|
-
* `1.10.0` sorts above `1.9.0` (numeric, not lexical) and `2.0.0-beta`
|
|
248
|
-
* below `2.0.0` (prerelease precedence).
|
|
249
|
-
*/
|
|
250
|
-
static readonly Order: Order.Order<SchemaVersion>;
|
|
251
|
-
/**
|
|
252
|
-
* The highest version label by {@link SchemaVersioning.Order}, or
|
|
253
|
-
* `Option.none()` for an empty collection.
|
|
254
|
-
*/
|
|
255
|
-
static latest(versions: ReadonlyArray<SchemaVersion>): Option.Option<SchemaVersion>;
|
|
256
|
-
/**
|
|
257
|
-
* Derives the schema file name for a catalog name: `name.json`
|
|
258
|
-
* unversioned, `name-<version>.json` versioned.
|
|
259
|
-
*
|
|
260
|
-
* The name must be a simple file base name (no separators, no
|
|
261
|
-
* whitespace); anything else is a wiring mistake and throws.
|
|
262
|
-
*/
|
|
263
|
-
static fileName(name: string, version?: SchemaVersion): string;
|
|
264
|
-
/**
|
|
265
|
-
* The canonical URL a schema file is hosted at: `baseUrl` joined with
|
|
266
|
-
* {@link SchemaVersioning.fileName}.
|
|
267
|
-
*/
|
|
268
|
-
static schemaUrl(baseUrl: string, name: string, version?: SchemaVersion): string;
|
|
269
|
-
/**
|
|
270
|
-
* Assembles the `url`/`versions` half of a catalog entry.
|
|
271
|
-
*
|
|
272
|
-
* Omitting `versions` selects the unversioned mode (`url` only,
|
|
273
|
-
* pointing at the plain `name.json`). Providing them selects the
|
|
274
|
-
* versioned mode: the `versions` map carries every label, and `url`
|
|
275
|
-
* points at the latest version's file. An **empty** `versions` array is
|
|
276
|
-
* a contradiction (versioned mode with no versions) and throws — pass
|
|
277
|
-
* `undefined` for the unversioned mode.
|
|
278
|
-
*
|
|
279
|
-
* Labels are inserted in ascending {@link SchemaVersioning.Order} and
|
|
280
|
-
* stay that way on serialization. Requiring three components is what
|
|
281
|
-
* buys this: JavaScript enumerates array-index-like keys first, so the
|
|
282
|
-
* old grammar's bare-major label (`"2"`) jumped ahead of every dotted
|
|
283
|
-
* one regardless of insertion order. No SemVer label is integer-like,
|
|
284
|
-
* so that hazard is gone. Deriving ordering from the labels themselves
|
|
285
|
-
* (as {@link SchemaVersioning.latest} does) is still the robust read.
|
|
286
|
-
*/
|
|
287
|
-
static catalogUrls(options: {
|
|
288
|
-
readonly baseUrl: string;
|
|
289
|
-
readonly name: string;
|
|
290
|
-
readonly versions?: ReadonlyArray<SchemaVersion>;
|
|
291
|
-
}): CatalogUrls;
|
|
292
|
-
}
|
|
293
|
-
//#endregion
|
|
294
|
-
//#region src/CatalogEntry.d.ts
|
|
295
|
-
declare const CatalogLintFinding_base: Schema.Class<CatalogLintFinding, Schema.Struct<{
|
|
296
|
-
/** Which hygiene check fired. */
|
|
297
|
-
readonly check: Schema.Literals<readonly ["GenericFileMatch", "ComplexFileMatch"]>;
|
|
298
|
-
/** The `fileMatch` pattern the finding is about. */
|
|
299
|
-
readonly pattern: Schema.String;
|
|
300
|
-
/** Human-readable explanation with the SchemaStore rationale. */
|
|
301
|
-
readonly message: Schema.String;
|
|
302
|
-
}>, {}>;
|
|
303
|
-
/**
|
|
304
|
-
* A fileMatch hygiene finding: a value in a lint report, not an error —
|
|
305
|
-
* SchemaStore reviewers reject entries over these, so surfacing them
|
|
306
|
-
* locally is the point, but a warned entry is still a valid entry.
|
|
307
|
-
*
|
|
308
|
-
* @public
|
|
309
|
-
*/
|
|
310
|
-
declare class CatalogLintFinding extends CatalogLintFinding_base {}
|
|
311
|
-
declare const CatalogEntry_base: Schema.Class<CatalogEntry, Schema.Struct<{
|
|
312
|
-
/** The schema's display name in the catalog. */
|
|
313
|
-
readonly name: Schema.String;
|
|
314
|
-
/** The catalog description. */
|
|
315
|
-
readonly description: Schema.String;
|
|
316
|
-
/** Glob patterns editors match files against. */
|
|
317
|
-
readonly fileMatch: Schema.$Array<Schema.String>;
|
|
318
|
-
/** The schema URL — the unversioned file, or the latest version. */
|
|
319
|
-
readonly url: Schema.String;
|
|
320
|
-
/**
|
|
321
|
-
* Versioned mode only: label → schema URL. Inserted ascending, but key
|
|
322
|
-
* order is not a contract — bare-major labels enumerate first (see
|
|
323
|
-
* `SchemaVersioning.catalogUrls`); derive ordering from the labels.
|
|
324
|
-
*/
|
|
325
|
-
readonly versions: Schema.optionalKey<Schema.$Record<Schema.String, Schema.String>>;
|
|
326
|
-
}>, {}>;
|
|
327
|
-
/**
|
|
328
|
-
* A SchemaStore `catalog.json` entry: the class is the schema, so decoding
|
|
329
|
-
* an existing entry and encoding one for submission are the same artifact.
|
|
330
|
-
* `versions` is present only for versioned catalogs
|
|
331
|
-
* ({@link SchemaVersioning.catalogUrls} assembles both modes).
|
|
332
|
-
*
|
|
333
|
-
* @public
|
|
334
|
-
*/
|
|
335
|
-
declare class CatalogEntry extends CatalogEntry_base {
|
|
336
|
-
/**
|
|
337
|
-
* Assembles an entry from a catalog identity plus
|
|
338
|
-
* {@link SchemaVersioning.catalogUrls}' inputs: pass `versions` for the
|
|
339
|
-
* versioned mode (the `versions` map and latest-pointing `url` are
|
|
340
|
-
* derived), omit it for the unversioned mode.
|
|
341
|
-
*/
|
|
342
|
-
static assemble(options: {
|
|
343
|
-
readonly name: string;
|
|
344
|
-
readonly description: string;
|
|
345
|
-
readonly fileMatch: ReadonlyArray<string>;
|
|
346
|
-
readonly baseUrl: string;
|
|
347
|
-
readonly fileBaseName?: string;
|
|
348
|
-
readonly versions?: ReadonlyArray<SchemaVersion>;
|
|
349
|
-
}): CatalogEntry;
|
|
350
|
-
/**
|
|
351
|
-
* The fileMatch hygiene lint over this entry's patterns — pure shape
|
|
352
|
-
* analysis (no glob engine): generic patterns SchemaStore rejects and
|
|
353
|
-
* complex constructs it asks contributors to expand.
|
|
354
|
-
*/
|
|
355
|
-
lint(): ReadonlyArray<CatalogLintFinding>;
|
|
356
|
-
/**
|
|
357
|
-
* {@link CatalogEntry.lint} over a bare pattern list, for callers
|
|
358
|
-
* checking patterns before an entry exists.
|
|
359
|
-
*/
|
|
360
|
-
static lintFileMatch(patterns: ReadonlyArray<string>): ReadonlyArray<CatalogLintFinding>;
|
|
361
|
-
}
|
|
362
|
-
//#endregion
|
|
363
99
|
//#region src/DocumentDiff.d.ts
|
|
364
100
|
/**
|
|
365
101
|
* What differs between two schema documents:
|
|
@@ -408,7 +144,7 @@ type SchemaChange = "none" | "annotations" | "contract";
|
|
|
408
144
|
*
|
|
409
145
|
* @public
|
|
410
146
|
*/
|
|
411
|
-
declare class DocumentDiff {
|
|
147
|
+
export declare class DocumentDiff {
|
|
412
148
|
private constructor();
|
|
413
149
|
/**
|
|
414
150
|
* Classify the difference between two emitted document values (the
|
|
@@ -448,7 +184,7 @@ declare class DocumentDiff {
|
|
|
448
184
|
*
|
|
449
185
|
* @public
|
|
450
186
|
*/
|
|
451
|
-
declare const DRAFT_07_META_SCHEMA = "http://json-schema.org/draft-07/schema#";
|
|
187
|
+
export declare const DRAFT_07_META_SCHEMA = "http://json-schema.org/draft-07/schema#";
|
|
452
188
|
declare const SchemaConversionError_base: Schema.Class<SchemaConversionError, Schema.TaggedStruct<"SchemaConversionError", {
|
|
453
189
|
/** The `$id` of the document that failed to build. */
|
|
454
190
|
readonly $id: Schema.String;
|
|
@@ -465,7 +201,34 @@ declare const SchemaConversionError_base: Schema.Class<SchemaConversionError, Sc
|
|
|
465
201
|
*
|
|
466
202
|
* @public
|
|
467
203
|
*/
|
|
468
|
-
declare class SchemaConversionError extends SchemaConversionError_base {
|
|
204
|
+
export declare class SchemaConversionError extends SchemaConversionError_base {
|
|
205
|
+
get message(): string;
|
|
206
|
+
}
|
|
207
|
+
declare const UndeclaredAnnotationKeyError_base: Schema.Class<UndeclaredAnnotationKeyError, Schema.TaggedStruct<"UndeclaredAnnotationKeyError", {
|
|
208
|
+
/** The `$id` of the document that was being built. */
|
|
209
|
+
readonly $id: Schema.String;
|
|
210
|
+
/** The offending keys, deduplicated and sorted. */
|
|
211
|
+
readonly keys: Schema.$Array<Schema.String>;
|
|
212
|
+
}>, import("effect/Cause").YieldableError>;
|
|
213
|
+
/**
|
|
214
|
+
* Indicates that a caller-supplied `includeAnnotationKey` admitted an
|
|
215
|
+
* annotation key outside the declared keyword families
|
|
216
|
+
* ({@link KeywordFamilies}).
|
|
217
|
+
*
|
|
218
|
+
* Raised by {@link StoreDocument.fromSchema}. This package emits
|
|
219
|
+
* SchemaStore-compatible documents only, so the declared families are the
|
|
220
|
+
* whole permitted non-standard surface. A key outside them is refused
|
|
221
|
+
* loudly rather than emitted — which would ship a document SchemaStore's
|
|
222
|
+
* own gate rejects — or silently omitted, which would hide the mistake in
|
|
223
|
+
* the caller's predicate.
|
|
224
|
+
*
|
|
225
|
+
* The predicate itself cannot be introspected, so the offending keys are
|
|
226
|
+
* the ones it actually admitted while the document was being generated: a
|
|
227
|
+
* key the source schema never annotates cannot appear here.
|
|
228
|
+
*
|
|
229
|
+
* @public
|
|
230
|
+
*/
|
|
231
|
+
export declare class UndeclaredAnnotationKeyError extends UndeclaredAnnotationKeyError_base {
|
|
469
232
|
get message(): string;
|
|
470
233
|
}
|
|
471
234
|
/**
|
|
@@ -482,14 +245,17 @@ interface StoreDocumentOptions {
|
|
|
482
245
|
* `includeAnnotationKey`).
|
|
483
246
|
*
|
|
484
247
|
* The declared non-standard keyword families ({@link KeywordFamilies})
|
|
485
|
-
* are **always admitted
|
|
486
|
-
*
|
|
487
|
-
*
|
|
488
|
-
*
|
|
489
|
-
*
|
|
490
|
-
*
|
|
491
|
-
*
|
|
492
|
-
*
|
|
248
|
+
* are **always admitted**, regardless of what a supplied
|
|
249
|
+
* `includeAnnotationKey` answers — annotate a schema node
|
|
250
|
+
* (`Schema.String.annotate({ "x-taplo": ... })`) and the key appears in
|
|
251
|
+
* the built document, in place, on the node it was attached to.
|
|
252
|
+
*
|
|
253
|
+
* A supplied `includeAnnotationKey` is consulted only for other keys,
|
|
254
|
+
* and **admitting one fails the build** with
|
|
255
|
+
* {@link UndeclaredAnnotationKeyError}. The families are the entire
|
|
256
|
+
* non-standard surface this package will emit, so the predicate has no
|
|
257
|
+
* admitting role left; it survives only because the rest of
|
|
258
|
+
* `ToJsonSchemaOptions` passes through, and is best left unset.
|
|
493
259
|
*/
|
|
494
260
|
readonly jsonSchema?: Schema.ToJsonSchemaOptions;
|
|
495
261
|
}
|
|
@@ -513,13 +279,21 @@ declare const StoreDocument_base: Schema.Class<StoreDocument, Schema.Struct<{
|
|
|
513
279
|
* `JsonSchema.toDocumentDraft07` lowering, the `#/definitions` →
|
|
514
280
|
* `#/$defs` `$ref` rewrite the lowering makes necessary — so every `$ref`
|
|
515
281
|
* in a built document already resolves against the `$defs` pool — and the
|
|
516
|
-
*
|
|
517
|
-
* families ({@link KeywordFamilies})
|
|
518
|
-
*
|
|
282
|
+
* gate that holds the document's non-standard surface to the declared
|
|
283
|
+
* keyword families ({@link KeywordFamilies}). The package owns assembly and
|
|
284
|
+
* publication shape, not a JSON Schema engine.
|
|
285
|
+
*
|
|
286
|
+
* Annotated declared-family keys survive into the built document because
|
|
287
|
+
* core's Draft-07 lowering copies unknown and custom keywords through as
|
|
288
|
+
* opaque values, in place, including across the tuple coordinate move
|
|
289
|
+
* (2020-12 `prefixItems[i]` → Draft-07 `items[i]`, trailing `items` →
|
|
290
|
+
* `additionalItems`). This package therefore does no re-grafting of its
|
|
291
|
+
* own; it only declines to rewrite `$ref`-shaped strings *inside* those
|
|
292
|
+
* opaque payloads.
|
|
519
293
|
*
|
|
520
294
|
* @public
|
|
521
295
|
*/
|
|
522
|
-
declare class StoreDocument extends StoreDocument_base {
|
|
296
|
+
export declare class StoreDocument extends StoreDocument_base {
|
|
523
297
|
/**
|
|
524
298
|
* Builds a Draft-07 document from its parts, filling `$schema` with
|
|
525
299
|
* {@link DRAFT_07_META_SCHEMA}.
|
|
@@ -552,26 +326,475 @@ declare class StoreDocument extends StoreDocument_base {
|
|
|
552
326
|
* synchronous — the primitive form; {@link StoreDocument.fromSchema} is
|
|
553
327
|
* the same pipeline behind a span.
|
|
554
328
|
*/
|
|
555
|
-
static fromSchemaResult(source: Schema.Constraint, options: StoreDocumentOptions): Result.Result<StoreDocument, SchemaConversionError>;
|
|
329
|
+
static fromSchemaResult(source: Schema.Constraint, options: StoreDocumentOptions): Result.Result<StoreDocument, SchemaConversionError | UndeclaredAnnotationKeyError>;
|
|
556
330
|
/**
|
|
557
331
|
* Effect form of {@link StoreDocument.fromSchemaResult}, adding only the
|
|
558
332
|
* `StoreDocument.fromSchema` span. Defined in terms of the `Result`
|
|
559
333
|
* primitive — synchronous callers can use that variant directly.
|
|
560
334
|
*/
|
|
561
|
-
static readonly fromSchema: (source: Schema.Constraint, options: StoreDocumentOptions) => Effect.Effect<StoreDocument, SchemaConversionError, never>;
|
|
335
|
+
static readonly fromSchema: (source: Schema.Constraint, options: StoreDocumentOptions) => Effect.Effect<StoreDocument, SchemaConversionError | UndeclaredAnnotationKeyError, never>;
|
|
562
336
|
/**
|
|
563
337
|
* The flat SchemaStore publication shape: `$schema`, `$id`, the root
|
|
564
338
|
* schema's keywords spread at the top level, then the `$defs` pool.
|
|
565
339
|
* `$defs` is omitted when the pool is empty (a deliberate divergence
|
|
566
340
|
* from the extraction source, which always emitted the key).
|
|
567
341
|
*/
|
|
568
|
-
toJson(): Record<string, unknown>;
|
|
342
|
+
toJson(): Record<string, unknown>;
|
|
343
|
+
/**
|
|
344
|
+
* Canonical JSON text of {@link StoreDocument.toJson}, via
|
|
345
|
+
* {@link CanonicalJson.serializeResult} — one serializer, so the
|
|
346
|
+
* document and any consumer-serialized value cannot drift.
|
|
347
|
+
*/
|
|
348
|
+
serializeResult(options?: CanonicalJsonOptions): Result.Result<string, CanonicalJsonError>;
|
|
349
|
+
}
|
|
350
|
+
//#endregion
|
|
351
|
+
//#region src/SchemaFile.d.ts
|
|
352
|
+
declare const SchemaFileReadError_base: Schema.Class<SchemaFileReadError, Schema.TaggedStruct<"SchemaFileReadError", {
|
|
353
|
+
/** The path that could not be read. */
|
|
354
|
+
readonly path: Schema.String;
|
|
355
|
+
/** The underlying filesystem failure, preserved structurally. */
|
|
356
|
+
readonly cause: Schema.Defect;
|
|
357
|
+
}>, import("effect/Cause").YieldableError>;
|
|
358
|
+
/**
|
|
359
|
+
* Indicates that a schema file could not be read from the filesystem (a
|
|
360
|
+
* filesystem error other than not-found).
|
|
361
|
+
*
|
|
362
|
+
* @public
|
|
363
|
+
*/
|
|
364
|
+
export declare class SchemaFileReadError extends SchemaFileReadError_base {
|
|
365
|
+
get message(): string;
|
|
366
|
+
}
|
|
367
|
+
declare const SchemaFileNotFoundError_base: Schema.Class<SchemaFileNotFoundError, Schema.TaggedStruct<"SchemaFileNotFoundError", {
|
|
368
|
+
/** The path where the schema file was expected. */
|
|
369
|
+
readonly path: Schema.String;
|
|
370
|
+
}>, import("effect/Cause").YieldableError>;
|
|
371
|
+
/**
|
|
372
|
+
* Indicates that no schema file exists at the expected path. Carries its
|
|
373
|
+
* own tag for `catchTag` routing.
|
|
374
|
+
*
|
|
375
|
+
* @public
|
|
376
|
+
*/
|
|
377
|
+
export declare class SchemaFileNotFoundError extends SchemaFileNotFoundError_base {
|
|
378
|
+
get message(): string;
|
|
379
|
+
}
|
|
380
|
+
declare const SchemaFileWriteError_base: Schema.Class<SchemaFileWriteError, Schema.TaggedStruct<"SchemaFileWriteError", {
|
|
381
|
+
/** The path that could not be written. */
|
|
382
|
+
readonly path: Schema.String;
|
|
383
|
+
/** The underlying filesystem failure, preserved structurally. */
|
|
384
|
+
readonly cause: Schema.Defect;
|
|
385
|
+
}>, import("effect/Cause").YieldableError>;
|
|
386
|
+
/**
|
|
387
|
+
* Indicates that a schema file could not be written to the filesystem.
|
|
388
|
+
* Narrowed to the filesystem failure only — a serialization failure
|
|
389
|
+
* surfaces as its own `CanonicalJsonError`, never wrapped here.
|
|
390
|
+
*
|
|
391
|
+
* @public
|
|
392
|
+
*/
|
|
393
|
+
export declare class SchemaFileWriteError extends SchemaFileWriteError_base {
|
|
394
|
+
get message(): string;
|
|
395
|
+
}
|
|
396
|
+
/**
|
|
397
|
+
* What {@link SchemaFileShape.write} did to the filesystem: `"written"`
|
|
398
|
+
* when it wrote, `"unchanged"` when it left the file alone — reported as a
|
|
399
|
+
* value so the caller decides what to surface, never a log.
|
|
400
|
+
*
|
|
401
|
+
* @public
|
|
402
|
+
*/
|
|
403
|
+
type WriteOutcome = "written" | "unchanged";
|
|
404
|
+
/**
|
|
405
|
+
* How the document being written relates to what was already on disk:
|
|
406
|
+
* {@link SchemaChange} plus `"created"` for a file that did not exist, so
|
|
407
|
+
* there was nothing to compare against.
|
|
408
|
+
*
|
|
409
|
+
* @public
|
|
410
|
+
*/
|
|
411
|
+
type WriteChange = SchemaChange | "created";
|
|
412
|
+
/**
|
|
413
|
+
* The result of {@link SchemaFileShape.write}: what happened to the file,
|
|
414
|
+
* and what the difference MEANT.
|
|
415
|
+
*
|
|
416
|
+
* The two are independent on purpose. `change` answers the versioning
|
|
417
|
+
* question — `"annotations"` means only prose and editor affordances moved,
|
|
418
|
+
* so the document replaces its predecessor transparently and needs no new
|
|
419
|
+
* {@link SchemaVersioning} version, while `"contract"` means an assertion
|
|
420
|
+
* keyword moved and a consumer's document valid yesterday may be invalid
|
|
421
|
+
* today. `outcome` answers only whether bytes were written, which under
|
|
422
|
+
* `compare: "bytes"` can be `"written"` even when `change` is `"none"`.
|
|
423
|
+
*
|
|
424
|
+
* @public
|
|
425
|
+
*/
|
|
426
|
+
interface WriteResult {
|
|
427
|
+
/**
|
|
428
|
+
* Whether the file was written. **This is the authoritative answer to
|
|
429
|
+
* "did the filesystem get touched"** — always, under either `compare`
|
|
430
|
+
* mode. Do not infer it from `change`: under `compare: "bytes"` a
|
|
431
|
+
* `change` of `"none"` still writes.
|
|
432
|
+
*/
|
|
433
|
+
readonly outcome: WriteOutcome;
|
|
434
|
+
/** What differs between the previous content and the new document. */
|
|
435
|
+
readonly change: WriteChange;
|
|
436
|
+
}
|
|
437
|
+
/**
|
|
438
|
+
* The result of {@link SchemaFileShape.check}: the same two answers
|
|
439
|
+
* {@link WriteResult} carries, for a call that touched nothing.
|
|
440
|
+
*
|
|
441
|
+
* `wouldWrite` is `outcome`'s counterpart — it honors `compare`, so it
|
|
442
|
+
* answers "would `write` do anything with these same options", which
|
|
443
|
+
* `change` alone cannot under `compare: "bytes"`.
|
|
444
|
+
*
|
|
445
|
+
* @public
|
|
446
|
+
*/
|
|
447
|
+
interface CheckResult {
|
|
448
|
+
/** Whether a `write` with the same options would touch the file. */
|
|
449
|
+
readonly wouldWrite: boolean;
|
|
450
|
+
/** What differs between the on-disk content and the new document. */
|
|
451
|
+
readonly change: WriteChange;
|
|
452
|
+
}
|
|
453
|
+
/**
|
|
454
|
+
* Options for {@link SchemaFileShape.write} and
|
|
455
|
+
* {@link SchemaFileShape.check}: the {@link CanonicalJsonOptions} the
|
|
456
|
+
* document serializes under, plus how `write` decides whether to touch the
|
|
457
|
+
* file.
|
|
458
|
+
*
|
|
459
|
+
* @public
|
|
460
|
+
*/
|
|
461
|
+
interface SchemaWriteOptions extends CanonicalJsonOptions {
|
|
462
|
+
/**
|
|
463
|
+
* How `write` decides the file needs rewriting:
|
|
464
|
+
*
|
|
465
|
+
* - `"value"` (the default) — compare the parsed content. Immune to any
|
|
466
|
+
* other tool that reformats the file, which is the common case: a repo
|
|
467
|
+
* whose pre-commit hook runs Biome or Prettier over `*.json` would
|
|
468
|
+
* otherwise see every run rewrite the file forever, because the
|
|
469
|
+
* formatter's bytes never match `CanonicalJson`'s.
|
|
470
|
+
* - `"bytes"` — compare the exact text, so the file on disk is only ever
|
|
471
|
+
* `CanonicalJson`'s own output. Choose this when the emitted bytes are
|
|
472
|
+
* themselves the artifact and no other tool is allowed to touch them.
|
|
473
|
+
*
|
|
474
|
+
* `change` in the {@link WriteResult} is classified by content either
|
|
475
|
+
* way; this option decides only whether a byte-level difference is
|
|
476
|
+
* enough to rewrite.
|
|
477
|
+
*/
|
|
478
|
+
readonly compare?: "bytes" | "value";
|
|
479
|
+
}
|
|
480
|
+
/**
|
|
481
|
+
* The shape of the {@link SchemaFile} service — the value produced by
|
|
482
|
+
* {@link SchemaFile.make} and carried by its layer.
|
|
483
|
+
*
|
|
484
|
+
* @public
|
|
485
|
+
*/
|
|
486
|
+
interface SchemaFileShape {
|
|
487
|
+
/**
|
|
488
|
+
* Read a schema file's exact text (the drift-test read side: compare it
|
|
489
|
+
* against `StoreDocument.serializeResult`). Fails with
|
|
490
|
+
* `SchemaFileNotFoundError` (ENOENT) or `SchemaFileReadError` (other
|
|
491
|
+
* filesystem errors).
|
|
492
|
+
*/
|
|
493
|
+
readonly read: (path: string) => Effect.Effect<string, SchemaFileReadError | SchemaFileNotFoundError>;
|
|
494
|
+
/**
|
|
495
|
+
* Serialize a document to canonical JSON and write it **only if the
|
|
496
|
+
* on-disk content differs** (a missing file counts as different),
|
|
497
|
+
* creating parent directories as needed. Answers a {@link WriteResult}
|
|
498
|
+
* as a value: what happened to the file, and what the difference meant.
|
|
499
|
+
* Fails with a `CanonicalJsonError` (the document does not serialize),
|
|
500
|
+
* `SchemaFileReadError` (the existing content could not be read for
|
|
501
|
+
* comparison) or `SchemaFileWriteError` (the filesystem write failed).
|
|
502
|
+
*/
|
|
503
|
+
readonly write: (path: string, document: StoreDocument, options?: SchemaWriteOptions) => Effect.Effect<WriteResult, CanonicalJsonError | SchemaFileReadError | SchemaFileWriteError>;
|
|
504
|
+
/**
|
|
505
|
+
* The same comparison {@link SchemaFileShape.write} makes, **without
|
|
506
|
+
* touching the filesystem** — the drift-check half of the pair, for a
|
|
507
|
+
* CI job that must assert a committed schema is current rather than
|
|
508
|
+
* regenerate it.
|
|
509
|
+
*
|
|
510
|
+
* Answers both questions the writer answers: `change` classifies the
|
|
511
|
+
* content (immune to a formatter having reflowed the committed file),
|
|
512
|
+
* and `wouldWrite` honors `compare`, so it agrees with `write` under
|
|
513
|
+
* either mode. Checking drift is `change`; predicting the writer is
|
|
514
|
+
* `wouldWrite`.
|
|
515
|
+
*/
|
|
516
|
+
readonly check: (path: string, document: StoreDocument, options?: SchemaWriteOptions) => Effect.Effect<CheckResult, CanonicalJsonError | SchemaFileReadError>;
|
|
517
|
+
}
|
|
518
|
+
declare const SchemaFile_base: Context.ServiceClass<SchemaFile, "@effected/schemastore/SchemaFile", SchemaFileShape>;
|
|
519
|
+
/**
|
|
520
|
+
* Reads and writes emitted schema documents over core `FileSystem` /
|
|
521
|
+
* `Path` — the package's one IO surface. The layer requires those
|
|
522
|
+
* services; provide `@effect/platform-node`'s `NodeFileSystem` / `NodePath`
|
|
523
|
+
* (or a bun equivalent) at the application boundary.
|
|
524
|
+
*
|
|
525
|
+
* `write` is write-if-changed, and by default compares **content**: an
|
|
526
|
+
* unchanged document never touches the file even if another tool has
|
|
527
|
+
* reformatted it, so a generator committed to a repo whose pre-commit hook
|
|
528
|
+
* formats JSON does not churn on every run. It also reports what the
|
|
529
|
+
* difference meant — `"annotations"` (prose only, replaces its predecessor
|
|
530
|
+
* transparently) versus `"contract"` (an assertion moved, so a new
|
|
531
|
+
* `SchemaVersioning` version is warranted). `check` makes the same
|
|
532
|
+
* comparison without writing, which is what a CI drift job wants.
|
|
533
|
+
*
|
|
534
|
+
* @example
|
|
535
|
+
* ```ts
|
|
536
|
+
* import { SchemaFile, StoreDocument } from "@effected/schemastore";
|
|
537
|
+
* import { NodeFileSystem, NodePath } from "@effect/platform-node";
|
|
538
|
+
* import { Effect, Layer, Schema } from "effect";
|
|
539
|
+
*
|
|
540
|
+
* const program = Effect.gen(function* () {
|
|
541
|
+
* const files = yield* SchemaFile;
|
|
542
|
+
* const document = yield* StoreDocument.fromSchema(Schema.Struct({ name: Schema.String }), {
|
|
543
|
+
* $id: "https://example.com/config.schema.json",
|
|
544
|
+
* });
|
|
545
|
+
* return yield* files.write("schemas/config.schema.json", document);
|
|
546
|
+
* }).pipe(
|
|
547
|
+
* Effect.provide(SchemaFile.layer),
|
|
548
|
+
* Effect.provide(Layer.mergeAll(NodeFileSystem.layer, NodePath.layer)),
|
|
549
|
+
* );
|
|
550
|
+
* ```
|
|
551
|
+
*
|
|
552
|
+
* @public
|
|
553
|
+
*/
|
|
554
|
+
export declare class SchemaFile extends SchemaFile_base {
|
|
555
|
+
/** Build the service implementation from `FileSystem` / `Path` in context; use {@link SchemaFile.layer} to provide it. */
|
|
556
|
+
static readonly make: Effect.Effect<SchemaFileShape, never, FileSystem.FileSystem | Path.Path>;
|
|
557
|
+
/**
|
|
558
|
+
* The live layer. Requires core `FileSystem` / `Path`, provided by the
|
|
559
|
+
* consumer's platform implementation at the edge.
|
|
560
|
+
*/
|
|
561
|
+
static readonly layer: Layer.Layer<SchemaFile, never, FileSystem.FileSystem | Path.Path>;
|
|
562
|
+
}
|
|
563
|
+
//#endregion
|
|
564
|
+
//#region src/SchemaVersioning.d.ts
|
|
565
|
+
declare const InvalidSchemaVersionError_base: Schema.Class<InvalidSchemaVersionError, Schema.TaggedStruct<"InvalidSchemaVersionError", {
|
|
566
|
+
/** The raw input string that failed to parse. */
|
|
567
|
+
readonly input: Schema.String;
|
|
568
|
+
}>, import("effect/Cause").YieldableError>;
|
|
569
|
+
/**
|
|
570
|
+
* Indicates that a string is not a valid SchemaStore version label.
|
|
571
|
+
*
|
|
572
|
+
* Raised by {@link SchemaVersioning.parse}.
|
|
573
|
+
*
|
|
574
|
+
* @public
|
|
575
|
+
*/
|
|
576
|
+
export declare class InvalidSchemaVersionError extends InvalidSchemaVersionError_base {
|
|
577
|
+
get message(): string;
|
|
578
|
+
}
|
|
579
|
+
/**
|
|
580
|
+
* A schema version label: a branded string holding a **full three-component
|
|
581
|
+
* SemVer** — `major.minor.patch` with an optional prerelease, validated by
|
|
582
|
+
* `@effected/semver` itself. Build metadata is rejected (see below).
|
|
583
|
+
*
|
|
584
|
+
* `1.2` and `1` are NOT accepted, though SchemaStore's own corpus uses such
|
|
585
|
+
* labels: requiring all three components makes a label unambiguous to split
|
|
586
|
+
* back out of `<name>-<version>.json` or its URL, which is what consumers
|
|
587
|
+
* do with it. The file-name convention around the label stays SchemaStore's.
|
|
588
|
+
*
|
|
589
|
+
* The label round-trips verbatim into file names and catalog `versions`
|
|
590
|
+
* keys; ordering parses it directly (see {@link SchemaVersioning.Order}).
|
|
591
|
+
*
|
|
592
|
+
* @public
|
|
593
|
+
*/
|
|
594
|
+
export declare const SchemaVersion: Schema.brand<Schema.String, "SchemaVersion">;
|
|
595
|
+
/**
|
|
596
|
+
* The type of a validated SchemaStore version label.
|
|
597
|
+
*
|
|
598
|
+
* @public
|
|
599
|
+
*/
|
|
600
|
+
export type SchemaVersion = typeof SchemaVersion.Type;
|
|
601
|
+
/**
|
|
602
|
+
* The `url`/`versions` half of a catalog entry, as assembled by
|
|
603
|
+
* {@link SchemaVersioning.catalogUrls}.
|
|
604
|
+
*
|
|
605
|
+
* @public
|
|
606
|
+
*/
|
|
607
|
+
interface CatalogUrls {
|
|
608
|
+
/** The catalog `url` — the unversioned file, or the latest versioned file. */
|
|
609
|
+
readonly url: string;
|
|
610
|
+
/**
|
|
611
|
+
* The versioned catalog's `versions` map (label → url), inserted — and,
|
|
612
|
+
* since a three-component label can never be integer-like, enumerated
|
|
613
|
+
* and serialized — in ascending version order.
|
|
614
|
+
*/
|
|
615
|
+
readonly versions?: Readonly<Record<string, string>>;
|
|
616
|
+
}
|
|
617
|
+
/**
|
|
618
|
+
* Both SchemaStore catalog modes as pure derivations: unversioned (a plain
|
|
619
|
+
* `name.json` file, `url` only) and versioned (`name-<version>.json` files
|
|
620
|
+
* — SchemaStore's own suffix convention — a `versions` map, and `url`
|
|
621
|
+
* pointing at the latest version).
|
|
622
|
+
*
|
|
623
|
+
* Version labels are full three-component SemVer, so ordering is plain
|
|
624
|
+
* SemVer precedence: `1.10.0` above `1.9.0`, `2.0.0-beta` below `2.0.0`.
|
|
625
|
+
*
|
|
626
|
+
* @public
|
|
627
|
+
*/
|
|
628
|
+
export declare class SchemaVersioning {
|
|
629
|
+
private constructor();
|
|
630
|
+
/**
|
|
631
|
+
* Parses a version label. Pure and synchronous — the primitive form;
|
|
632
|
+
* {@link SchemaVersioning.parse} is the same check behind a span.
|
|
633
|
+
*/
|
|
634
|
+
static parseResult(input: string): Result.Result<SchemaVersion, InvalidSchemaVersionError>;
|
|
635
|
+
/**
|
|
636
|
+
* Effect form of {@link SchemaVersioning.parseResult}, adding only the
|
|
637
|
+
* `SchemaVersioning.parse` span. Defined in terms of the `Result`
|
|
638
|
+
* primitive — synchronous callers can use that variant directly.
|
|
639
|
+
*/
|
|
640
|
+
static readonly parse: (input: string) => Effect.Effect<string & import("effect/Brand").Brand<"SchemaVersion">, InvalidSchemaVersionError, never>;
|
|
641
|
+
/**
|
|
642
|
+
* `Order` instance over version labels: plain SemVer precedence.
|
|
643
|
+
* `1.10.0` sorts above `1.9.0` (numeric, not lexical) and `2.0.0-beta`
|
|
644
|
+
* below `2.0.0` (prerelease precedence).
|
|
645
|
+
*/
|
|
646
|
+
static readonly Order: Order.Order<SchemaVersion>;
|
|
647
|
+
/**
|
|
648
|
+
* The highest version label by {@link SchemaVersioning.Order}, or
|
|
649
|
+
* `Option.none()` for an empty collection.
|
|
650
|
+
*/
|
|
651
|
+
static latest(versions: ReadonlyArray<SchemaVersion>): Option.Option<SchemaVersion>;
|
|
652
|
+
/**
|
|
653
|
+
* Whether a label names a pinned, published document — i.e. it is NOT a
|
|
654
|
+
* prerelease. SemVer §9 makes a prerelease's own instability explicit, so
|
|
655
|
+
* a contract change inside one is not a break for anyone.
|
|
656
|
+
*
|
|
657
|
+
* ONE predicate consumed by two policies so they cannot drift:
|
|
658
|
+
* `SchemaPipeline`'s `"block-versioned"` guard (a pinned versioned target
|
|
659
|
+
* refuses an in-place contract change) and {@link SchemaVersioning.next}
|
|
660
|
+
* (a non-pinned label is not bumped). If the two used different tests, a
|
|
661
|
+
* caller could be refused a write AND told to keep the same label — a
|
|
662
|
+
* deadlock.
|
|
663
|
+
*/
|
|
664
|
+
static isPinned(version: SchemaVersion): boolean;
|
|
665
|
+
/**
|
|
666
|
+
* The version label a change classification calls for. Pure and
|
|
667
|
+
* synchronous; total over validated labels — a non-label input is a wiring
|
|
668
|
+
* bug and dies as a defect, the same as {@link SchemaVersioning.Order}.
|
|
669
|
+
*
|
|
670
|
+
* - `change !== "contract"` (`"none"`, `"annotations"`, `"created"`) →
|
|
671
|
+
* `current`. A created file has no predecessor to break; an annotation
|
|
672
|
+
* change is transparently replaceable (`DocumentDiff`).
|
|
673
|
+
* - `current` is not pinned (a prerelease) → `current`. A prerelease
|
|
674
|
+
* declares its own instability; the pipeline's `"block-versioned"`
|
|
675
|
+
* policy uses the same {@link SchemaVersioning.isPinned}, so the gate
|
|
676
|
+
* and the bump agree.
|
|
677
|
+
* - `major === 0` → MINOR bump (`0.4.0` → `0.5.0`): on the 0.x line MINOR
|
|
678
|
+
* is the breaking axis.
|
|
679
|
+
* - otherwise → MAJOR bump (`5.0.0` → `6.0.0`).
|
|
680
|
+
*
|
|
681
|
+
* The bump's job is to be strictly greater and conspicuous, NOT to encode
|
|
682
|
+
* SemVer compatibility: `DocumentDiff` cannot tell an added optional
|
|
683
|
+
* property from a removed required one, so every contract change reads as
|
|
684
|
+
* breaking. Each label is its own file and URL, so an over-bump costs a
|
|
685
|
+
* file; an under-bump would overwrite a pinned document. `next` never
|
|
686
|
+
* introduces a prerelease from a stable input.
|
|
687
|
+
*
|
|
688
|
+
* A component that would be bumped past `Number.MAX_SAFE_INTEGER` cannot be
|
|
689
|
+
* represented, and throws this module's explicit invariant `Error` naming
|
|
690
|
+
* the label and the ceiling rather than `SemVer.make`'s bare schema failure.
|
|
691
|
+
*/
|
|
692
|
+
static next(current: SchemaVersion, change: WriteChange): SchemaVersion;
|
|
693
|
+
/**
|
|
694
|
+
* Derives the schema file name for a catalog name: `name.json`
|
|
695
|
+
* unversioned, `name-<version>.json` versioned.
|
|
696
|
+
*
|
|
697
|
+
* The name must be a simple file base name (no separators, no
|
|
698
|
+
* whitespace); anything else is a wiring mistake and throws.
|
|
699
|
+
*/
|
|
700
|
+
static fileName(name: string, version?: SchemaVersion): string;
|
|
701
|
+
/**
|
|
702
|
+
* The canonical URL a schema file is hosted at: `baseUrl` joined with
|
|
703
|
+
* {@link SchemaVersioning.fileName}.
|
|
704
|
+
*/
|
|
705
|
+
static schemaUrl(baseUrl: string, name: string, version?: SchemaVersion): string;
|
|
706
|
+
/**
|
|
707
|
+
* Assembles the `url`/`versions` half of a catalog entry.
|
|
708
|
+
*
|
|
709
|
+
* Omitting `versions` selects the unversioned mode (`url` only,
|
|
710
|
+
* pointing at the plain `name.json`). Providing them selects the
|
|
711
|
+
* versioned mode: the `versions` map carries every label, and `url`
|
|
712
|
+
* points at the latest version's file. An **empty** `versions` array is
|
|
713
|
+
* a contradiction (versioned mode with no versions) and throws — pass
|
|
714
|
+
* `undefined` for the unversioned mode.
|
|
715
|
+
*
|
|
716
|
+
* Labels are inserted in ascending {@link SchemaVersioning.Order} and
|
|
717
|
+
* stay that way on serialization. Requiring three components is what
|
|
718
|
+
* buys this: JavaScript enumerates array-index-like keys first, so the
|
|
719
|
+
* old grammar's bare-major label (`"2"`) jumped ahead of every dotted
|
|
720
|
+
* one regardless of insertion order. No SemVer label is integer-like,
|
|
721
|
+
* so that hazard is gone. Deriving ordering from the labels themselves
|
|
722
|
+
* (as {@link SchemaVersioning.latest} does) is still the robust read.
|
|
723
|
+
*/
|
|
724
|
+
static catalogUrls(options: {
|
|
725
|
+
readonly baseUrl: string;
|
|
726
|
+
readonly name: string;
|
|
727
|
+
readonly versions?: ReadonlyArray<SchemaVersion>;
|
|
728
|
+
}): CatalogUrls;
|
|
729
|
+
}
|
|
730
|
+
//#endregion
|
|
731
|
+
//#region src/CatalogEntry.d.ts
|
|
732
|
+
declare const CatalogLintFinding_base: Schema.Class<CatalogLintFinding, Schema.Struct<{
|
|
733
|
+
/** Which hygiene check fired. */
|
|
734
|
+
readonly check: Schema.Literals<readonly ["GenericFileMatch", "ComplexFileMatch"]>;
|
|
735
|
+
/** The `fileMatch` pattern the finding is about. */
|
|
736
|
+
readonly pattern: Schema.String;
|
|
737
|
+
/** Human-readable explanation with the SchemaStore rationale. */
|
|
738
|
+
readonly message: Schema.String;
|
|
739
|
+
}>, {}>;
|
|
740
|
+
/**
|
|
741
|
+
* A fileMatch hygiene finding: a value in a lint report, not an error —
|
|
742
|
+
* SchemaStore reviewers reject entries over these, so surfacing them
|
|
743
|
+
* locally is the point, but a warned entry is still a valid entry.
|
|
744
|
+
*
|
|
745
|
+
* @public
|
|
746
|
+
*/
|
|
747
|
+
export declare class CatalogLintFinding extends CatalogLintFinding_base {}
|
|
748
|
+
declare const CatalogEntry_base: Schema.Class<CatalogEntry, Schema.Struct<{
|
|
749
|
+
/** The schema's display name in the catalog. */
|
|
750
|
+
readonly name: Schema.String;
|
|
751
|
+
/** The catalog description. */
|
|
752
|
+
readonly description: Schema.String;
|
|
753
|
+
/** Glob patterns editors match files against. */
|
|
754
|
+
readonly fileMatch: Schema.$Array<Schema.String>;
|
|
755
|
+
/** The schema URL — the unversioned file, or the latest version. */
|
|
756
|
+
readonly url: Schema.String;
|
|
757
|
+
/**
|
|
758
|
+
* Versioned mode only: label → schema URL. Inserted ascending, but key
|
|
759
|
+
* order is not a contract — bare-major labels enumerate first (see
|
|
760
|
+
* `SchemaVersioning.catalogUrls`); derive ordering from the labels.
|
|
761
|
+
*/
|
|
762
|
+
readonly versions: Schema.optionalKey<Schema.$Record<Schema.String, Schema.String>>;
|
|
763
|
+
}>, {}>;
|
|
764
|
+
/**
|
|
765
|
+
* A SchemaStore `catalog.json` entry: the class is the schema, so decoding
|
|
766
|
+
* an existing entry and encoding one for submission are the same artifact.
|
|
767
|
+
* `versions` is present only for versioned catalogs
|
|
768
|
+
* ({@link SchemaVersioning.catalogUrls} assembles both modes).
|
|
769
|
+
*
|
|
770
|
+
* @public
|
|
771
|
+
*/
|
|
772
|
+
export declare class CatalogEntry extends CatalogEntry_base {
|
|
773
|
+
/**
|
|
774
|
+
* Assembles an entry from a catalog identity plus
|
|
775
|
+
* {@link SchemaVersioning.catalogUrls}' inputs: pass `versions` for the
|
|
776
|
+
* versioned mode (the `versions` map and latest-pointing `url` are
|
|
777
|
+
* derived), omit it for the unversioned mode.
|
|
778
|
+
*/
|
|
779
|
+
static assemble(options: {
|
|
780
|
+
readonly name: string;
|
|
781
|
+
readonly description: string;
|
|
782
|
+
readonly fileMatch: ReadonlyArray<string>;
|
|
783
|
+
readonly baseUrl: string;
|
|
784
|
+
readonly fileBaseName?: string;
|
|
785
|
+
readonly versions?: ReadonlyArray<SchemaVersion>;
|
|
786
|
+
}): CatalogEntry;
|
|
787
|
+
/**
|
|
788
|
+
* The fileMatch hygiene lint over this entry's patterns — pure shape
|
|
789
|
+
* analysis (no glob engine): generic patterns SchemaStore rejects and
|
|
790
|
+
* complex constructs it asks contributors to expand.
|
|
791
|
+
*/
|
|
792
|
+
lint(): ReadonlyArray<CatalogLintFinding>;
|
|
569
793
|
/**
|
|
570
|
-
*
|
|
571
|
-
*
|
|
572
|
-
* document and any consumer-serialized value cannot drift.
|
|
794
|
+
* {@link CatalogEntry.lint} over a bare pattern list, for callers
|
|
795
|
+
* checking patterns before an entry exists.
|
|
573
796
|
*/
|
|
574
|
-
|
|
797
|
+
static lintFileMatch(patterns: ReadonlyArray<string>): ReadonlyArray<CatalogLintFinding>;
|
|
575
798
|
}
|
|
576
799
|
//#endregion
|
|
577
800
|
//#region src/DocumentLint.d.ts
|
|
@@ -592,7 +815,7 @@ declare const DocumentLintFinding_base: Schema.Class<DocumentLintFinding, Schema
|
|
|
592
815
|
*
|
|
593
816
|
* @public
|
|
594
817
|
*/
|
|
595
|
-
declare class DocumentLintFinding extends DocumentLintFinding_base {}
|
|
818
|
+
export declare class DocumentLintFinding extends DocumentLintFinding_base {}
|
|
596
819
|
/**
|
|
597
820
|
* Owned structural checks over an assembled {@link StoreDocument} — the
|
|
598
821
|
* always-available half of the validation story (a real-engine gate like
|
|
@@ -603,7 +826,7 @@ declare class DocumentLintFinding extends DocumentLintFinding_base {}
|
|
|
603
826
|
* `#/definitions/...` pointer, is a warning).
|
|
604
827
|
* - `UnknownKeyword` — no keyword outside Draft-07 plus the declared
|
|
605
828
|
* non-standard families ({@link KeywordFamilies}: `x-taplo*`, `x-tombi-*`,
|
|
606
|
-
* `x-intellij-*` and the vscode set), which ajv strict mode would reject.
|
|
829
|
+
* `x-intellij-*`, `x-ai-*` and the vscode set), which ajv strict mode would reject.
|
|
607
830
|
* - `DescriptionWithoutUrl` — advisory: SchemaStore's description
|
|
608
831
|
* convention ends the root description with a docs URL line.
|
|
609
832
|
*
|
|
@@ -612,7 +835,7 @@ declare class DocumentLintFinding extends DocumentLintFinding_base {}
|
|
|
612
835
|
*
|
|
613
836
|
* @public
|
|
614
837
|
*/
|
|
615
|
-
declare class DocumentLint {
|
|
838
|
+
export declare class DocumentLint {
|
|
616
839
|
private constructor();
|
|
617
840
|
/**
|
|
618
841
|
* Runs every check; total — hostile nesting degrades to a
|
|
@@ -623,10 +846,12 @@ declare class DocumentLint {
|
|
|
623
846
|
//#endregion
|
|
624
847
|
//#region src/KeywordFamilies.d.ts
|
|
625
848
|
/**
|
|
626
|
-
* The one owner of the declared non-standard keyword families
|
|
627
|
-
*
|
|
628
|
-
*
|
|
629
|
-
*
|
|
849
|
+
* The one owner of the declared non-standard keyword families, in two
|
|
850
|
+
* groups.
|
|
851
|
+
*
|
|
852
|
+
* **Upstream language-server families** — mirrored from SchemaStore's
|
|
853
|
+
* CONTRIBUTING, the keyword sets legitimately consumed by editor
|
|
854
|
+
* toolchains that ajv strict mode would otherwise reject:
|
|
630
855
|
*
|
|
631
856
|
* - **vscode-json-languageservice** (exact names): `allowTrailingCommas`,
|
|
632
857
|
* `defaultSnippets`, `enumDescriptions`, `markdownDescription`,
|
|
@@ -639,241 +864,67 @@ declare class DocumentLint {
|
|
|
639
864
|
* - **IntelliJ**: the `x-intellij-` prefix (`x-intellij-language-injection`,
|
|
640
865
|
* `x-intellij-html-description`, `x-intellij-enum-metadata`).
|
|
641
866
|
*
|
|
867
|
+
* **The house machine-annotation family** — `x-ai-` (WITH the trailing
|
|
868
|
+
* dash; bare `x-ai` and a look-alike prefix like `x-aida-foo` are NOT
|
|
869
|
+
* declared), owned by this package rather than mirrored from anywhere:
|
|
870
|
+
*
|
|
871
|
+
* - It is a NAMESPACE, not a vocabulary — any `x-ai-*` key is declared, and
|
|
872
|
+
* this package does not enumerate specific keys.
|
|
873
|
+
* - The key itself must be one ajv can register: after the prefix, only
|
|
874
|
+
* `[A-Za-z0-9_$:-]` (ajv holds a keyword name to
|
|
875
|
+
* `/^[a-z_$][a-z0-9_$:-]*$/i`). A dot, a space, a slash, an `@`, a `+` or
|
|
876
|
+
* any non-ASCII character makes the engine gate reject the whole document
|
|
877
|
+
* — as a root-pathed `ValidationFinding`, not an error.
|
|
878
|
+
* - A value under a declared `x-ai-*` key must be JSON — `CanonicalJson`
|
|
879
|
+
* fails typed (`NonJsonValueError`) on anything else, the same as
|
|
880
|
+
* every other emitted value.
|
|
881
|
+
* - The one recommended, non-binding key is `x-ai-hint`: a string carrying
|
|
882
|
+
* an instruction to a machine reader about the annotated value.
|
|
883
|
+
* - `x-ai-example` is deliberately NOT recommended. Draft-07's own
|
|
884
|
+
* `examples` keyword already exists, is carried by the assembly, and
|
|
885
|
+
* classifies as a CONTRACT change in `DocumentDiff`; an `x-ai-*`
|
|
886
|
+
* key classifies as ANNOTATIONS. The two would be two example channels
|
|
887
|
+
* with opposite version semantics.
|
|
888
|
+
* - A declared-family value must not contain an `$id` — or a repeated
|
|
889
|
+
* `$anchor` — at ANY depth, not merely as its own top-level key: ajv's
|
|
890
|
+
* reference collection walks unknown keywords looking for them, so a
|
|
891
|
+
* colliding one buried anywhere inside an annotation payload fails the
|
|
892
|
+
* compile, surfacing as a blocking root-pathed `ValidationFinding` rather
|
|
893
|
+
* than a silent no-op. An empty-string `$id` collides too — it resolves
|
|
894
|
+
* to the root id.
|
|
895
|
+
* - No upstream tool sanctions `x-ai-`: a document carrying it that is
|
|
896
|
+
* submitted to schemastore.org needs the corresponding entry added to
|
|
897
|
+
* that repo's own validation config. Until then it is intended for
|
|
898
|
+
* self-hosted publication.
|
|
899
|
+
* - `DocumentDiff` classifies a delta confined to `x-ai-*` keys as
|
|
900
|
+
* `"annotations"`, so adopting the family on an already-published
|
|
901
|
+
* versioned document rewrites that file in place — correct, because
|
|
902
|
+
* annotations are transparently replaceable.
|
|
903
|
+
*
|
|
642
904
|
* Both consumers of the registry route through {@link KeywordFamilies.isDeclared}:
|
|
643
905
|
* `DocumentLint`'s `UnknownKeyword` check (a declared key is not flagged) and
|
|
644
|
-
* `
|
|
645
|
-
*
|
|
906
|
+
* `StoreDocument.fromSchema`'s gate (a key outside the families fails the
|
|
907
|
+
* build rather than being emitted). One predicate, so the lint and the gate
|
|
908
|
+
* cannot drift.
|
|
646
909
|
*/
|
|
647
910
|
/**
|
|
648
911
|
* The declared non-standard keyword families as one predicate: the
|
|
649
912
|
* vscode-json-languageservice set by exact name, plus the `x-taplo`,
|
|
650
|
-
* `x-tombi-` and `x-
|
|
913
|
+
* `x-tombi-`, `x-intellij-` and `x-ai-` prefixes.
|
|
651
914
|
*
|
|
652
915
|
* @public
|
|
653
916
|
*/
|
|
654
|
-
declare class KeywordFamilies {
|
|
917
|
+
export declare class KeywordFamilies {
|
|
655
918
|
private constructor();
|
|
656
919
|
/**
|
|
657
920
|
* Whether `key` belongs to a declared non-standard keyword family.
|
|
658
921
|
* Draft-07's own keywords are a separate vocabulary — this predicate
|
|
659
|
-
* answers only for the language-server extension families
|
|
922
|
+
* answers only for the language-server extension families and the
|
|
923
|
+
* house `x-ai-` machine-annotation namespace.
|
|
660
924
|
*/
|
|
661
925
|
static isDeclared(key: string): boolean;
|
|
662
926
|
}
|
|
663
927
|
//#endregion
|
|
664
|
-
//#region src/SchemaFile.d.ts
|
|
665
|
-
declare const SchemaFileReadError_base: Schema.Class<SchemaFileReadError, Schema.TaggedStruct<"SchemaFileReadError", {
|
|
666
|
-
/** The path that could not be read. */
|
|
667
|
-
readonly path: Schema.String;
|
|
668
|
-
/** The underlying filesystem failure, preserved structurally. */
|
|
669
|
-
readonly cause: Schema.Defect;
|
|
670
|
-
}>, import("effect/Cause").YieldableError>;
|
|
671
|
-
/**
|
|
672
|
-
* Indicates that a schema file could not be read from the filesystem (a
|
|
673
|
-
* filesystem error other than not-found).
|
|
674
|
-
*
|
|
675
|
-
* @public
|
|
676
|
-
*/
|
|
677
|
-
declare class SchemaFileReadError extends SchemaFileReadError_base {
|
|
678
|
-
get message(): string;
|
|
679
|
-
}
|
|
680
|
-
declare const SchemaFileNotFoundError_base: Schema.Class<SchemaFileNotFoundError, Schema.TaggedStruct<"SchemaFileNotFoundError", {
|
|
681
|
-
/** The path where the schema file was expected. */
|
|
682
|
-
readonly path: Schema.String;
|
|
683
|
-
}>, import("effect/Cause").YieldableError>;
|
|
684
|
-
/**
|
|
685
|
-
* Indicates that no schema file exists at the expected path. Carries its
|
|
686
|
-
* own tag for `catchTag` routing.
|
|
687
|
-
*
|
|
688
|
-
* @public
|
|
689
|
-
*/
|
|
690
|
-
declare class SchemaFileNotFoundError extends SchemaFileNotFoundError_base {
|
|
691
|
-
get message(): string;
|
|
692
|
-
}
|
|
693
|
-
declare const SchemaFileWriteError_base: Schema.Class<SchemaFileWriteError, Schema.TaggedStruct<"SchemaFileWriteError", {
|
|
694
|
-
/** The path that could not be written. */
|
|
695
|
-
readonly path: Schema.String;
|
|
696
|
-
/** The underlying filesystem failure, preserved structurally. */
|
|
697
|
-
readonly cause: Schema.Defect;
|
|
698
|
-
}>, import("effect/Cause").YieldableError>;
|
|
699
|
-
/**
|
|
700
|
-
* Indicates that a schema file could not be written to the filesystem.
|
|
701
|
-
* Narrowed to the filesystem failure only — a serialization failure
|
|
702
|
-
* surfaces as its own `CanonicalJsonError`, never wrapped here.
|
|
703
|
-
*
|
|
704
|
-
* @public
|
|
705
|
-
*/
|
|
706
|
-
declare class SchemaFileWriteError extends SchemaFileWriteError_base {
|
|
707
|
-
get message(): string;
|
|
708
|
-
}
|
|
709
|
-
/**
|
|
710
|
-
* What {@link SchemaFileShape.write} did to the filesystem: `"written"`
|
|
711
|
-
* when it wrote, `"unchanged"` when it left the file alone — reported as a
|
|
712
|
-
* value so the caller decides what to surface, never a log.
|
|
713
|
-
*
|
|
714
|
-
* @public
|
|
715
|
-
*/
|
|
716
|
-
type WriteOutcome = "written" | "unchanged";
|
|
717
|
-
/**
|
|
718
|
-
* How the document being written relates to what was already on disk:
|
|
719
|
-
* {@link SchemaChange} plus `"created"` for a file that did not exist, so
|
|
720
|
-
* there was nothing to compare against.
|
|
721
|
-
*
|
|
722
|
-
* @public
|
|
723
|
-
*/
|
|
724
|
-
type WriteChange = SchemaChange | "created";
|
|
725
|
-
/**
|
|
726
|
-
* The result of {@link SchemaFileShape.write}: what happened to the file,
|
|
727
|
-
* and what the difference MEANT.
|
|
728
|
-
*
|
|
729
|
-
* The two are independent on purpose. `change` answers the versioning
|
|
730
|
-
* question — `"annotations"` means only prose and editor affordances moved,
|
|
731
|
-
* so the document replaces its predecessor transparently and needs no new
|
|
732
|
-
* {@link SchemaVersioning} version, while `"contract"` means an assertion
|
|
733
|
-
* keyword moved and a consumer's document valid yesterday may be invalid
|
|
734
|
-
* today. `outcome` answers only whether bytes were written, which under
|
|
735
|
-
* `compare: "bytes"` can be `"written"` even when `change` is `"none"`.
|
|
736
|
-
*
|
|
737
|
-
* @public
|
|
738
|
-
*/
|
|
739
|
-
interface WriteResult {
|
|
740
|
-
/**
|
|
741
|
-
* Whether the file was written. **This is the authoritative answer to
|
|
742
|
-
* "did the filesystem get touched"** — always, under either `compare`
|
|
743
|
-
* mode. Do not infer it from `change`: under `compare: "bytes"` a
|
|
744
|
-
* `change` of `"none"` still writes.
|
|
745
|
-
*/
|
|
746
|
-
readonly outcome: WriteOutcome;
|
|
747
|
-
/** What differs between the previous content and the new document. */
|
|
748
|
-
readonly change: WriteChange;
|
|
749
|
-
}
|
|
750
|
-
/**
|
|
751
|
-
* The result of {@link SchemaFileShape.check}: the same two answers
|
|
752
|
-
* {@link WriteResult} carries, for a call that touched nothing.
|
|
753
|
-
*
|
|
754
|
-
* `wouldWrite` is `outcome`'s counterpart — it honors `compare`, so it
|
|
755
|
-
* answers "would `write` do anything with these same options", which
|
|
756
|
-
* `change` alone cannot under `compare: "bytes"`.
|
|
757
|
-
*
|
|
758
|
-
* @public
|
|
759
|
-
*/
|
|
760
|
-
interface CheckResult {
|
|
761
|
-
/** Whether a `write` with the same options would touch the file. */
|
|
762
|
-
readonly wouldWrite: boolean;
|
|
763
|
-
/** What differs between the on-disk content and the new document. */
|
|
764
|
-
readonly change: WriteChange;
|
|
765
|
-
}
|
|
766
|
-
/**
|
|
767
|
-
* Options for {@link SchemaFileShape.write} and
|
|
768
|
-
* {@link SchemaFileShape.check}: the {@link CanonicalJsonOptions} the
|
|
769
|
-
* document serializes under, plus how `write` decides whether to touch the
|
|
770
|
-
* file.
|
|
771
|
-
*
|
|
772
|
-
* @public
|
|
773
|
-
*/
|
|
774
|
-
interface SchemaWriteOptions extends CanonicalJsonOptions {
|
|
775
|
-
/**
|
|
776
|
-
* How `write` decides the file needs rewriting:
|
|
777
|
-
*
|
|
778
|
-
* - `"value"` (the default) — compare the parsed content. Immune to any
|
|
779
|
-
* other tool that reformats the file, which is the common case: a repo
|
|
780
|
-
* whose pre-commit hook runs Biome or Prettier over `*.json` would
|
|
781
|
-
* otherwise see every run rewrite the file forever, because the
|
|
782
|
-
* formatter's bytes never match `CanonicalJson`'s.
|
|
783
|
-
* - `"bytes"` — compare the exact text, so the file on disk is only ever
|
|
784
|
-
* `CanonicalJson`'s own output. Choose this when the emitted bytes are
|
|
785
|
-
* themselves the artifact and no other tool is allowed to touch them.
|
|
786
|
-
*
|
|
787
|
-
* `change` in the {@link WriteResult} is classified by content either
|
|
788
|
-
* way; this option decides only whether a byte-level difference is
|
|
789
|
-
* enough to rewrite.
|
|
790
|
-
*/
|
|
791
|
-
readonly compare?: "bytes" | "value";
|
|
792
|
-
}
|
|
793
|
-
/**
|
|
794
|
-
* The shape of the {@link SchemaFile} service — the value produced by
|
|
795
|
-
* {@link SchemaFile.make} and carried by its layer.
|
|
796
|
-
*
|
|
797
|
-
* @public
|
|
798
|
-
*/
|
|
799
|
-
interface SchemaFileShape {
|
|
800
|
-
/**
|
|
801
|
-
* Read a schema file's exact text (the drift-test read side: compare it
|
|
802
|
-
* against `StoreDocument.serializeResult`). Fails with
|
|
803
|
-
* `SchemaFileNotFoundError` (ENOENT) or `SchemaFileReadError` (other
|
|
804
|
-
* filesystem errors).
|
|
805
|
-
*/
|
|
806
|
-
readonly read: (path: string) => Effect.Effect<string, SchemaFileReadError | SchemaFileNotFoundError>;
|
|
807
|
-
/**
|
|
808
|
-
* Serialize a document to canonical JSON and write it **only if the
|
|
809
|
-
* on-disk content differs** (a missing file counts as different),
|
|
810
|
-
* creating parent directories as needed. Answers a {@link WriteResult}
|
|
811
|
-
* as a value: what happened to the file, and what the difference meant.
|
|
812
|
-
* Fails with a `CanonicalJsonError` (the document does not serialize),
|
|
813
|
-
* `SchemaFileReadError` (the existing content could not be read for
|
|
814
|
-
* comparison) or `SchemaFileWriteError` (the filesystem write failed).
|
|
815
|
-
*/
|
|
816
|
-
readonly write: (path: string, document: StoreDocument, options?: SchemaWriteOptions) => Effect.Effect<WriteResult, CanonicalJsonError | SchemaFileReadError | SchemaFileWriteError>;
|
|
817
|
-
/**
|
|
818
|
-
* The same comparison {@link SchemaFileShape.write} makes, **without
|
|
819
|
-
* touching the filesystem** — the drift-check half of the pair, for a
|
|
820
|
-
* CI job that must assert a committed schema is current rather than
|
|
821
|
-
* regenerate it.
|
|
822
|
-
*
|
|
823
|
-
* Answers both questions the writer answers: `change` classifies the
|
|
824
|
-
* content (immune to a formatter having reflowed the committed file),
|
|
825
|
-
* and `wouldWrite` honors `compare`, so it agrees with `write` under
|
|
826
|
-
* either mode. Checking drift is `change`; predicting the writer is
|
|
827
|
-
* `wouldWrite`.
|
|
828
|
-
*/
|
|
829
|
-
readonly check: (path: string, document: StoreDocument, options?: SchemaWriteOptions) => Effect.Effect<CheckResult, CanonicalJsonError | SchemaFileReadError>;
|
|
830
|
-
}
|
|
831
|
-
declare const SchemaFile_base: Context.ServiceClass<SchemaFile, "@effected/schemastore/SchemaFile", SchemaFileShape>;
|
|
832
|
-
/**
|
|
833
|
-
* Reads and writes emitted schema documents over core `FileSystem` /
|
|
834
|
-
* `Path` — the package's one IO surface. The layer requires those
|
|
835
|
-
* services; provide `@effect/platform-node`'s `NodeFileSystem` / `NodePath`
|
|
836
|
-
* (or a bun equivalent) at the application boundary.
|
|
837
|
-
*
|
|
838
|
-
* `write` is write-if-changed, and by default compares **content**: an
|
|
839
|
-
* unchanged document never touches the file even if another tool has
|
|
840
|
-
* reformatted it, so a generator committed to a repo whose pre-commit hook
|
|
841
|
-
* formats JSON does not churn on every run. It also reports what the
|
|
842
|
-
* difference meant — `"annotations"` (prose only, replaces its predecessor
|
|
843
|
-
* transparently) versus `"contract"` (an assertion moved, so a new
|
|
844
|
-
* `SchemaVersioning` version is warranted). `check` makes the same
|
|
845
|
-
* comparison without writing, which is what a CI drift job wants.
|
|
846
|
-
*
|
|
847
|
-
* @example
|
|
848
|
-
* ```ts
|
|
849
|
-
* import { SchemaFile, StoreDocument } from "@effected/schemastore";
|
|
850
|
-
* import { NodeFileSystem, NodePath } from "@effect/platform-node";
|
|
851
|
-
* import { Effect, Layer, Schema } from "effect";
|
|
852
|
-
*
|
|
853
|
-
* const program = Effect.gen(function* () {
|
|
854
|
-
* const files = yield* SchemaFile;
|
|
855
|
-
* const document = yield* StoreDocument.fromSchema(Schema.Struct({ name: Schema.String }), {
|
|
856
|
-
* $id: "https://example.com/config.schema.json",
|
|
857
|
-
* });
|
|
858
|
-
* return yield* files.write("schemas/config.schema.json", document);
|
|
859
|
-
* }).pipe(
|
|
860
|
-
* Effect.provide(SchemaFile.layer),
|
|
861
|
-
* Effect.provide(Layer.mergeAll(NodeFileSystem.layer, NodePath.layer)),
|
|
862
|
-
* );
|
|
863
|
-
* ```
|
|
864
|
-
*
|
|
865
|
-
* @public
|
|
866
|
-
*/
|
|
867
|
-
declare class SchemaFile extends SchemaFile_base {
|
|
868
|
-
/** Build the service implementation from `FileSystem` / `Path` in context; use {@link SchemaFile.layer} to provide it. */
|
|
869
|
-
static readonly make: Effect.Effect<SchemaFileShape, never, FileSystem.FileSystem | Path.Path>;
|
|
870
|
-
/**
|
|
871
|
-
* The live layer. Requires core `FileSystem` / `Path`, provided by the
|
|
872
|
-
* consumer's platform implementation at the edge.
|
|
873
|
-
*/
|
|
874
|
-
static readonly layer: Layer.Layer<SchemaFile, never, FileSystem.FileSystem | Path.Path>;
|
|
875
|
-
}
|
|
876
|
-
//#endregion
|
|
877
928
|
//#region src/SchemaTarget.d.ts
|
|
878
929
|
/**
|
|
879
930
|
* A single schema publication target: an Effect Schema source paired with
|
|
@@ -886,7 +937,7 @@ declare class SchemaFile extends SchemaFile_base {
|
|
|
886
937
|
*
|
|
887
938
|
* @public
|
|
888
939
|
*/
|
|
889
|
-
interface SchemaTarget {
|
|
940
|
+
export interface SchemaTarget {
|
|
890
941
|
/** The Effect Schema source the document is generated from. */
|
|
891
942
|
readonly schema: Schema.Constraint;
|
|
892
943
|
/** The canonical `$id` URL the generated document declares. */
|
|
@@ -903,7 +954,20 @@ interface SchemaTarget {
|
|
|
903
954
|
readonly name?: string;
|
|
904
955
|
/** The destination path the document is written to (`SchemaFile`). */
|
|
905
956
|
readonly path: string;
|
|
906
|
-
/**
|
|
957
|
+
/**
|
|
958
|
+
* The version label, for versioned catalog mode. Omit for unversioned.
|
|
959
|
+
*
|
|
960
|
+
* It carries a second meaning the catalog does not: presence of a
|
|
961
|
+
* **pinned** label (one with no prerelease) declares that consumers pin
|
|
962
|
+
* this document's URL, so `SchemaPipeline.run` refuses to rewrite it in
|
|
963
|
+
* place when its validation contract changes — bump `version`, `$id` and
|
|
964
|
+
* `path` together instead, or pass `contractChanges: "allow"`. That is
|
|
965
|
+
* only coherent when the version participates in `path`
|
|
966
|
+
* (`schemas/<version>/<name>-<version>.json`): a versioned target at a
|
|
967
|
+
* fixed path compares the same file forever, and bumping `version` does
|
|
968
|
+
* not move it. A prerelease label declares its own instability and is
|
|
969
|
+
* rewritten in place.
|
|
970
|
+
*/
|
|
907
971
|
readonly version?: SchemaVersion;
|
|
908
972
|
}
|
|
909
973
|
/**
|
|
@@ -911,7 +975,7 @@ interface SchemaTarget {
|
|
|
911
975
|
*
|
|
912
976
|
* @public
|
|
913
977
|
*/
|
|
914
|
-
declare class SchemaTarget {
|
|
978
|
+
export declare class SchemaTarget {
|
|
915
979
|
private constructor();
|
|
916
980
|
/**
|
|
917
981
|
* Builds an unversioned target. `name` is optional — only catalog
|
|
@@ -954,7 +1018,7 @@ declare const SchemaValidatorError_base: Schema.Class<SchemaValidatorError, Sche
|
|
|
954
1018
|
*
|
|
955
1019
|
* @public
|
|
956
1020
|
*/
|
|
957
|
-
declare class SchemaValidatorError extends SchemaValidatorError_base {
|
|
1021
|
+
export declare class SchemaValidatorError extends SchemaValidatorError_base {
|
|
958
1022
|
get message(): string;
|
|
959
1023
|
}
|
|
960
1024
|
declare const ValidationFinding_base: Schema.Class<ValidationFinding, Schema.Struct<{
|
|
@@ -972,7 +1036,7 @@ declare const ValidationFinding_base: Schema.Class<ValidationFinding, Schema.Str
|
|
|
972
1036
|
*
|
|
973
1037
|
* @public
|
|
974
1038
|
*/
|
|
975
|
-
declare class ValidationFinding extends ValidationFinding_base {}
|
|
1039
|
+
export declare class ValidationFinding extends ValidationFinding_base {}
|
|
976
1040
|
/**
|
|
977
1041
|
* Options for {@link SchemaValidatorShape.validate}.
|
|
978
1042
|
*
|
|
@@ -1038,16 +1102,19 @@ declare const SchemaValidator_base: Context.ServiceClass<SchemaValidator, "@effe
|
|
|
1038
1102
|
*
|
|
1039
1103
|
* @public
|
|
1040
1104
|
*/
|
|
1041
|
-
declare class SchemaValidator extends SchemaValidator_base {
|
|
1105
|
+
export declare class SchemaValidator extends SchemaValidator_base {
|
|
1042
1106
|
/**
|
|
1043
1107
|
* The shipped ajv implementation — the default a consumer provides.
|
|
1044
1108
|
*
|
|
1045
1109
|
* `validate` checks the document against the Draft-07 meta-schema and
|
|
1046
1110
|
* then compiles it, reporting BOTH as {@link ValidationFinding} values:
|
|
1047
1111
|
* meta-schema failures keep ajv's structured `instancePath` and
|
|
1048
|
-
* `keyword`, while a
|
|
1049
|
-
*
|
|
1050
|
-
*
|
|
1112
|
+
* `keyword`, while a rejection ajv raises by *throwing* becomes a
|
|
1113
|
+
* root-pathed finding — both a strict-mode compile failure and a
|
|
1114
|
+
* declared keyword whose NAME ajv's own grammar
|
|
1115
|
+
* (`/^[a-z_$][a-z0-9_$:-]*$/i`) refuses, such as an `x-ai-*` key
|
|
1116
|
+
* carrying a dot or a space. The error channel stays reserved for the
|
|
1117
|
+
* engine failing as a mechanism.
|
|
1051
1118
|
*
|
|
1052
1119
|
* `strict` defaults to `true` — SchemaStore's gate. Each call builds its
|
|
1053
1120
|
* own ajv instance, so documents sharing an `$id` never collide.
|
|
@@ -1094,7 +1161,7 @@ declare const PipelineFinding_base: Schema.Class<PipelineFinding, Schema.Struct<
|
|
|
1094
1161
|
*
|
|
1095
1162
|
* @public
|
|
1096
1163
|
*/
|
|
1097
|
-
declare class PipelineFinding extends PipelineFinding_base {
|
|
1164
|
+
export declare class PipelineFinding extends PipelineFinding_base {
|
|
1098
1165
|
/**
|
|
1099
1166
|
* What to call this finding when rendering it: the check name when the
|
|
1100
1167
|
* gate named one, the gate itself otherwise.
|
|
@@ -1118,7 +1185,64 @@ declare const SchemaGateError_base: Schema.Class<SchemaGateError, Schema.TaggedS
|
|
|
1118
1185
|
*
|
|
1119
1186
|
* @public
|
|
1120
1187
|
*/
|
|
1121
|
-
declare class SchemaGateError extends SchemaGateError_base {
|
|
1188
|
+
export declare class SchemaGateError extends SchemaGateError_base {
|
|
1189
|
+
get message(): string;
|
|
1190
|
+
}
|
|
1191
|
+
/**
|
|
1192
|
+
* How {@link SchemaPipeline.run} treats a target whose document would change
|
|
1193
|
+
* its validation contract.
|
|
1194
|
+
*
|
|
1195
|
+
* - `"block-versioned"` (the default) — a target carrying a PINNED `version`
|
|
1196
|
+
* ({@link SchemaVersioning.isPinned}) is a published, URL-pinned document:
|
|
1197
|
+
* a `"contract"` change fails with {@link SchemaContractChangeError} BEFORE
|
|
1198
|
+
* any write. A target with no `version`, or with a prerelease label, is a
|
|
1199
|
+
* document that replaces its predecessor in place and is rewritten as
|
|
1200
|
+
* before.
|
|
1201
|
+
* - `"allow"` — classify and report only, never refuse: the pre-guard
|
|
1202
|
+
* behaviour. Also the sanctioned REPAIR path for a published file whose
|
|
1203
|
+
* text no longer parses — `SchemaFile` classifies unparseable text as
|
|
1204
|
+
* `"contract"` so it stays regenerable, and under the default that
|
|
1205
|
+
* classification is refused.
|
|
1206
|
+
*
|
|
1207
|
+
* The policy reads `change`, which is content-classified under either
|
|
1208
|
+
* `write.compare` mode, so `"bytes"` neither strengthens nor weakens it.
|
|
1209
|
+
*
|
|
1210
|
+
* The policy is only coherent when the version participates in `path`
|
|
1211
|
+
* (`schemas/<version>/<name>-<version>.json`): a versioned target at a fixed
|
|
1212
|
+
* path compares the same file forever, and bumping `version` does not move
|
|
1213
|
+
* it.
|
|
1214
|
+
*
|
|
1215
|
+
* @public
|
|
1216
|
+
*/
|
|
1217
|
+
type ContractChangePolicy = "block-versioned" | "allow";
|
|
1218
|
+
declare const ContractChangeTarget_base: Schema.Class<ContractChangeTarget, Schema.Struct<{
|
|
1219
|
+
/** The target's `$id`. */
|
|
1220
|
+
readonly $id: Schema.String;
|
|
1221
|
+
/** The path the document would have been written to. */
|
|
1222
|
+
readonly path: Schema.String;
|
|
1223
|
+
/** The target's pinned label. */
|
|
1224
|
+
readonly version: Schema.brand<Schema.String, "SchemaVersion">;
|
|
1225
|
+
/** The label to publish under instead — {@link SchemaVersioning.next} of `version`. */
|
|
1226
|
+
readonly nextVersion: Schema.brand<Schema.String, "SchemaVersion">;
|
|
1227
|
+
}>, {}>;
|
|
1228
|
+
/**
|
|
1229
|
+
* One published document whose validation contract would change.
|
|
1230
|
+
*
|
|
1231
|
+
* @public
|
|
1232
|
+
*/
|
|
1233
|
+
export declare class ContractChangeTarget extends ContractChangeTarget_base {}
|
|
1234
|
+
declare const SchemaContractChangeError_base: Schema.Class<SchemaContractChangeError, Schema.TaggedStruct<"SchemaContractChangeError", {
|
|
1235
|
+
/** Every published target whose contract would change, in target order. */
|
|
1236
|
+
readonly targets: Schema.$Array<typeof ContractChangeTarget>;
|
|
1237
|
+
}>, import("effect/Cause").YieldableError>;
|
|
1238
|
+
/**
|
|
1239
|
+
* Indicates that at least one published target's contract changed under the
|
|
1240
|
+
* active {@link ContractChangePolicy}. Raised BEFORE any target is written
|
|
1241
|
+
* and total over the targets, so two broken documents surface in one run.
|
|
1242
|
+
*
|
|
1243
|
+
* @public
|
|
1244
|
+
*/
|
|
1245
|
+
export declare class SchemaContractChangeError extends SchemaContractChangeError_base {
|
|
1122
1246
|
get message(): string;
|
|
1123
1247
|
}
|
|
1124
1248
|
/**
|
|
@@ -1161,6 +1285,17 @@ interface PipelineCheckResult {
|
|
|
1161
1285
|
* never mistaken for clean drift.
|
|
1162
1286
|
*/
|
|
1163
1287
|
readonly blocked: boolean;
|
|
1288
|
+
/**
|
|
1289
|
+
* Whether the {@link ContractChangePolicy} would refuse this write.
|
|
1290
|
+
*
|
|
1291
|
+
* Read it side by side with {@link PipelineCheckResult.blocked}: `blocked`
|
|
1292
|
+
* answers "would findings block a run under `blocking`", while
|
|
1293
|
+
* `contractBlocked` answers "would the contract policy refuse this write
|
|
1294
|
+
* under `contractChanges`". A drift test that reads `contractBlocked` can
|
|
1295
|
+
* print the right remedy — "regenerate" is wrong advice for a target the
|
|
1296
|
+
* generator will refuse; the fix is a version bump.
|
|
1297
|
+
*/
|
|
1298
|
+
readonly contractBlocked: boolean;
|
|
1164
1299
|
/** What differs between the on-disk content and the new document. */
|
|
1165
1300
|
readonly change: WriteChange;
|
|
1166
1301
|
/** Every finding, blocking or not. */
|
|
@@ -1185,16 +1320,25 @@ interface SchemaPipelineOptions {
|
|
|
1185
1320
|
*
|
|
1186
1321
|
* **Which findings can actually reach you here.** A `SchemaTarget`
|
|
1187
1322
|
* carries a `Schema`, so the pipeline's documents come from
|
|
1188
|
-
* `StoreDocument.fromSchema` —
|
|
1189
|
-
* keyword
|
|
1190
|
-
*
|
|
1191
|
-
*
|
|
1192
|
-
*
|
|
1323
|
+
* `StoreDocument.fromSchema` — which never admits an undeclared
|
|
1324
|
+
* keyword: the pipeline supplies no `includeAnnotationKey`, and one
|
|
1325
|
+
* that admitted anything outside the declared families would fail the
|
|
1326
|
+
* build. An undeclared keyword therefore never exists to be linted.
|
|
1327
|
+
* Through this entry point `UnknownKeyword` is effectively unreachable,
|
|
1328
|
+
* and **the engine gate is what blocks in practice**. The lint's warning checks earn their keep on
|
|
1193
1329
|
* documents this pipeline did not build — a hand-assembled
|
|
1194
1330
|
* `StoreDocument.draft07`, or one read back off disk — and on depth,
|
|
1195
1331
|
* which a schema can genuinely exceed.
|
|
1196
1332
|
*/
|
|
1197
1333
|
readonly blocking?: (finding: PipelineFinding) => boolean;
|
|
1334
|
+
/**
|
|
1335
|
+
* How {@link SchemaPipeline.run} treats a target whose document would
|
|
1336
|
+
* change its validation contract. Defaults to `"block-versioned"`: a
|
|
1337
|
+
* target carrying a pinned `version` is refused rather than rewritten in
|
|
1338
|
+
* place. Pass `"allow"` to classify and report only — including to repair
|
|
1339
|
+
* a published file whose on-disk text no longer parses.
|
|
1340
|
+
*/
|
|
1341
|
+
readonly contractChanges?: ContractChangePolicy;
|
|
1198
1342
|
/** Passed through to `SchemaValidator.validate`. */
|
|
1199
1343
|
readonly validator?: SchemaValidatorOptions;
|
|
1200
1344
|
/** Passed through to `SchemaFile.write` / `SchemaFile.check`. */
|
|
@@ -1233,17 +1377,49 @@ interface SchemaPipelineOptions {
|
|
|
1233
1377
|
*
|
|
1234
1378
|
* @public
|
|
1235
1379
|
*/
|
|
1236
|
-
declare class SchemaPipeline {
|
|
1380
|
+
export declare class SchemaPipeline {
|
|
1237
1381
|
private constructor();
|
|
1238
1382
|
/**
|
|
1239
1383
|
* Run every target: build its document, gather both gates' findings,
|
|
1240
|
-
* fail with a {@link SchemaGateError} if any block,
|
|
1384
|
+
* fail with a {@link SchemaGateError} if any block, refuse a published
|
|
1385
|
+
* target whose contract changed, and write otherwise.
|
|
1241
1386
|
*
|
|
1242
|
-
*
|
|
1243
|
-
*
|
|
1244
|
-
*
|
|
1387
|
+
* **The run writes nothing unless every target passes both gates.** It
|
|
1388
|
+
* is two-phase: every target is generated, gated and (for a target the
|
|
1389
|
+
* {@link ContractChangePolicy} guards) compared against its predecessor
|
|
1390
|
+
* before any file is touched, and only then are the held documents
|
|
1391
|
+
* written in target order. A gate failure on the third target therefore
|
|
1392
|
+
* leaves the first two unwritten.
|
|
1393
|
+
*
|
|
1394
|
+
* Phase 2 itself is sequential and **not transactional**: a filesystem or
|
|
1395
|
+
* serialization failure part-way through it leaves the targets already
|
|
1396
|
+
* written in place, with no rollback. The guarantee is "no writes unless
|
|
1397
|
+
* every gate passes", not "every write or none".
|
|
1398
|
+
*
|
|
1399
|
+
* The gates run in a fixed precedence: {@link SchemaGateError} is
|
|
1400
|
+
* fail-fast on the first blocked target, because a document the engine
|
|
1401
|
+
* rejects would never be written under any contract policy, so its
|
|
1402
|
+
* classification is noise. {@link SchemaContractChangeError} is total
|
|
1403
|
+
* over the remaining targets, so two published documents whose contracts
|
|
1404
|
+
* moved surface in one run.
|
|
1405
|
+
*
|
|
1406
|
+
* @example
|
|
1407
|
+
* ```ts
|
|
1408
|
+
* import { SchemaContractChangeError, SchemaPipeline } from "@effected/schemastore";
|
|
1409
|
+
* import { Effect } from "effect";
|
|
1410
|
+
*
|
|
1411
|
+
* declare const targets: Parameters<typeof SchemaPipeline.run>[0];
|
|
1412
|
+
*
|
|
1413
|
+
* const program = SchemaPipeline.run(targets).pipe(
|
|
1414
|
+
* Effect.catchTag("SchemaContractChangeError", (error: SchemaContractChangeError) =>
|
|
1415
|
+
* Effect.succeed(
|
|
1416
|
+
* error.targets.map((target) => `${target.$id}: ${target.version} -> ${target.nextVersion}`),
|
|
1417
|
+
* ),
|
|
1418
|
+
* ),
|
|
1419
|
+
* );
|
|
1420
|
+
* ```
|
|
1245
1421
|
*/
|
|
1246
|
-
static run(targets: ReadonlyArray<SchemaTarget>, options?: SchemaPipelineOptions): Effect.Effect<ReadonlyArray<PipelineResult>, SchemaGateError | SchemaConversionError | SchemaValidatorError | CanonicalJsonError | SchemaFileReadError | SchemaFileWriteError, SchemaFile | SchemaValidator>;
|
|
1422
|
+
static run(targets: ReadonlyArray<SchemaTarget>, options?: SchemaPipelineOptions): Effect.Effect<ReadonlyArray<PipelineResult>, SchemaGateError | SchemaContractChangeError | SchemaConversionError | UndeclaredAnnotationKeyError | SchemaValidatorError | CanonicalJsonError | SchemaFileReadError | SchemaFileWriteError, SchemaFile | SchemaValidator>;
|
|
1247
1423
|
/**
|
|
1248
1424
|
* The same walk with **no writes** — the drift-check counterpart, for a
|
|
1249
1425
|
* CI job asserting the committed schemas are current.
|
|
@@ -1258,19 +1434,19 @@ declare class SchemaPipeline {
|
|
|
1258
1434
|
* The error channel is left to the mechanisms that genuinely cannot
|
|
1259
1435
|
* produce a report (generation, serialization, the engine, the read).
|
|
1260
1436
|
*/
|
|
1261
|
-
static check(targets: ReadonlyArray<SchemaTarget>, options?: SchemaPipelineOptions): Effect.Effect<ReadonlyArray<PipelineCheckResult>, SchemaConversionError | SchemaValidatorError | CanonicalJsonError | SchemaFileReadError, SchemaFile | SchemaValidator>;
|
|
1437
|
+
static check(targets: ReadonlyArray<SchemaTarget>, options?: SchemaPipelineOptions): Effect.Effect<ReadonlyArray<PipelineCheckResult>, SchemaConversionError | UndeclaredAnnotationKeyError | SchemaValidatorError | CanonicalJsonError | SchemaFileReadError, SchemaFile | SchemaValidator>;
|
|
1262
1438
|
/**
|
|
1263
1439
|
* {@link SchemaPipeline.run} for a single target, answering its one
|
|
1264
1440
|
* result directly — so a caller with one target does not index into an
|
|
1265
1441
|
* array and prove to the type system that element zero exists.
|
|
1266
1442
|
*/
|
|
1267
|
-
static runOne(target: SchemaTarget, options?: SchemaPipelineOptions): Effect.Effect<PipelineResult, SchemaGateError | SchemaConversionError | SchemaValidatorError | CanonicalJsonError | SchemaFileReadError | SchemaFileWriteError, SchemaFile | SchemaValidator>;
|
|
1443
|
+
static runOne(target: SchemaTarget, options?: SchemaPipelineOptions): Effect.Effect<PipelineResult, SchemaGateError | SchemaContractChangeError | SchemaConversionError | UndeclaredAnnotationKeyError | SchemaValidatorError | CanonicalJsonError | SchemaFileReadError | SchemaFileWriteError, SchemaFile | SchemaValidator>;
|
|
1268
1444
|
/**
|
|
1269
1445
|
* {@link SchemaPipeline.check} for a single target, answering its one
|
|
1270
1446
|
* result directly.
|
|
1271
1447
|
*/
|
|
1272
|
-
static checkOne(target: SchemaTarget, options?: SchemaPipelineOptions): Effect.Effect<PipelineCheckResult, SchemaConversionError | SchemaValidatorError | CanonicalJsonError | SchemaFileReadError, SchemaFile | SchemaValidator>;
|
|
1448
|
+
static checkOne(target: SchemaTarget, options?: SchemaPipelineOptions): Effect.Effect<PipelineCheckResult, SchemaConversionError | UndeclaredAnnotationKeyError | SchemaValidatorError | CanonicalJsonError | SchemaFileReadError, SchemaFile | SchemaValidator>;
|
|
1273
1449
|
}
|
|
1274
1450
|
//#endregion
|
|
1275
|
-
export {
|
|
1451
|
+
export type { CanonicalJsonError, CanonicalJsonOptions, CatalogUrls, CheckResult, ContractChangePolicy, PipelineCheckResult, PipelineResult, SchemaChange, SchemaFileShape, SchemaPipelineOptions, SchemaValidatorOptions, SchemaValidatorShape, SchemaWriteOptions, StoreDocumentOptions, WriteChange, WriteOutcome, WriteResult };
|
|
1276
1452
|
//# sourceMappingURL=index.d.ts.map
|