@kubb/adapter-oas 5.0.0-beta.57 → 5.0.0-beta.59
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/dist/index.cjs +178 -137
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +9 -11
- package/dist/index.js +177 -136
- package/dist/index.js.map +1 -1
- package/package.json +3 -3
- package/src/adapter.ts +2 -2
- package/src/constants.ts +3 -3
- package/src/discriminator.ts +42 -2
- package/src/parser.ts +64 -55
- package/src/resolvers.ts +1 -1
- package/src/stream.ts +7 -6
- package/src/types.ts +9 -11
package/dist/index.cjs
CHANGED
|
@@ -114,7 +114,7 @@ const structuralKeys = new Set([
|
|
|
114
114
|
*
|
|
115
115
|
* Only formats whose AST type differs from the OAS `type` field appear here.
|
|
116
116
|
* Formats that depend on runtime options (`int64`, `date-time`, `date`, `time`) are handled separately
|
|
117
|
-
* in the parser. `ipv4` and `ipv6` map to their own dedicated schema types
|
|
117
|
+
* in the parser. `ipv4` and `ipv6` map to their own dedicated schema types. `hostname` and
|
|
118
118
|
* `idn-hostname` map to `'url'` as the closest generic string-format type.
|
|
119
119
|
*
|
|
120
120
|
* @example
|
|
@@ -167,8 +167,8 @@ const formatMap = {
|
|
|
167
167
|
*/
|
|
168
168
|
const enumExtensionKeys = ["x-enumNames", "x-enum-varnames"];
|
|
169
169
|
/**
|
|
170
|
-
* Maps
|
|
171
|
-
*
|
|
170
|
+
* Maps the `unknownType`/`emptySchemaType` option string to its `ScalarSchemaType` constant.
|
|
171
|
+
* A `Map` (over a plain object) lets callers test key membership with `.has()`.
|
|
172
172
|
*/
|
|
173
173
|
const typeOptionMap = new Map([
|
|
174
174
|
["any", _kubb_core.ast.schemaTypes.any],
|
|
@@ -863,6 +863,120 @@ const oasDialect = _kubb_core.ast.defineSchemaDialect({
|
|
|
863
863
|
resolveRef
|
|
864
864
|
});
|
|
865
865
|
//#endregion
|
|
866
|
+
//#region src/discriminator.ts
|
|
867
|
+
/**
|
|
868
|
+
* Builds a map of child schema names → discriminator patch data by scanning the given
|
|
869
|
+
* top-level AST schema nodes for union schemas that carry a `discriminatorPropertyName`.
|
|
870
|
+
*
|
|
871
|
+
* The streaming path calls this on a small pre-parsed subset of schemas (only the
|
|
872
|
+
* discriminator parents) rather than on all schemas at once.
|
|
873
|
+
*/
|
|
874
|
+
function buildDiscriminatorChildMap(schemas) {
|
|
875
|
+
const childMap = /* @__PURE__ */ new Map();
|
|
876
|
+
for (const schema of schemas) {
|
|
877
|
+
let unionNode = _kubb_core.ast.narrowSchema(schema, "union");
|
|
878
|
+
if (!unionNode) {
|
|
879
|
+
const intersectionMembers = _kubb_core.ast.narrowSchema(schema, "intersection")?.members;
|
|
880
|
+
if (intersectionMembers) for (const m of intersectionMembers) {
|
|
881
|
+
const u = _kubb_core.ast.narrowSchema(m, "union");
|
|
882
|
+
if (u) {
|
|
883
|
+
unionNode = u;
|
|
884
|
+
break;
|
|
885
|
+
}
|
|
886
|
+
}
|
|
887
|
+
}
|
|
888
|
+
if (!unionNode?.discriminatorPropertyName || !unionNode.members) continue;
|
|
889
|
+
const { discriminatorPropertyName, members } = unionNode;
|
|
890
|
+
for (const member of members) {
|
|
891
|
+
const intersectionNode = _kubb_core.ast.narrowSchema(member, "intersection");
|
|
892
|
+
if (!intersectionNode?.members) continue;
|
|
893
|
+
let refNode = null;
|
|
894
|
+
let objNode = null;
|
|
895
|
+
for (const m of intersectionNode.members) {
|
|
896
|
+
refNode ??= _kubb_core.ast.narrowSchema(m, "ref");
|
|
897
|
+
objNode ??= _kubb_core.ast.narrowSchema(m, "object");
|
|
898
|
+
}
|
|
899
|
+
if (!refNode?.name || !objNode) continue;
|
|
900
|
+
const prop = objNode.properties.find((p) => p.name === discriminatorPropertyName);
|
|
901
|
+
const enumNode = prop ? _kubb_core.ast.narrowSchema(prop.schema, "enum") : null;
|
|
902
|
+
if (!enumNode?.enumValues?.length) continue;
|
|
903
|
+
const enumValues = enumNode.enumValues.filter((v) => v !== null);
|
|
904
|
+
if (!enumValues.length) continue;
|
|
905
|
+
const existing = childMap.get(refNode.name);
|
|
906
|
+
if (!existing) {
|
|
907
|
+
childMap.set(refNode.name, {
|
|
908
|
+
propertyName: discriminatorPropertyName,
|
|
909
|
+
enumValues: [...enumValues]
|
|
910
|
+
});
|
|
911
|
+
continue;
|
|
912
|
+
}
|
|
913
|
+
existing.enumValues.push(...enumValues);
|
|
914
|
+
}
|
|
915
|
+
}
|
|
916
|
+
return childMap;
|
|
917
|
+
}
|
|
918
|
+
/**
|
|
919
|
+
* Patches a single top-level `SchemaNode` with its discriminator entry (adds or replaces
|
|
920
|
+
* the discriminant property). Used by the streaming path to apply patches inline per yield
|
|
921
|
+
* without buffering all schemas.
|
|
922
|
+
*/
|
|
923
|
+
function patchDiscriminatorNode(node, entry) {
|
|
924
|
+
const objectNode = _kubb_core.ast.narrowSchema(node, "object");
|
|
925
|
+
if (!objectNode) return node;
|
|
926
|
+
const { propertyName, enumValues } = entry;
|
|
927
|
+
const enumSchema = _kubb_core.ast.factory.createSchema({
|
|
928
|
+
type: "enum",
|
|
929
|
+
enumValues
|
|
930
|
+
});
|
|
931
|
+
const newProp = _kubb_core.ast.factory.createProperty({
|
|
932
|
+
name: propertyName,
|
|
933
|
+
required: true,
|
|
934
|
+
schema: enumSchema
|
|
935
|
+
});
|
|
936
|
+
const existingIdx = objectNode.properties.findIndex((p) => p.name === propertyName);
|
|
937
|
+
const newProperties = existingIdx >= 0 ? objectNode.properties.map((p, i) => i === existingIdx ? newProp : p) : [...objectNode.properties, newProp];
|
|
938
|
+
return {
|
|
939
|
+
...objectNode,
|
|
940
|
+
properties: newProperties
|
|
941
|
+
};
|
|
942
|
+
}
|
|
943
|
+
/**
|
|
944
|
+
* Creates a single-property object schema used as a discriminator literal.
|
|
945
|
+
*
|
|
946
|
+
* @example
|
|
947
|
+
* ```ts
|
|
948
|
+
* createDiscriminantNode({ propertyName: 'type', value: 'dog' })
|
|
949
|
+
* // -> { type: 'object', properties: [{ name: 'type', required: true, schema: enum('dog') }] }
|
|
950
|
+
* ```
|
|
951
|
+
*/
|
|
952
|
+
function createDiscriminantNode({ propertyName, value }) {
|
|
953
|
+
return _kubb_core.ast.factory.createSchema({
|
|
954
|
+
type: "object",
|
|
955
|
+
primitive: "object",
|
|
956
|
+
properties: [_kubb_core.ast.factory.createProperty({
|
|
957
|
+
name: propertyName,
|
|
958
|
+
schema: _kubb_core.ast.factory.createSchema({
|
|
959
|
+
type: "enum",
|
|
960
|
+
primitive: "string",
|
|
961
|
+
enumValues: [value]
|
|
962
|
+
}),
|
|
963
|
+
required: true
|
|
964
|
+
})]
|
|
965
|
+
});
|
|
966
|
+
}
|
|
967
|
+
/**
|
|
968
|
+
* Returns the discriminator key whose mapping value matches `ref`, or `null` when there is no match.
|
|
969
|
+
*
|
|
970
|
+
* @example
|
|
971
|
+
* ```ts
|
|
972
|
+
* findDiscriminator({ dog: '#/components/schemas/Dog' }, '#/components/schemas/Dog') // 'dog'
|
|
973
|
+
* ```
|
|
974
|
+
*/
|
|
975
|
+
function findDiscriminator(mapping, ref) {
|
|
976
|
+
if (!mapping || !ref) return null;
|
|
977
|
+
return Object.entries(mapping).find(([, value]) => value === ref)?.[0] ?? null;
|
|
978
|
+
}
|
|
979
|
+
//#endregion
|
|
866
980
|
//#region src/mime.ts
|
|
867
981
|
/**
|
|
868
982
|
* MIME type fragments that mark a media type as JSON-like.
|
|
@@ -1351,7 +1465,7 @@ function getSchemas(document, { contentType }) {
|
|
|
1351
1465
|
}
|
|
1352
1466
|
/**
|
|
1353
1467
|
* Resolves the AST type descriptor for a date/time format, honoring the `dateType` option.
|
|
1354
|
-
* Returns `null` when `dateType: false`,
|
|
1468
|
+
* Returns `null` when `dateType: false`, so the format falls through to `string`.
|
|
1355
1469
|
*/
|
|
1356
1470
|
function getDateType(options, format) {
|
|
1357
1471
|
if (!options.dateType) return null;
|
|
@@ -1453,9 +1567,9 @@ function getResponseBodyContentTypes(document, operation, statusCode) {
|
|
|
1453
1567
|
* Normalizes malformed `{ type: 'array', enum: [...] }` schemas by moving enum values into items.
|
|
1454
1568
|
*
|
|
1455
1569
|
* This pattern violates the OpenAPI spec but appears in real specs. The fix moves enum values
|
|
1456
|
-
* from the array to its items sub-schema,
|
|
1570
|
+
* from the array to its items sub-schema, so they are valid for downstream processing.
|
|
1457
1571
|
*
|
|
1458
|
-
* @note
|
|
1572
|
+
* @note A defensive measure for non-compliant specs.
|
|
1459
1573
|
*/
|
|
1460
1574
|
function normalizeArrayEnum(schema) {
|
|
1461
1575
|
const normalizedItems = {
|
|
@@ -1473,7 +1587,7 @@ function normalizeArrayEnum(schema) {
|
|
|
1473
1587
|
*
|
|
1474
1588
|
* Returns closures that share mutable state (`resolvingRefs` set for cycle detection).
|
|
1475
1589
|
* Each converter branch (`convertRef`, `convertAllOf`, etc.) mutually recursively calls `parseSchema`,
|
|
1476
|
-
*
|
|
1590
|
+
* which works because function declarations hoist.
|
|
1477
1591
|
*
|
|
1478
1592
|
* @internal
|
|
1479
1593
|
*/
|
|
@@ -1518,7 +1632,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1518
1632
|
}
|
|
1519
1633
|
resolvedSchema = resolvedRefCache.get(refPath) ?? null;
|
|
1520
1634
|
}
|
|
1521
|
-
return _kubb_core.ast.createSchema({
|
|
1635
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1522
1636
|
...buildSchemaNode(schema, name, nullable, defaultValue),
|
|
1523
1637
|
type: "ref",
|
|
1524
1638
|
name: (0, _kubb_ast_utils.extractRefName)(schema.$ref),
|
|
@@ -1539,7 +1653,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1539
1653
|
const { kind: _kind, ...memberNodeProps } = memberNode;
|
|
1540
1654
|
const mergedNullable = nullable || memberNode.nullable || void 0;
|
|
1541
1655
|
const mergedDefault = schema.default === null && mergedNullable ? void 0 : schema.default ?? memberNode.default;
|
|
1542
|
-
return _kubb_core.ast.createSchema({
|
|
1656
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1543
1657
|
...memberNodeProps,
|
|
1544
1658
|
name,
|
|
1545
1659
|
title: schema.title ?? memberNode.title,
|
|
@@ -1565,7 +1679,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1565
1679
|
const inOneOf = parentUnion.some((oneOfItem) => dialect.isReference(oneOfItem) && oneOfItem.$ref === childRef);
|
|
1566
1680
|
const inMapping = Object.values(deref.discriminator.mapping ?? {}).some((v) => v === childRef);
|
|
1567
1681
|
if (inOneOf || inMapping) {
|
|
1568
|
-
const discriminatorValue =
|
|
1682
|
+
const discriminatorValue = findDiscriminator(deref.discriminator.mapping, childRef);
|
|
1569
1683
|
if (discriminatorValue) filteredDiscriminantValues.push({
|
|
1570
1684
|
propertyName: deref.discriminator.propertyName,
|
|
1571
1685
|
value: discriminatorValue
|
|
@@ -1603,11 +1717,11 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1603
1717
|
const { allOf: _allOf, ...schemaWithoutAllOf } = schema;
|
|
1604
1718
|
allOfMembers.push(parseSchema({ schema: schemaWithoutAllOf }, rawOptions));
|
|
1605
1719
|
}
|
|
1606
|
-
for (const { propertyName, value } of filteredDiscriminantValues) allOfMembers.push(
|
|
1720
|
+
for (const { propertyName, value } of filteredDiscriminantValues) allOfMembers.push(createDiscriminantNode({
|
|
1607
1721
|
propertyName,
|
|
1608
1722
|
value
|
|
1609
1723
|
}));
|
|
1610
|
-
return _kubb_core.ast.createSchema({
|
|
1724
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1611
1725
|
type: "intersection",
|
|
1612
1726
|
members: [..._kubb_core.ast.mergeAdjacentObjectsLazy(allOfMembers.slice(0, syntheticStart)), ..._kubb_core.ast.mergeAdjacentObjectsLazy(allOfMembers.slice(syntheticStart))],
|
|
1613
1727
|
...buildSchemaNode(schema, name, nullable, defaultValue)
|
|
@@ -1620,7 +1734,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1620
1734
|
function pickDiscriminatorPropertyNode(node, propertyName) {
|
|
1621
1735
|
const discriminatorProperty = _kubb_core.ast.narrowSchema(node, "object")?.properties?.find((property) => property.name === propertyName);
|
|
1622
1736
|
if (!discriminatorProperty) return null;
|
|
1623
|
-
return _kubb_core.ast.createSchema({
|
|
1737
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1624
1738
|
type: "object",
|
|
1625
1739
|
primitive: "object",
|
|
1626
1740
|
properties: [discriminatorProperty]
|
|
@@ -1644,7 +1758,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1644
1758
|
if (sharedPropertiesNode || discriminator?.mapping) {
|
|
1645
1759
|
const members = unionMembers.map((s) => {
|
|
1646
1760
|
const ref = dialect.isReference(s) ? s.$ref : void 0;
|
|
1647
|
-
const discriminatorValue =
|
|
1761
|
+
const discriminatorValue = findDiscriminator(discriminator?.mapping, ref);
|
|
1648
1762
|
const memberNode = parseSchema({
|
|
1649
1763
|
schema: s,
|
|
1650
1764
|
name
|
|
@@ -1655,27 +1769,27 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1655
1769
|
propertyName: discriminator.propertyName,
|
|
1656
1770
|
values: [discriminatorValue]
|
|
1657
1771
|
}), discriminator.propertyName) : void 0;
|
|
1658
|
-
return _kubb_core.ast.createSchema({
|
|
1772
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1659
1773
|
type: "intersection",
|
|
1660
|
-
members: [memberNode, narrowedDiscriminatorNode ??
|
|
1774
|
+
members: [memberNode, narrowedDiscriminatorNode ?? createDiscriminantNode({
|
|
1661
1775
|
propertyName: discriminator.propertyName,
|
|
1662
1776
|
value: discriminatorValue
|
|
1663
1777
|
})]
|
|
1664
1778
|
});
|
|
1665
1779
|
});
|
|
1666
|
-
const unionNode = _kubb_core.ast.createSchema({
|
|
1780
|
+
const unionNode = _kubb_core.ast.factory.createSchema({
|
|
1667
1781
|
type: "union",
|
|
1668
1782
|
...unionBase,
|
|
1669
1783
|
members
|
|
1670
1784
|
});
|
|
1671
1785
|
if (!sharedPropertiesNode) return unionNode;
|
|
1672
|
-
return _kubb_core.ast.createSchema({
|
|
1786
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1673
1787
|
type: "intersection",
|
|
1674
1788
|
...buildSchemaNode(schema, name, nullable, defaultValue),
|
|
1675
1789
|
members: [unionNode, sharedPropertiesNode]
|
|
1676
1790
|
});
|
|
1677
1791
|
}
|
|
1678
|
-
return _kubb_core.ast.createSchema({
|
|
1792
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1679
1793
|
type: "union",
|
|
1680
1794
|
...unionBase,
|
|
1681
1795
|
members: _kubb_core.ast.simplifyUnion(unionMembers.map((s) => parseSchema({
|
|
@@ -1689,7 +1803,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1689
1803
|
*/
|
|
1690
1804
|
function convertConst({ schema, name, nullable, defaultValue }) {
|
|
1691
1805
|
const constValue = schema.const;
|
|
1692
|
-
if (constValue === null) return _kubb_core.ast.createSchema({
|
|
1806
|
+
if (constValue === null) return _kubb_core.ast.factory.createSchema({
|
|
1693
1807
|
type: "null",
|
|
1694
1808
|
primitive: "null",
|
|
1695
1809
|
name,
|
|
@@ -1699,7 +1813,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1699
1813
|
format: schema.format
|
|
1700
1814
|
});
|
|
1701
1815
|
const constPrimitive = getPrimitiveType(typeof constValue === "number" ? "number" : typeof constValue === "boolean" ? "boolean" : "string");
|
|
1702
|
-
return _kubb_core.ast.createSchema({
|
|
1816
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1703
1817
|
type: "enum",
|
|
1704
1818
|
primitive: constPrimitive,
|
|
1705
1819
|
enumValues: [constValue],
|
|
@@ -1712,7 +1826,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1712
1826
|
*/
|
|
1713
1827
|
function convertFormat({ schema, name, nullable, defaultValue, options }) {
|
|
1714
1828
|
const base = buildSchemaNode(schema, name, nullable, defaultValue);
|
|
1715
|
-
if (schema.format === "int64") return _kubb_core.ast.createSchema({
|
|
1829
|
+
if (schema.format === "int64") return _kubb_core.ast.factory.createSchema({
|
|
1716
1830
|
type: options.integerType === "bigint" ? "bigint" : "integer",
|
|
1717
1831
|
primitive: "integer",
|
|
1718
1832
|
...base,
|
|
@@ -1724,14 +1838,14 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1724
1838
|
if (schema.format === "date-time" || schema.format === "date" || schema.format === "time") {
|
|
1725
1839
|
const dateType = getDateType(options, schema.format);
|
|
1726
1840
|
if (!dateType) return null;
|
|
1727
|
-
if (dateType.type === "datetime") return _kubb_core.ast.createSchema({
|
|
1841
|
+
if (dateType.type === "datetime") return _kubb_core.ast.factory.createSchema({
|
|
1728
1842
|
...base,
|
|
1729
1843
|
primitive: "string",
|
|
1730
1844
|
type: "datetime",
|
|
1731
1845
|
offset: dateType.offset,
|
|
1732
1846
|
local: dateType.local
|
|
1733
1847
|
});
|
|
1734
|
-
return _kubb_core.ast.createSchema({
|
|
1848
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1735
1849
|
...base,
|
|
1736
1850
|
primitive: "string",
|
|
1737
1851
|
type: dateType.type,
|
|
@@ -1741,36 +1855,36 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1741
1855
|
const specialType = getSchemaType(schema.format);
|
|
1742
1856
|
if (!specialType) return null;
|
|
1743
1857
|
const specialPrimitive = specialType === "number" || specialType === "integer" || specialType === "bigint" ? specialType : "string";
|
|
1744
|
-
if (specialType === "number" || specialType === "integer" || specialType === "bigint") return _kubb_core.ast.createSchema({
|
|
1858
|
+
if (specialType === "number" || specialType === "integer" || specialType === "bigint") return _kubb_core.ast.factory.createSchema({
|
|
1745
1859
|
...base,
|
|
1746
1860
|
primitive: specialPrimitive,
|
|
1747
1861
|
type: specialType
|
|
1748
1862
|
});
|
|
1749
|
-
if (specialType === "url") return _kubb_core.ast.createSchema({
|
|
1863
|
+
if (specialType === "url") return _kubb_core.ast.factory.createSchema({
|
|
1750
1864
|
...base,
|
|
1751
1865
|
primitive: "string",
|
|
1752
1866
|
type: "url",
|
|
1753
1867
|
min: schema.minLength,
|
|
1754
1868
|
max: schema.maxLength
|
|
1755
1869
|
});
|
|
1756
|
-
if (specialType === "ipv4") return _kubb_core.ast.createSchema({
|
|
1870
|
+
if (specialType === "ipv4") return _kubb_core.ast.factory.createSchema({
|
|
1757
1871
|
...base,
|
|
1758
1872
|
primitive: "string",
|
|
1759
1873
|
type: "ipv4"
|
|
1760
1874
|
});
|
|
1761
|
-
if (specialType === "ipv6") return _kubb_core.ast.createSchema({
|
|
1875
|
+
if (specialType === "ipv6") return _kubb_core.ast.factory.createSchema({
|
|
1762
1876
|
...base,
|
|
1763
1877
|
primitive: "string",
|
|
1764
1878
|
type: "ipv6"
|
|
1765
1879
|
});
|
|
1766
|
-
if (specialType === "uuid" || specialType === "email") return _kubb_core.ast.createSchema({
|
|
1880
|
+
if (specialType === "uuid" || specialType === "email") return _kubb_core.ast.factory.createSchema({
|
|
1767
1881
|
...base,
|
|
1768
1882
|
primitive: "string",
|
|
1769
1883
|
type: specialType,
|
|
1770
1884
|
min: schema.minLength,
|
|
1771
1885
|
max: schema.maxLength
|
|
1772
1886
|
});
|
|
1773
|
-
return _kubb_core.ast.createSchema({
|
|
1887
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1774
1888
|
...base,
|
|
1775
1889
|
primitive: specialPrimitive,
|
|
1776
1890
|
type: specialType
|
|
@@ -1786,7 +1900,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1786
1900
|
}, rawOptions);
|
|
1787
1901
|
const nullInEnum = schema.enum.includes(null);
|
|
1788
1902
|
const filteredValues = nullInEnum ? schema.enum.filter((v) => v !== null) : schema.enum;
|
|
1789
|
-
if (nullInEnum && filteredValues.length === 0) return _kubb_core.ast.createSchema({
|
|
1903
|
+
if (nullInEnum && filteredValues.length === 0) return _kubb_core.ast.factory.createSchema({
|
|
1790
1904
|
type: "null",
|
|
1791
1905
|
primitive: "null",
|
|
1792
1906
|
name,
|
|
@@ -1818,7 +1932,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1818
1932
|
const rawEnumNames = extensionKey ? schema[extensionKey] : void 0;
|
|
1819
1933
|
const uniqueValues = [...new Set(filteredValues)];
|
|
1820
1934
|
const seenNames = /* @__PURE__ */ new Set();
|
|
1821
|
-
return _kubb_core.ast.createSchema({
|
|
1935
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1822
1936
|
...enumBase,
|
|
1823
1937
|
primitive: enumPrimitiveType,
|
|
1824
1938
|
namedEnumValues: uniqueValues.map((value, index) => ({
|
|
@@ -1832,7 +1946,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1832
1946
|
})
|
|
1833
1947
|
});
|
|
1834
1948
|
}
|
|
1835
|
-
return _kubb_core.ast.createSchema({
|
|
1949
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1836
1950
|
...enumBase,
|
|
1837
1951
|
enumValues: [...new Set(filteredValues)]
|
|
1838
1952
|
});
|
|
@@ -1861,7 +1975,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1861
1975
|
}
|
|
1862
1976
|
return node;
|
|
1863
1977
|
})();
|
|
1864
|
-
return _kubb_core.ast.createProperty({
|
|
1978
|
+
return _kubb_core.ast.factory.createProperty({
|
|
1865
1979
|
name: propName,
|
|
1866
1980
|
schema: {
|
|
1867
1981
|
...schemaNode,
|
|
@@ -1875,11 +1989,11 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1875
1989
|
if (additionalProperties === true) return true;
|
|
1876
1990
|
if (additionalProperties === false) return false;
|
|
1877
1991
|
if (additionalProperties && Object.keys(additionalProperties).length > 0) return parseSchema({ schema: additionalProperties }, rawOptions);
|
|
1878
|
-
if (additionalProperties) return _kubb_core.ast.createSchema({ type: typeOptionMap.get(options.unknownType) });
|
|
1992
|
+
if (additionalProperties) return _kubb_core.ast.factory.createSchema({ type: typeOptionMap.get(options.unknownType) });
|
|
1879
1993
|
})();
|
|
1880
1994
|
const rawPatternProperties = "patternProperties" in schema ? schema.patternProperties : void 0;
|
|
1881
|
-
const patternProperties = rawPatternProperties ? Object.fromEntries(Object.entries(rawPatternProperties).map(([pattern, patternSchema]) => [pattern, patternSchema === true || typeof patternSchema === "object" && Object.keys(patternSchema).length === 0 ? _kubb_core.ast.createSchema({ type: typeOptionMap.get(options.unknownType) }) : parseSchema({ schema: patternSchema }, rawOptions)])) : void 0;
|
|
1882
|
-
const objectNode = _kubb_core.ast.createSchema({
|
|
1995
|
+
const patternProperties = rawPatternProperties ? Object.fromEntries(Object.entries(rawPatternProperties).map(([pattern, patternSchema]) => [pattern, patternSchema === true || typeof patternSchema === "object" && Object.keys(patternSchema).length === 0 ? _kubb_core.ast.factory.createSchema({ type: typeOptionMap.get(options.unknownType) }) : parseSchema({ schema: patternSchema }, rawOptions)])) : void 0;
|
|
1996
|
+
const objectNode = _kubb_core.ast.factory.createSchema({
|
|
1883
1997
|
type: "object",
|
|
1884
1998
|
primitive: "object",
|
|
1885
1999
|
properties,
|
|
@@ -1907,8 +2021,8 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1907
2021
|
*/
|
|
1908
2022
|
function convertTuple({ schema, name, nullable, defaultValue, rawOptions }) {
|
|
1909
2023
|
const tupleItems = (schema.prefixItems ?? []).map((item) => parseSchema({ schema: item }, rawOptions));
|
|
1910
|
-
const rest = schema.items ? parseSchema({ schema: schema.items }, rawOptions) : _kubb_core.ast.createSchema({ type: "any" });
|
|
1911
|
-
return _kubb_core.ast.createSchema({
|
|
2024
|
+
const rest = schema.items ? parseSchema({ schema: schema.items }, rawOptions) : _kubb_core.ast.factory.createSchema({ type: "any" });
|
|
2025
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1912
2026
|
type: "tuple",
|
|
1913
2027
|
primitive: "array",
|
|
1914
2028
|
items: tupleItems,
|
|
@@ -1928,7 +2042,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1928
2042
|
schema: rawItems,
|
|
1929
2043
|
name: itemName
|
|
1930
2044
|
}, rawOptions)] : [];
|
|
1931
|
-
return _kubb_core.ast.createSchema({
|
|
2045
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1932
2046
|
type: "array",
|
|
1933
2047
|
primitive: "array",
|
|
1934
2048
|
items,
|
|
@@ -1942,7 +2056,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1942
2056
|
* Converts a `type: 'string'` schema into a `StringSchemaNode`.
|
|
1943
2057
|
*/
|
|
1944
2058
|
function convertString({ schema, name, nullable, defaultValue }) {
|
|
1945
|
-
return _kubb_core.ast.createSchema({
|
|
2059
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1946
2060
|
type: "string",
|
|
1947
2061
|
primitive: "string",
|
|
1948
2062
|
min: schema.minLength,
|
|
@@ -1955,7 +2069,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1955
2069
|
* Converts a `type: 'number'` or `type: 'integer'` schema.
|
|
1956
2070
|
*/
|
|
1957
2071
|
function convertNumeric({ schema, name, nullable, defaultValue }, type) {
|
|
1958
|
-
return _kubb_core.ast.createSchema({
|
|
2072
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1959
2073
|
type,
|
|
1960
2074
|
primitive: type,
|
|
1961
2075
|
min: schema.minimum,
|
|
@@ -1970,7 +2084,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1970
2084
|
* Converts a `type: 'boolean'` schema.
|
|
1971
2085
|
*/
|
|
1972
2086
|
function convertBoolean({ schema, name, nullable, defaultValue }) {
|
|
1973
|
-
return _kubb_core.ast.createSchema({
|
|
2087
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1974
2088
|
type: "boolean",
|
|
1975
2089
|
primitive: "boolean",
|
|
1976
2090
|
...buildSchemaNode(schema, name, nullable, defaultValue)
|
|
@@ -1980,7 +2094,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1980
2094
|
* Converts an explicit `type: 'null'` schema.
|
|
1981
2095
|
*/
|
|
1982
2096
|
function convertNull({ schema, name, nullable }) {
|
|
1983
|
-
return _kubb_core.ast.createSchema({
|
|
2097
|
+
return _kubb_core.ast.factory.createSchema({
|
|
1984
2098
|
type: "null",
|
|
1985
2099
|
primitive: "null",
|
|
1986
2100
|
name,
|
|
@@ -1996,7 +2110,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
1996
2110
|
* into a `blob` node.
|
|
1997
2111
|
*/
|
|
1998
2112
|
function convertBlob({ schema, name, nullable, defaultValue }) {
|
|
1999
|
-
return _kubb_core.ast.createSchema({
|
|
2113
|
+
return _kubb_core.ast.factory.createSchema({
|
|
2000
2114
|
type: "blob",
|
|
2001
2115
|
primitive: "string",
|
|
2002
2116
|
...buildSchemaNode(schema, name, nullable, defaultValue)
|
|
@@ -2013,7 +2127,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
2013
2127
|
const nonNullTypes = types.filter((t) => t !== "null");
|
|
2014
2128
|
if (nonNullTypes.length <= 1) return null;
|
|
2015
2129
|
const arrayNullable = types.includes("null") || nullable || void 0;
|
|
2016
|
-
return _kubb_core.ast.createSchema({
|
|
2130
|
+
return _kubb_core.ast.factory.createSchema({
|
|
2017
2131
|
type: "union",
|
|
2018
2132
|
members: nonNullTypes.map((t) => parseSchema({
|
|
2019
2133
|
schema: {
|
|
@@ -2156,7 +2270,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
2156
2270
|
if (node) return node;
|
|
2157
2271
|
}
|
|
2158
2272
|
const emptyType = typeOptionMap.get(options.emptySchemaType);
|
|
2159
|
-
return _kubb_core.ast.createSchema({
|
|
2273
|
+
return _kubb_core.ast.factory.createSchema({
|
|
2160
2274
|
type: emptyType,
|
|
2161
2275
|
name,
|
|
2162
2276
|
title: schema.title,
|
|
@@ -2174,8 +2288,8 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
2174
2288
|
const schema = param["schema"] ? parseSchema({
|
|
2175
2289
|
schema: param["schema"],
|
|
2176
2290
|
name: schemaName
|
|
2177
|
-
}, options) : _kubb_core.ast.createSchema({ type: typeOptionMap.get(options.unknownType) });
|
|
2178
|
-
return _kubb_core.ast.createParameter({
|
|
2291
|
+
}, options) : _kubb_core.ast.factory.createSchema({ type: typeOptionMap.get(options.unknownType) });
|
|
2292
|
+
return _kubb_core.ast.factory.createParameter({
|
|
2179
2293
|
name: paramName,
|
|
2180
2294
|
in: param["in"],
|
|
2181
2295
|
schema: {
|
|
@@ -2262,7 +2376,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
2262
2376
|
schema: raw && Object.keys(raw).length > 0 ? parseSchema({
|
|
2263
2377
|
schema: raw,
|
|
2264
2378
|
name: responseName
|
|
2265
|
-
}, options) : _kubb_core.ast.createSchema({ type: typeOptionMap.get(options.emptySchemaType) }),
|
|
2379
|
+
}, options) : _kubb_core.ast.factory.createSchema({ type: typeOptionMap.get(options.emptySchemaType) }),
|
|
2266
2380
|
keysToOmit: collectPropertyKeysByFlag(raw, "writeOnly")
|
|
2267
2381
|
};
|
|
2268
2382
|
};
|
|
@@ -2277,7 +2391,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
2277
2391
|
}) || "application/json",
|
|
2278
2392
|
...parseEntrySchema(ctx.contentType)
|
|
2279
2393
|
});
|
|
2280
|
-
return _kubb_core.ast.createResponse({
|
|
2394
|
+
return _kubb_core.ast.factory.createResponse({
|
|
2281
2395
|
statusCode,
|
|
2282
2396
|
description,
|
|
2283
2397
|
content
|
|
@@ -2291,7 +2405,7 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
2291
2405
|
const fallback = pathItemDoc?.[key];
|
|
2292
2406
|
return typeof fallback === "string" ? fallback : void 0;
|
|
2293
2407
|
};
|
|
2294
|
-
return _kubb_core.ast.createOperation({
|
|
2408
|
+
return _kubb_core.ast.factory.createOperation({
|
|
2295
2409
|
operationId,
|
|
2296
2410
|
protocol: "http",
|
|
2297
2411
|
method: operation.method.toUpperCase(),
|
|
@@ -2312,84 +2426,6 @@ function createSchemaParser(ctx, dialect = oasDialect) {
|
|
|
2312
2426
|
};
|
|
2313
2427
|
}
|
|
2314
2428
|
//#endregion
|
|
2315
|
-
//#region src/discriminator.ts
|
|
2316
|
-
/**
|
|
2317
|
-
* Builds a map of child schema names → discriminator patch data by scanning the given
|
|
2318
|
-
* top-level AST schema nodes for union schemas that carry a `discriminatorPropertyName`.
|
|
2319
|
-
*
|
|
2320
|
-
* The streaming path calls this on a small pre-parsed subset of schemas (only the
|
|
2321
|
-
* discriminator parents) rather than on all schemas at once.
|
|
2322
|
-
*/
|
|
2323
|
-
function buildDiscriminatorChildMap(schemas) {
|
|
2324
|
-
const childMap = /* @__PURE__ */ new Map();
|
|
2325
|
-
for (const schema of schemas) {
|
|
2326
|
-
let unionNode = _kubb_core.ast.narrowSchema(schema, "union");
|
|
2327
|
-
if (!unionNode) {
|
|
2328
|
-
const intersectionMembers = _kubb_core.ast.narrowSchema(schema, "intersection")?.members;
|
|
2329
|
-
if (intersectionMembers) for (const m of intersectionMembers) {
|
|
2330
|
-
const u = _kubb_core.ast.narrowSchema(m, "union");
|
|
2331
|
-
if (u) {
|
|
2332
|
-
unionNode = u;
|
|
2333
|
-
break;
|
|
2334
|
-
}
|
|
2335
|
-
}
|
|
2336
|
-
}
|
|
2337
|
-
if (!unionNode?.discriminatorPropertyName || !unionNode.members) continue;
|
|
2338
|
-
const { discriminatorPropertyName, members } = unionNode;
|
|
2339
|
-
for (const member of members) {
|
|
2340
|
-
const intersectionNode = _kubb_core.ast.narrowSchema(member, "intersection");
|
|
2341
|
-
if (!intersectionNode?.members) continue;
|
|
2342
|
-
let refNode = null;
|
|
2343
|
-
let objNode = null;
|
|
2344
|
-
for (const m of intersectionNode.members) {
|
|
2345
|
-
refNode ??= _kubb_core.ast.narrowSchema(m, "ref");
|
|
2346
|
-
objNode ??= _kubb_core.ast.narrowSchema(m, "object");
|
|
2347
|
-
}
|
|
2348
|
-
if (!refNode?.name || !objNode) continue;
|
|
2349
|
-
const prop = objNode.properties.find((p) => p.name === discriminatorPropertyName);
|
|
2350
|
-
const enumNode = prop ? _kubb_core.ast.narrowSchema(prop.schema, "enum") : null;
|
|
2351
|
-
if (!enumNode?.enumValues?.length) continue;
|
|
2352
|
-
const enumValues = enumNode.enumValues.filter((v) => v !== null);
|
|
2353
|
-
if (!enumValues.length) continue;
|
|
2354
|
-
const existing = childMap.get(refNode.name);
|
|
2355
|
-
if (!existing) {
|
|
2356
|
-
childMap.set(refNode.name, {
|
|
2357
|
-
propertyName: discriminatorPropertyName,
|
|
2358
|
-
enumValues: [...enumValues]
|
|
2359
|
-
});
|
|
2360
|
-
continue;
|
|
2361
|
-
}
|
|
2362
|
-
existing.enumValues.push(...enumValues);
|
|
2363
|
-
}
|
|
2364
|
-
}
|
|
2365
|
-
return childMap;
|
|
2366
|
-
}
|
|
2367
|
-
/**
|
|
2368
|
-
* Patches a single top-level `SchemaNode` with its discriminator entry (adds or replaces
|
|
2369
|
-
* the discriminant property). Used by the streaming path to apply patches inline per yield
|
|
2370
|
-
* without buffering all schemas.
|
|
2371
|
-
*/
|
|
2372
|
-
function patchDiscriminatorNode(node, entry) {
|
|
2373
|
-
const objectNode = _kubb_core.ast.narrowSchema(node, "object");
|
|
2374
|
-
if (!objectNode) return node;
|
|
2375
|
-
const { propertyName, enumValues } = entry;
|
|
2376
|
-
const enumSchema = _kubb_core.ast.createSchema({
|
|
2377
|
-
type: "enum",
|
|
2378
|
-
enumValues
|
|
2379
|
-
});
|
|
2380
|
-
const newProp = _kubb_core.ast.createProperty({
|
|
2381
|
-
name: propertyName,
|
|
2382
|
-
required: true,
|
|
2383
|
-
schema: enumSchema
|
|
2384
|
-
});
|
|
2385
|
-
const existingIdx = objectNode.properties.findIndex((p) => p.name === propertyName);
|
|
2386
|
-
const newProperties = existingIdx >= 0 ? objectNode.properties.map((p, i) => i === existingIdx ? newProp : p) : [...objectNode.properties, newProp];
|
|
2387
|
-
return {
|
|
2388
|
-
...objectNode,
|
|
2389
|
-
properties: newProperties
|
|
2390
|
-
};
|
|
2391
|
-
}
|
|
2392
|
-
//#endregion
|
|
2393
2429
|
//#region src/schemaDiagnostics.ts
|
|
2394
2430
|
/**
|
|
2395
2431
|
* Reports the advisory diagnostics (`KUBB_UNSUPPORTED_FORMAT`, `KUBB_DEPRECATED`) for one
|
|
@@ -2452,7 +2488,7 @@ function visit(node, pointer) {
|
|
|
2452
2488
|
*
|
|
2453
2489
|
* Only enums and objects are candidates, and object shapes that reference a circular schema are
|
|
2454
2490
|
* rejected to avoid hoisting recursive structures. Inline shapes reuse their context-derived
|
|
2455
|
-
* name (collision-resolved against existing component names)
|
|
2491
|
+
* name (collision-resolved against existing component names). Shapes without a name stay inline.
|
|
2456
2492
|
*/
|
|
2457
2493
|
function createDedupePlan({ schemaNodes, operationNodes, schemaNames, circularNames }) {
|
|
2458
2494
|
const circularSchemas = new Set(circularNames);
|
|
@@ -2462,7 +2498,7 @@ function createDedupePlan({ schemaNodes, operationNodes, schemaNames, circularNa
|
|
|
2462
2498
|
if (node.type === "enum") return true;
|
|
2463
2499
|
if (node.type !== "object") return false;
|
|
2464
2500
|
if (node.name && circularSchemas.has(node.name)) return false;
|
|
2465
|
-
return !
|
|
2501
|
+
return !(0, _kubb_ast_utils.containsCircularRef)(node, { circularSchemas });
|
|
2466
2502
|
},
|
|
2467
2503
|
nameFor: (node) => {
|
|
2468
2504
|
const base = node.name;
|
|
@@ -2536,7 +2572,7 @@ function preScan({ schemas, parseSchema, parseOperation, document, parserOptions
|
|
|
2536
2572
|
if (_kubb_core.ast.narrowSchema(node, _kubb_core.ast.schemaTypes.enum) && node.name) enumNames.push(node.name);
|
|
2537
2573
|
if (discriminator === "inherit" && (schema.oneOf ?? schema.anyOf) && schema.discriminator?.propertyName) discriminatorParentNodes.push(node);
|
|
2538
2574
|
}
|
|
2539
|
-
const circularNames = [...
|
|
2575
|
+
const circularNames = [...(0, _kubb_ast_utils.findCircularSchemas)(allNodes)];
|
|
2540
2576
|
const discriminatorChildMap = discriminatorParentNodes.length > 0 ? buildDiscriminatorChildMap(discriminatorParentNodes) : null;
|
|
2541
2577
|
let dedupePlan = null;
|
|
2542
2578
|
if (dedupe) {
|
|
@@ -2584,7 +2620,7 @@ function createInputStream({ schemas, parseSchema, parseOperation, document, par
|
|
|
2584
2620
|
const rewriteTopLevelSchema = (node) => {
|
|
2585
2621
|
if (!dedupePlan) return node;
|
|
2586
2622
|
const canonical = dedupePlan.canonicalBySignature.get(_kubb_core.ast.signatureOf(node));
|
|
2587
|
-
if (canonical && canonical.name !== node.name) return _kubb_core.ast.createSchema({
|
|
2623
|
+
if (canonical && canonical.name !== node.name) return _kubb_core.ast.factory.createSchema({
|
|
2588
2624
|
type: "ref",
|
|
2589
2625
|
name: node.name ?? null,
|
|
2590
2626
|
ref: canonical.ref,
|
|
@@ -2625,7 +2661,12 @@ function createInputStream({ schemas, parseSchema, parseOperation, document, par
|
|
|
2625
2661
|
}
|
|
2626
2662
|
})();
|
|
2627
2663
|
} };
|
|
2628
|
-
return _kubb_core.ast.
|
|
2664
|
+
return _kubb_core.ast.factory.createInput({
|
|
2665
|
+
stream: true,
|
|
2666
|
+
schemas: schemasIterable,
|
|
2667
|
+
operations: operationsIterable,
|
|
2668
|
+
meta
|
|
2669
|
+
});
|
|
2629
2670
|
}
|
|
2630
2671
|
//#endregion
|
|
2631
2672
|
//#region src/adapter.ts
|
|
@@ -2784,7 +2825,7 @@ const adapterOas = (0, _kubb_core.createAdapter)((options) => {
|
|
|
2784
2825
|
const rawName = (0, _kubb_ast_utils.extractRefName)(schemaRef.ref);
|
|
2785
2826
|
const result = resolve(nameMapping.get(rawName) ?? rawName);
|
|
2786
2827
|
if (!result) return null;
|
|
2787
|
-
return _kubb_core.ast.createImport({
|
|
2828
|
+
return _kubb_core.ast.factory.createImport({
|
|
2788
2829
|
name: [result.name],
|
|
2789
2830
|
path: result.path
|
|
2790
2831
|
});
|
|
@@ -2793,7 +2834,7 @@ const adapterOas = (0, _kubb_core.createAdapter)((options) => {
|
|
|
2793
2834
|
async parse(source) {
|
|
2794
2835
|
const streamNode = await createStream(source);
|
|
2795
2836
|
const [schemas, operations] = await Promise.all([Array.fromAsync(streamNode.schemas), Array.fromAsync(streamNode.operations)]);
|
|
2796
|
-
return _kubb_core.ast.createInput({
|
|
2837
|
+
return _kubb_core.ast.factory.createInput({
|
|
2797
2838
|
schemas,
|
|
2798
2839
|
operations,
|
|
2799
2840
|
meta: streamNode.meta
|