adorn-api 1.0.20 → 1.0.22
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/cli.cjs +643 -42
- package/dist/cli.cjs.map +1 -1
- package/dist/cli.js +643 -42
- package/dist/cli.js.map +1 -1
- package/dist/compiler/schema/objectHandler.d.ts +40 -0
- package/dist/compiler/schema/objectHandler.d.ts.map +1 -1
- package/dist/compiler/schema/openapi.d.ts +29 -0
- package/dist/compiler/schema/openapi.d.ts.map +1 -1
- package/dist/compiler/schema/queryBuilderAnalyzer.d.ts +76 -0
- package/dist/compiler/schema/queryBuilderAnalyzer.d.ts.map +1 -0
- package/dist/compiler/schema/queryBuilderSchemaBuilder.d.ts +13 -0
- package/dist/compiler/schema/queryBuilderSchemaBuilder.d.ts.map +1 -0
- package/dist/compiler/schema/types.d.ts +1 -0
- package/dist/compiler/schema/types.d.ts.map +1 -1
- package/dist/metal/applyListQuery.d.ts +1 -1
- package/dist/metal/applyListQuery.d.ts.map +1 -1
- package/dist/metal/index.cjs.map +1 -1
- package/dist/metal/index.js.map +1 -1
- package/package.json +2 -2
package/dist/cli.cjs
CHANGED
|
@@ -323,7 +323,7 @@ function unwrapPromiseTypeNode(typeNode) {
|
|
|
323
323
|
}
|
|
324
324
|
|
|
325
325
|
// src/compiler/schema/openapi.ts
|
|
326
|
-
var
|
|
326
|
+
var import_typescript11 = __toESM(require("typescript"), 1);
|
|
327
327
|
|
|
328
328
|
// src/compiler/schema/typeToJsonSchema.ts
|
|
329
329
|
var import_typescript7 = __toESM(require("typescript"), 1);
|
|
@@ -718,6 +718,48 @@ function getExplicitTypeNameFromNode3(typeNode) {
|
|
|
718
718
|
|
|
719
719
|
// src/compiler/schema/objectHandler.ts
|
|
720
720
|
var import_typescript6 = __toESM(require("typescript"), 1);
|
|
721
|
+
function getTypeParameterName(type) {
|
|
722
|
+
if (type.flags & import_typescript6.default.TypeFlags.TypeParameter) {
|
|
723
|
+
const typeParam = type;
|
|
724
|
+
return typeParam.symbol?.getName() ?? null;
|
|
725
|
+
}
|
|
726
|
+
return null;
|
|
727
|
+
}
|
|
728
|
+
function getTypeArguments(type) {
|
|
729
|
+
const typeRef = type;
|
|
730
|
+
const args = typeRef.typeArguments;
|
|
731
|
+
if (!args) return void 0;
|
|
732
|
+
return Array.from(args);
|
|
733
|
+
}
|
|
734
|
+
function createTypeParameterSubstitutions(type, typeNode, checker) {
|
|
735
|
+
const typeArgs = getTypeArguments(type);
|
|
736
|
+
if (!typeArgs || typeArgs.length === 0) {
|
|
737
|
+
return void 0;
|
|
738
|
+
}
|
|
739
|
+
if (!typeNode || !import_typescript6.default.isTypeReferenceNode(typeNode)) {
|
|
740
|
+
return void 0;
|
|
741
|
+
}
|
|
742
|
+
const typeParams = typeNode.typeArguments;
|
|
743
|
+
if (!typeParams || typeParams.length !== typeArgs.length) {
|
|
744
|
+
return void 0;
|
|
745
|
+
}
|
|
746
|
+
const substitutions = /* @__PURE__ */ new Map();
|
|
747
|
+
for (let i = 0; i < typeParams.length; i++) {
|
|
748
|
+
const typeParamNode = typeParams[i];
|
|
749
|
+
const typeArg = typeArgs[i];
|
|
750
|
+
if (import_typescript6.default.isIdentifier(typeParamNode)) {
|
|
751
|
+
substitutions.set(typeParamNode.text, typeArg);
|
|
752
|
+
}
|
|
753
|
+
}
|
|
754
|
+
return substitutions.size > 0 ? substitutions : void 0;
|
|
755
|
+
}
|
|
756
|
+
function resolveTypeParameter(type, substitutions, _checker) {
|
|
757
|
+
if (!substitutions) return null;
|
|
758
|
+
const paramName = getTypeParameterName(type);
|
|
759
|
+
if (!paramName) return null;
|
|
760
|
+
const resolved = substitutions.get(paramName);
|
|
761
|
+
return resolved ?? null;
|
|
762
|
+
}
|
|
721
763
|
function handleObjectType(type, ctx, typeNode) {
|
|
722
764
|
const { checker, components, typeStack } = ctx;
|
|
723
765
|
const symbol = type.getSymbol();
|
|
@@ -737,7 +779,9 @@ function handleObjectType(type, ctx, typeNode) {
|
|
|
737
779
|
}
|
|
738
780
|
typeStack.add(type);
|
|
739
781
|
}
|
|
740
|
-
const
|
|
782
|
+
const typeParamSubstitutions = createTypeParameterSubstitutions(type, typeNode, checker);
|
|
783
|
+
const buildCtx = typeParamSubstitutions ? { ...ctx, typeParameterSubstitutions: typeParamSubstitutions } : ctx;
|
|
784
|
+
const schema = buildObjectSchema(type, buildCtx, typeNode);
|
|
741
785
|
if (typeName && typeName !== "__type") {
|
|
742
786
|
typeStack.delete(type);
|
|
743
787
|
const existing = components.get(typeName);
|
|
@@ -755,7 +799,7 @@ function handleObjectType(type, ctx, typeNode) {
|
|
|
755
799
|
return schema;
|
|
756
800
|
}
|
|
757
801
|
function buildObjectSchema(type, ctx, _typeNode) {
|
|
758
|
-
const { checker, mode } = ctx;
|
|
802
|
+
const { checker, mode, typeParameterSubstitutions } = ctx;
|
|
759
803
|
const properties = {};
|
|
760
804
|
const required = [];
|
|
761
805
|
const props = checker.getPropertiesOfType(type);
|
|
@@ -764,10 +808,14 @@ function buildObjectSchema(type, ctx, _typeNode) {
|
|
|
764
808
|
if (isIteratorOrSymbolProperty(propName)) {
|
|
765
809
|
continue;
|
|
766
810
|
}
|
|
767
|
-
|
|
811
|
+
let propType = checker.getTypeOfSymbol(prop);
|
|
768
812
|
if (isMethodLike(propType)) {
|
|
769
813
|
continue;
|
|
770
814
|
}
|
|
815
|
+
const resolvedType = resolveTypeParameter(propType, typeParameterSubstitutions, checker);
|
|
816
|
+
if (resolvedType) {
|
|
817
|
+
propType = resolvedType;
|
|
818
|
+
}
|
|
771
819
|
const isOptional = !!(prop.flags & import_typescript6.default.SymbolFlags.Optional);
|
|
772
820
|
const isRelation = isMetalOrmWrapperType(propType, checker);
|
|
773
821
|
const propCtx = { ...ctx, propertyName: propName };
|
|
@@ -787,7 +835,8 @@ function buildObjectSchema(type, ctx, _typeNode) {
|
|
|
787
835
|
if (isRecordType(type, checker)) {
|
|
788
836
|
const valueType = getRecordValueType(type, checker);
|
|
789
837
|
if (valueType) {
|
|
790
|
-
|
|
838
|
+
const resolvedValueType = resolveTypeParameter(valueType, typeParameterSubstitutions, checker);
|
|
839
|
+
schema.additionalProperties = typeToJsonSchema(resolvedValueType ?? valueType, ctx);
|
|
791
840
|
}
|
|
792
841
|
}
|
|
793
842
|
return schema;
|
|
@@ -1579,6 +1628,384 @@ function resolveAndCollectObjectProps(schema, components) {
|
|
|
1579
1628
|
return { properties, required };
|
|
1580
1629
|
}
|
|
1581
1630
|
|
|
1631
|
+
// src/compiler/schema/queryBuilderAnalyzer.ts
|
|
1632
|
+
var import_typescript9 = __toESM(require("typescript"), 1);
|
|
1633
|
+
function analyzeQueryBuilderForSchema(methodDeclaration, checker, options = {}) {
|
|
1634
|
+
const body = methodDeclaration.body;
|
|
1635
|
+
if (!body) {
|
|
1636
|
+
return null;
|
|
1637
|
+
}
|
|
1638
|
+
const trackedSchema = analyzeWithVariableTracking(body, checker, options);
|
|
1639
|
+
if (trackedSchema) {
|
|
1640
|
+
return trackedSchema;
|
|
1641
|
+
}
|
|
1642
|
+
const returnStatement = findReturnStatement(body);
|
|
1643
|
+
if (!returnStatement) {
|
|
1644
|
+
return null;
|
|
1645
|
+
}
|
|
1646
|
+
const callChain = analyzeReturnExpression(returnStatement.expression);
|
|
1647
|
+
if (!callChain) {
|
|
1648
|
+
return null;
|
|
1649
|
+
}
|
|
1650
|
+
return parseQueryBuilderChain(callChain, checker, options);
|
|
1651
|
+
}
|
|
1652
|
+
function analyzeQueryBuilderWithDetails(methodDeclaration, checker, options = {}, operationInfo) {
|
|
1653
|
+
const schema = analyzeQueryBuilderForSchema(methodDeclaration, checker, options);
|
|
1654
|
+
return {
|
|
1655
|
+
detected: schema !== null,
|
|
1656
|
+
schema,
|
|
1657
|
+
...operationInfo
|
|
1658
|
+
};
|
|
1659
|
+
}
|
|
1660
|
+
function analyzeWithVariableTracking(body, checker, options) {
|
|
1661
|
+
let queryBuilderVar = null;
|
|
1662
|
+
let entityName = null;
|
|
1663
|
+
const selectedFields = /* @__PURE__ */ new Set();
|
|
1664
|
+
const includes = {};
|
|
1665
|
+
let isPaged = false;
|
|
1666
|
+
let hasReturn = false;
|
|
1667
|
+
for (const statement of body.statements) {
|
|
1668
|
+
if (import_typescript9.default.isReturnStatement(statement)) {
|
|
1669
|
+
hasReturn = true;
|
|
1670
|
+
const returnExpr = statement.expression;
|
|
1671
|
+
if (returnExpr && import_typescript9.default.isCallExpression(returnExpr)) {
|
|
1672
|
+
const callExpr = returnExpr;
|
|
1673
|
+
if (import_typescript9.default.isIdentifier(callExpr.expression) && queryBuilderVar) {
|
|
1674
|
+
const varName = callExpr.expression.text;
|
|
1675
|
+
if (varName === queryBuilderVar) {
|
|
1676
|
+
const methodName = callExpr.expression.text;
|
|
1677
|
+
if (methodName === "executePaged") {
|
|
1678
|
+
isPaged = true;
|
|
1679
|
+
}
|
|
1680
|
+
}
|
|
1681
|
+
}
|
|
1682
|
+
if (import_typescript9.default.isPropertyAccessExpression(callExpr.expression) && queryBuilderVar) {
|
|
1683
|
+
const propAccess = callExpr.expression;
|
|
1684
|
+
if (import_typescript9.default.isIdentifier(propAccess.expression) && propAccess.expression.text === queryBuilderVar) {
|
|
1685
|
+
const methodName = propAccess.name.text;
|
|
1686
|
+
if (methodName === "executePaged") {
|
|
1687
|
+
isPaged = true;
|
|
1688
|
+
}
|
|
1689
|
+
}
|
|
1690
|
+
}
|
|
1691
|
+
}
|
|
1692
|
+
continue;
|
|
1693
|
+
}
|
|
1694
|
+
if (!import_typescript9.default.isExpressionStatement(statement)) {
|
|
1695
|
+
if (import_typescript9.default.isVariableStatement(statement)) {
|
|
1696
|
+
for (const declaration of statement.declarationList.declarations) {
|
|
1697
|
+
if (!import_typescript9.default.isIdentifier(declaration.name)) continue;
|
|
1698
|
+
const varName = declaration.name.text;
|
|
1699
|
+
const initializer = declaration.initializer;
|
|
1700
|
+
if (!initializer || !import_typescript9.default.isCallExpression(initializer)) continue;
|
|
1701
|
+
const opInfo = extractChainedOperation(initializer);
|
|
1702
|
+
if (opInfo && (opInfo.operation === "selectFromEntity" || opInfo.operation === "selectFrom")) {
|
|
1703
|
+
queryBuilderVar = varName;
|
|
1704
|
+
if (opInfo.entityName) {
|
|
1705
|
+
entityName = opInfo.entityName;
|
|
1706
|
+
}
|
|
1707
|
+
}
|
|
1708
|
+
}
|
|
1709
|
+
}
|
|
1710
|
+
continue;
|
|
1711
|
+
}
|
|
1712
|
+
const expr = statement.expression;
|
|
1713
|
+
if (import_typescript9.default.isBinaryExpression(expr) && expr.operatorToken.kind === import_typescript9.default.SyntaxKind.EqualsToken) {
|
|
1714
|
+
if (!import_typescript9.default.isIdentifier(expr.left)) {
|
|
1715
|
+
continue;
|
|
1716
|
+
}
|
|
1717
|
+
const varName = expr.left.text;
|
|
1718
|
+
const rightSide = expr.right;
|
|
1719
|
+
if (import_typescript9.default.isCallExpression(rightSide)) {
|
|
1720
|
+
const opInfo = extractChainedOperation(rightSide);
|
|
1721
|
+
if (opInfo) {
|
|
1722
|
+
if (opInfo.operation === "selectFromEntity" || opInfo.operation === "selectFrom") {
|
|
1723
|
+
queryBuilderVar = varName;
|
|
1724
|
+
if (opInfo.entityName) {
|
|
1725
|
+
entityName = opInfo.entityName;
|
|
1726
|
+
}
|
|
1727
|
+
}
|
|
1728
|
+
if ((opInfo.operation === "select" || opInfo.operation === "include") && queryBuilderVar === varName) {
|
|
1729
|
+
if (opInfo.operation === "select") {
|
|
1730
|
+
for (const field of opInfo.fields || []) {
|
|
1731
|
+
selectedFields.add(field);
|
|
1732
|
+
}
|
|
1733
|
+
} else if (opInfo.operation === "include" && opInfo.includeArg) {
|
|
1734
|
+
const parsedIncludes = parseIncludeObjectLiteral(opInfo.includeArg);
|
|
1735
|
+
if (parsedIncludes) {
|
|
1736
|
+
for (const [relName, relSchema] of Object.entries(parsedIncludes)) {
|
|
1737
|
+
includes[relName] = relSchema;
|
|
1738
|
+
}
|
|
1739
|
+
}
|
|
1740
|
+
}
|
|
1741
|
+
}
|
|
1742
|
+
}
|
|
1743
|
+
}
|
|
1744
|
+
}
|
|
1745
|
+
}
|
|
1746
|
+
if (!hasReturn || !queryBuilderVar || !entityName) {
|
|
1747
|
+
return null;
|
|
1748
|
+
}
|
|
1749
|
+
return {
|
|
1750
|
+
entityName,
|
|
1751
|
+
selectedFields: Array.from(selectedFields),
|
|
1752
|
+
includes,
|
|
1753
|
+
isPaged
|
|
1754
|
+
};
|
|
1755
|
+
}
|
|
1756
|
+
function extractChainedOperation(callExpr) {
|
|
1757
|
+
if (import_typescript9.default.isIdentifier(callExpr.expression)) {
|
|
1758
|
+
const methodName2 = callExpr.expression.text;
|
|
1759
|
+
if (methodName2 === "selectFromEntity" || methodName2 === "selectFrom") {
|
|
1760
|
+
const entityArg = callExpr.arguments[0];
|
|
1761
|
+
let entityName = null;
|
|
1762
|
+
if (import_typescript9.default.isIdentifier(entityArg)) {
|
|
1763
|
+
entityName = entityArg.text;
|
|
1764
|
+
} else if (import_typescript9.default.isPropertyAccessExpression(entityArg)) {
|
|
1765
|
+
entityName = entityArg.name.text;
|
|
1766
|
+
}
|
|
1767
|
+
return {
|
|
1768
|
+
operation: methodName2 === "selectFromEntity" ? "selectFromEntity" : "selectFrom",
|
|
1769
|
+
fields: null,
|
|
1770
|
+
includeArg: null,
|
|
1771
|
+
entityName
|
|
1772
|
+
};
|
|
1773
|
+
}
|
|
1774
|
+
}
|
|
1775
|
+
if (!import_typescript9.default.isPropertyAccessExpression(callExpr.expression)) {
|
|
1776
|
+
return null;
|
|
1777
|
+
}
|
|
1778
|
+
const propAccess = callExpr.expression;
|
|
1779
|
+
const methodName = propAccess.name.text;
|
|
1780
|
+
if (methodName === "select") {
|
|
1781
|
+
const fields = [];
|
|
1782
|
+
for (const arg of callExpr.arguments) {
|
|
1783
|
+
if (import_typescript9.default.isStringLiteral(arg)) {
|
|
1784
|
+
fields.push(arg.text);
|
|
1785
|
+
}
|
|
1786
|
+
}
|
|
1787
|
+
return {
|
|
1788
|
+
operation: "select",
|
|
1789
|
+
fields,
|
|
1790
|
+
includeArg: null,
|
|
1791
|
+
entityName: null
|
|
1792
|
+
};
|
|
1793
|
+
}
|
|
1794
|
+
if (methodName === "include") {
|
|
1795
|
+
return {
|
|
1796
|
+
operation: "include",
|
|
1797
|
+
fields: null,
|
|
1798
|
+
includeArg: callExpr.arguments[0] || null,
|
|
1799
|
+
entityName: null
|
|
1800
|
+
};
|
|
1801
|
+
}
|
|
1802
|
+
return null;
|
|
1803
|
+
}
|
|
1804
|
+
function parseIncludeObjectLiteral(arg) {
|
|
1805
|
+
if (!import_typescript9.default.isObjectLiteralExpression(arg)) {
|
|
1806
|
+
return null;
|
|
1807
|
+
}
|
|
1808
|
+
const includes = {};
|
|
1809
|
+
for (const prop of arg.properties) {
|
|
1810
|
+
if (!import_typescript9.default.isPropertyAssignment(prop) || !import_typescript9.default.isIdentifier(prop.name)) {
|
|
1811
|
+
continue;
|
|
1812
|
+
}
|
|
1813
|
+
const relationName = prop.name.text;
|
|
1814
|
+
const value = prop.initializer;
|
|
1815
|
+
if (value.kind === import_typescript9.default.SyntaxKind.TrueKeyword) {
|
|
1816
|
+
includes[relationName] = true;
|
|
1817
|
+
} else if (import_typescript9.default.isObjectLiteralExpression(value)) {
|
|
1818
|
+
const nestedSchema = parseNestedInclude(value, 0);
|
|
1819
|
+
if (nestedSchema) {
|
|
1820
|
+
includes[relationName] = nestedSchema;
|
|
1821
|
+
}
|
|
1822
|
+
}
|
|
1823
|
+
}
|
|
1824
|
+
return includes;
|
|
1825
|
+
}
|
|
1826
|
+
function parseNestedInclude(obj, depth) {
|
|
1827
|
+
const selectedFields = [];
|
|
1828
|
+
const includes = {};
|
|
1829
|
+
for (const prop of obj.properties) {
|
|
1830
|
+
if (!import_typescript9.default.isPropertyAssignment(prop) || !import_typescript9.default.isIdentifier(prop.name)) {
|
|
1831
|
+
continue;
|
|
1832
|
+
}
|
|
1833
|
+
const propName = prop.name.text;
|
|
1834
|
+
const value = prop.initializer;
|
|
1835
|
+
if (propName === "select" && import_typescript9.default.isArrayLiteralExpression(value)) {
|
|
1836
|
+
for (const element of value.elements) {
|
|
1837
|
+
if (import_typescript9.default.isStringLiteral(element)) {
|
|
1838
|
+
selectedFields.push(element.text);
|
|
1839
|
+
}
|
|
1840
|
+
}
|
|
1841
|
+
} else if (propName === "include" && import_typescript9.default.isObjectLiteralExpression(value)) {
|
|
1842
|
+
const nestedIncludes = parseIncludeObjectLiteral(value);
|
|
1843
|
+
if (nestedIncludes) {
|
|
1844
|
+
for (const [relName, relSchema] of Object.entries(nestedIncludes)) {
|
|
1845
|
+
includes[relName] = relSchema;
|
|
1846
|
+
}
|
|
1847
|
+
}
|
|
1848
|
+
}
|
|
1849
|
+
}
|
|
1850
|
+
return {
|
|
1851
|
+
entityName: "",
|
|
1852
|
+
selectedFields,
|
|
1853
|
+
includes,
|
|
1854
|
+
isPaged: false
|
|
1855
|
+
};
|
|
1856
|
+
}
|
|
1857
|
+
function getMethodName(expression) {
|
|
1858
|
+
if (import_typescript9.default.isIdentifier(expression)) {
|
|
1859
|
+
return expression.text;
|
|
1860
|
+
}
|
|
1861
|
+
if (import_typescript9.default.isPropertyAccessExpression(expression)) {
|
|
1862
|
+
return expression.name.text;
|
|
1863
|
+
}
|
|
1864
|
+
return null;
|
|
1865
|
+
}
|
|
1866
|
+
function findReturnStatement(body) {
|
|
1867
|
+
let returnStatement = null;
|
|
1868
|
+
for (const statement of body.statements) {
|
|
1869
|
+
if (import_typescript9.default.isReturnStatement(statement)) {
|
|
1870
|
+
if (returnStatement !== null) {
|
|
1871
|
+
return null;
|
|
1872
|
+
}
|
|
1873
|
+
returnStatement = statement;
|
|
1874
|
+
}
|
|
1875
|
+
}
|
|
1876
|
+
return returnStatement;
|
|
1877
|
+
}
|
|
1878
|
+
function analyzeReturnExpression(expression) {
|
|
1879
|
+
if (!expression) {
|
|
1880
|
+
return null;
|
|
1881
|
+
}
|
|
1882
|
+
if (import_typescript9.default.isCallExpression(expression)) {
|
|
1883
|
+
return buildCallChain(expression, null);
|
|
1884
|
+
}
|
|
1885
|
+
return null;
|
|
1886
|
+
}
|
|
1887
|
+
function buildCallChain(node, parent) {
|
|
1888
|
+
if (import_typescript9.default.isCallExpression(node)) {
|
|
1889
|
+
const callNode = {
|
|
1890
|
+
expression: node.expression,
|
|
1891
|
+
methodName: getMethodName(node.expression),
|
|
1892
|
+
arguments: node.arguments,
|
|
1893
|
+
parent
|
|
1894
|
+
};
|
|
1895
|
+
if (import_typescript9.default.isPropertyAccessExpression(node.expression)) {
|
|
1896
|
+
return buildCallChain(node.expression.expression, callNode);
|
|
1897
|
+
}
|
|
1898
|
+
return callNode;
|
|
1899
|
+
}
|
|
1900
|
+
return parent;
|
|
1901
|
+
}
|
|
1902
|
+
function parseQueryBuilderChain(chain, checker, options) {
|
|
1903
|
+
if (!chain) {
|
|
1904
|
+
return null;
|
|
1905
|
+
}
|
|
1906
|
+
const rootNode = findSelectFromEntityCall(chain);
|
|
1907
|
+
if (!rootNode) {
|
|
1908
|
+
return null;
|
|
1909
|
+
}
|
|
1910
|
+
const entityName = extractEntityName(rootNode, checker);
|
|
1911
|
+
if (!entityName) {
|
|
1912
|
+
return null;
|
|
1913
|
+
}
|
|
1914
|
+
const selectedFields = /* @__PURE__ */ new Set();
|
|
1915
|
+
const includes = {};
|
|
1916
|
+
let isPaged = false;
|
|
1917
|
+
let currentNode = chain;
|
|
1918
|
+
while (currentNode) {
|
|
1919
|
+
const methodName = currentNode.methodName;
|
|
1920
|
+
if (methodName === "select") {
|
|
1921
|
+
for (const arg of currentNode.arguments) {
|
|
1922
|
+
if (import_typescript9.default.isStringLiteral(arg)) {
|
|
1923
|
+
selectedFields.add(arg.text);
|
|
1924
|
+
}
|
|
1925
|
+
}
|
|
1926
|
+
} else if (methodName === "include") {
|
|
1927
|
+
parseIncludeArgument(currentNode.arguments[0], includes, checker, options, 0);
|
|
1928
|
+
} else if (methodName === "executePaged") {
|
|
1929
|
+
isPaged = true;
|
|
1930
|
+
}
|
|
1931
|
+
currentNode = currentNode.parent;
|
|
1932
|
+
}
|
|
1933
|
+
return {
|
|
1934
|
+
entityName,
|
|
1935
|
+
selectedFields: Array.from(selectedFields),
|
|
1936
|
+
includes,
|
|
1937
|
+
isPaged
|
|
1938
|
+
};
|
|
1939
|
+
}
|
|
1940
|
+
function findSelectFromEntityCall(chain) {
|
|
1941
|
+
let currentNode = chain;
|
|
1942
|
+
let lastNode = null;
|
|
1943
|
+
while (currentNode) {
|
|
1944
|
+
if (currentNode.methodName === "selectFromEntity" || currentNode.methodName === "selectFrom") {
|
|
1945
|
+
return currentNode;
|
|
1946
|
+
}
|
|
1947
|
+
lastNode = currentNode;
|
|
1948
|
+
currentNode = currentNode.parent;
|
|
1949
|
+
}
|
|
1950
|
+
return lastNode;
|
|
1951
|
+
}
|
|
1952
|
+
function extractEntityName(callNode, checker) {
|
|
1953
|
+
if (callNode.arguments.length === 0) {
|
|
1954
|
+
return null;
|
|
1955
|
+
}
|
|
1956
|
+
const entityArg = callNode.arguments[0];
|
|
1957
|
+
if (import_typescript9.default.isIdentifier(entityArg)) {
|
|
1958
|
+
return entityArg.text;
|
|
1959
|
+
}
|
|
1960
|
+
if (import_typescript9.default.isPropertyAccessExpression(entityArg)) {
|
|
1961
|
+
return entityArg.name.text;
|
|
1962
|
+
}
|
|
1963
|
+
return null;
|
|
1964
|
+
}
|
|
1965
|
+
function parseIncludeArgument(arg, includes, checker, options, depth) {
|
|
1966
|
+
if (!arg) {
|
|
1967
|
+
return;
|
|
1968
|
+
}
|
|
1969
|
+
if (import_typescript9.default.isObjectLiteralExpression(arg)) {
|
|
1970
|
+
for (const prop of arg.properties) {
|
|
1971
|
+
if (!import_typescript9.default.isPropertyAssignment(prop) || !import_typescript9.default.isIdentifier(prop.name)) {
|
|
1972
|
+
continue;
|
|
1973
|
+
}
|
|
1974
|
+
const relationName = prop.name.text;
|
|
1975
|
+
const value = prop.initializer;
|
|
1976
|
+
if (value.kind === import_typescript9.default.SyntaxKind.TrueKeyword) {
|
|
1977
|
+
includes[relationName] = true;
|
|
1978
|
+
} else if (import_typescript9.default.isObjectLiteralExpression(value)) {
|
|
1979
|
+
const maxDepth = options.maxDepth ?? 5;
|
|
1980
|
+
if (depth < maxDepth) {
|
|
1981
|
+
const nestedSchema = parseNestedInclude(value, depth + 1);
|
|
1982
|
+
if (nestedSchema) {
|
|
1983
|
+
includes[relationName] = nestedSchema;
|
|
1984
|
+
}
|
|
1985
|
+
}
|
|
1986
|
+
}
|
|
1987
|
+
}
|
|
1988
|
+
}
|
|
1989
|
+
}
|
|
1990
|
+
|
|
1991
|
+
// src/compiler/schema/queryBuilderSchemaBuilder.ts
|
|
1992
|
+
var import_typescript10 = require("typescript");
|
|
1993
|
+
function wrapInPaginatedResult(schema) {
|
|
1994
|
+
return {
|
|
1995
|
+
type: "object",
|
|
1996
|
+
properties: {
|
|
1997
|
+
items: {
|
|
1998
|
+
type: "array",
|
|
1999
|
+
items: schema
|
|
2000
|
+
},
|
|
2001
|
+
page: { type: "integer" },
|
|
2002
|
+
pageSize: { type: "integer" },
|
|
2003
|
+
totalItems: { type: "integer" }
|
|
2004
|
+
},
|
|
2005
|
+
required: ["items", "page", "pageSize", "totalItems"]
|
|
2006
|
+
};
|
|
2007
|
+
}
|
|
2008
|
+
|
|
1582
2009
|
// src/compiler/schema/openapi.ts
|
|
1583
2010
|
var METAL_ORM_WRAPPER_NAMES2 = ["BelongsToReference", "HasOneReference", "HasManyCollection", "ManyToManyCollection"];
|
|
1584
2011
|
function generateOpenAPI(controllers, checker, options = {}) {
|
|
@@ -1591,7 +2018,12 @@ function generateOpenAPI(controllers, checker, options = {}) {
|
|
|
1591
2018
|
mode: "response"
|
|
1592
2019
|
};
|
|
1593
2020
|
const paths = {};
|
|
1594
|
-
const { onProgress } = options;
|
|
2021
|
+
const { onProgress, onQueryBuilderProgress } = options;
|
|
2022
|
+
let totalOperations = 0;
|
|
2023
|
+
for (const controller of controllers) {
|
|
2024
|
+
totalOperations += controller.operations.length;
|
|
2025
|
+
}
|
|
2026
|
+
let currentOperation = 0;
|
|
1595
2027
|
for (let i = 0; i < controllers.length; i++) {
|
|
1596
2028
|
const controller = controllers[i];
|
|
1597
2029
|
if (onProgress) {
|
|
@@ -1603,6 +2035,32 @@ function generateOpenAPI(controllers, checker, options = {}) {
|
|
|
1603
2035
|
paths[fullPath] = {};
|
|
1604
2036
|
}
|
|
1605
2037
|
const method = operation.httpMethod.toLowerCase();
|
|
2038
|
+
const analysisResult = analyzeQueryBuilderWithDetails(
|
|
2039
|
+
operation.methodDeclaration,
|
|
2040
|
+
checker,
|
|
2041
|
+
{},
|
|
2042
|
+
{
|
|
2043
|
+
methodName: operation.operationId,
|
|
2044
|
+
httpMethod: operation.httpMethod,
|
|
2045
|
+
path: operation.path,
|
|
2046
|
+
operationId: operation.operationId
|
|
2047
|
+
}
|
|
2048
|
+
);
|
|
2049
|
+
if (onQueryBuilderProgress) {
|
|
2050
|
+
currentOperation++;
|
|
2051
|
+
onQueryBuilderProgress({
|
|
2052
|
+
controller: controller.className,
|
|
2053
|
+
operation: operation.operationId,
|
|
2054
|
+
method: operation.httpMethod,
|
|
2055
|
+
path: operation.path,
|
|
2056
|
+
queryBuilderDetected: analysisResult.detected,
|
|
2057
|
+
entityName: analysisResult.schema?.entityName,
|
|
2058
|
+
selectedFields: analysisResult.schema?.selectedFields,
|
|
2059
|
+
isPaged: analysisResult.schema?.isPaged,
|
|
2060
|
+
current: currentOperation,
|
|
2061
|
+
total: totalOperations
|
|
2062
|
+
});
|
|
2063
|
+
}
|
|
1606
2064
|
paths[fullPath][method] = buildOperation(operation, ctx, controller.consumes);
|
|
1607
2065
|
}
|
|
1608
2066
|
}
|
|
@@ -1733,6 +2191,88 @@ function convertToOpenApiPath(basePath, path4) {
|
|
|
1733
2191
|
}
|
|
1734
2192
|
return fullPath;
|
|
1735
2193
|
}
|
|
2194
|
+
function tryInferQueryBuilderSchema(operation, checker) {
|
|
2195
|
+
return analyzeQueryBuilderForSchema(operation.methodDeclaration, checker) ?? null;
|
|
2196
|
+
}
|
|
2197
|
+
function getEntityTypeFromReturnType(operation, checker) {
|
|
2198
|
+
const returnType = operation.returnType;
|
|
2199
|
+
const unwrapPromise2 = (type) => {
|
|
2200
|
+
const symbol2 = type.getSymbol();
|
|
2201
|
+
if (symbol2?.getName() === "Promise") {
|
|
2202
|
+
const typeArgs = type.typeArguments;
|
|
2203
|
+
if (typeArgs && typeArgs.length > 0) {
|
|
2204
|
+
return typeArgs[0];
|
|
2205
|
+
}
|
|
2206
|
+
}
|
|
2207
|
+
return type;
|
|
2208
|
+
};
|
|
2209
|
+
const innerType = unwrapPromise2(returnType);
|
|
2210
|
+
const symbol = innerType.getSymbol();
|
|
2211
|
+
if (symbol?.getName() === "PaginatedResult") {
|
|
2212
|
+
const typeArgs = innerType.typeArguments;
|
|
2213
|
+
if (typeArgs && typeArgs.length > 0) {
|
|
2214
|
+
return typeArgs[0];
|
|
2215
|
+
}
|
|
2216
|
+
}
|
|
2217
|
+
return null;
|
|
2218
|
+
}
|
|
2219
|
+
function filterSchemaByQueryBuilder(querySchema, operation, ctx) {
|
|
2220
|
+
const entityType = getEntityTypeFromReturnType(operation, ctx.checker);
|
|
2221
|
+
if (!entityType) {
|
|
2222
|
+
return {};
|
|
2223
|
+
}
|
|
2224
|
+
const entitySchema = typeToJsonSchema(entityType, ctx);
|
|
2225
|
+
let baseSchema = entitySchema;
|
|
2226
|
+
if (entitySchema.$ref && entitySchema.$ref.startsWith("#/components/schemas/")) {
|
|
2227
|
+
const schemaName = entitySchema.$ref.replace("#/components/schemas/", "");
|
|
2228
|
+
const componentSchema = ctx.components.get(schemaName);
|
|
2229
|
+
if (componentSchema) {
|
|
2230
|
+
baseSchema = componentSchema;
|
|
2231
|
+
}
|
|
2232
|
+
}
|
|
2233
|
+
if (!baseSchema.properties || Object.keys(baseSchema.properties).length === 0) {
|
|
2234
|
+
return {};
|
|
2235
|
+
}
|
|
2236
|
+
const filteredSchema = buildFilteredSchema(querySchema, baseSchema);
|
|
2237
|
+
if (querySchema.isPaged) {
|
|
2238
|
+
return wrapInPaginatedResult(filteredSchema);
|
|
2239
|
+
}
|
|
2240
|
+
return filteredSchema;
|
|
2241
|
+
}
|
|
2242
|
+
function buildFilteredSchema(querySchema, entitySchema) {
|
|
2243
|
+
const properties = {};
|
|
2244
|
+
const required = [];
|
|
2245
|
+
for (const field of querySchema.selectedFields) {
|
|
2246
|
+
if (entitySchema.properties?.[field]) {
|
|
2247
|
+
properties[field] = entitySchema.properties[field];
|
|
2248
|
+
if (entitySchema.required && entitySchema.required.includes(field)) {
|
|
2249
|
+
required.push(field);
|
|
2250
|
+
}
|
|
2251
|
+
}
|
|
2252
|
+
}
|
|
2253
|
+
for (const [relationName, includeSpec] of Object.entries(querySchema.includes)) {
|
|
2254
|
+
if (entitySchema.properties?.[relationName]) {
|
|
2255
|
+
properties[relationName] = {
|
|
2256
|
+
type: "object",
|
|
2257
|
+
properties: {
|
|
2258
|
+
id: { type: "integer" }
|
|
2259
|
+
},
|
|
2260
|
+
required: ["id"]
|
|
2261
|
+
};
|
|
2262
|
+
if (entitySchema.required && entitySchema.required.includes(relationName)) {
|
|
2263
|
+
required.push(relationName);
|
|
2264
|
+
}
|
|
2265
|
+
}
|
|
2266
|
+
}
|
|
2267
|
+
const schema = {
|
|
2268
|
+
type: "object",
|
|
2269
|
+
properties
|
|
2270
|
+
};
|
|
2271
|
+
if (required.length > 0) {
|
|
2272
|
+
schema.required = required;
|
|
2273
|
+
}
|
|
2274
|
+
return schema;
|
|
2275
|
+
}
|
|
1736
2276
|
function buildOperation(operation, ctx, controllerConsumes) {
|
|
1737
2277
|
const op = {
|
|
1738
2278
|
operationId: operation.operationId,
|
|
@@ -1747,7 +2287,18 @@ function buildOperation(operation, ctx, controllerConsumes) {
|
|
|
1747
2287
|
op.parameters = parameters;
|
|
1748
2288
|
}
|
|
1749
2289
|
const responseCtx = { ...ctx, mode: "response" };
|
|
1750
|
-
|
|
2290
|
+
let responseSchema;
|
|
2291
|
+
const querySchema = tryInferQueryBuilderSchema(operation, ctx.checker);
|
|
2292
|
+
if (querySchema) {
|
|
2293
|
+
const entityType = getEntityTypeFromReturnType(operation, ctx.checker);
|
|
2294
|
+
if (entityType) {
|
|
2295
|
+
responseSchema = filterSchemaByQueryBuilder(querySchema, operation, responseCtx);
|
|
2296
|
+
} else {
|
|
2297
|
+
responseSchema = typeToJsonSchema(operation.returnType, responseCtx, operation.returnTypeNode);
|
|
2298
|
+
}
|
|
2299
|
+
} else {
|
|
2300
|
+
responseSchema = typeToJsonSchema(operation.returnType, responseCtx, operation.returnTypeNode);
|
|
2301
|
+
}
|
|
1751
2302
|
const status = operation.httpMethod === "POST" ? 201 : 200;
|
|
1752
2303
|
op.responses[status] = {
|
|
1753
2304
|
description: status === 201 ? "Created" : "OK",
|
|
@@ -1789,12 +2340,12 @@ function mergeBodySchemaAnnotations(bodyParam, ctx, schema) {
|
|
|
1789
2340
|
const declarations = typeSymbol.getDeclarations();
|
|
1790
2341
|
if (!declarations || declarations.length === 0) return schema;
|
|
1791
2342
|
const classDecl = declarations[0];
|
|
1792
|
-
if (!
|
|
2343
|
+
if (!import_typescript11.default.isClassDeclaration(classDecl)) return schema;
|
|
1793
2344
|
const result = { ...schema };
|
|
1794
2345
|
const props = { ...result.properties };
|
|
1795
2346
|
for (const member of classDecl.members) {
|
|
1796
|
-
if (!
|
|
1797
|
-
const propName =
|
|
2347
|
+
if (!import_typescript11.default.isPropertyDeclaration(member) || !member.name) continue;
|
|
2348
|
+
const propName = import_typescript11.default.isIdentifier(member.name) ? member.name.text : null;
|
|
1798
2349
|
if (!propName) continue;
|
|
1799
2350
|
if (!props[propName]) continue;
|
|
1800
2351
|
const frags = extractPropertySchemaFragments(ctx.checker, member);
|
|
@@ -1807,7 +2358,7 @@ function mergeBodySchemaAnnotations(bodyParam, ctx, schema) {
|
|
|
1807
2358
|
}
|
|
1808
2359
|
|
|
1809
2360
|
// src/compiler/manifest/emit.ts
|
|
1810
|
-
var
|
|
2361
|
+
var import_typescript12 = __toESM(require("typescript"), 1);
|
|
1811
2362
|
function generateManifest(controllers, checker, version, validationMode = "ajv-runtime") {
|
|
1812
2363
|
const components = /* @__PURE__ */ new Map();
|
|
1813
2364
|
const ctx = {
|
|
@@ -1829,7 +2380,7 @@ function generateManifest(controllers, checker, version, validationMode = "ajv-r
|
|
|
1829
2380
|
generator: {
|
|
1830
2381
|
name: "adorn-api",
|
|
1831
2382
|
version,
|
|
1832
|
-
typescript:
|
|
2383
|
+
typescript: import_typescript12.default.version
|
|
1833
2384
|
},
|
|
1834
2385
|
schemas: {
|
|
1835
2386
|
kind: "openapi-3.1",
|
|
@@ -2315,7 +2866,7 @@ async function isStale(params) {
|
|
|
2315
2866
|
// src/compiler/cache/writeCache.ts
|
|
2316
2867
|
var import_node_fs4 = __toESM(require("fs"), 1);
|
|
2317
2868
|
var import_node_path4 = __toESM(require("path"), 1);
|
|
2318
|
-
var
|
|
2869
|
+
var import_typescript13 = __toESM(require("typescript"), 1);
|
|
2319
2870
|
function statMtimeMs2(p) {
|
|
2320
2871
|
return import_node_fs4.default.statSync(p).mtimeMs;
|
|
2321
2872
|
}
|
|
@@ -2348,7 +2899,7 @@ function writeCache(params) {
|
|
|
2348
2899
|
generator: {
|
|
2349
2900
|
name: "adorn-api",
|
|
2350
2901
|
version: params.adornVersion,
|
|
2351
|
-
typescript:
|
|
2902
|
+
typescript: import_typescript13.default.version
|
|
2352
2903
|
},
|
|
2353
2904
|
project: {
|
|
2354
2905
|
tsconfigPath: params.tsconfigAbs,
|
|
@@ -3101,7 +3652,7 @@ function getEdgesByRelation(graph, relation) {
|
|
|
3101
3652
|
}
|
|
3102
3653
|
|
|
3103
3654
|
// src/compiler/graph/builder.ts
|
|
3104
|
-
var
|
|
3655
|
+
var import_typescript14 = __toESM(require("typescript"), 1);
|
|
3105
3656
|
|
|
3106
3657
|
// src/compiler/graph/schemaGraph.ts
|
|
3107
3658
|
var SchemaGraph = class {
|
|
@@ -3353,7 +3904,7 @@ var SchemaGraph = class {
|
|
|
3353
3904
|
};
|
|
3354
3905
|
|
|
3355
3906
|
// src/cli.ts
|
|
3356
|
-
var
|
|
3907
|
+
var import_typescript15 = __toESM(require("typescript"), 1);
|
|
3357
3908
|
var import_node_process2 = __toESM(require("process"), 1);
|
|
3358
3909
|
var import_meta2 = {};
|
|
3359
3910
|
var ADORN_VERSION = (() => {
|
|
@@ -3432,7 +3983,7 @@ function sanitizeForJson(obj) {
|
|
|
3432
3983
|
return result;
|
|
3433
3984
|
}
|
|
3434
3985
|
function buildControllerGraph(controllers) {
|
|
3435
|
-
const graph = createGraph(
|
|
3986
|
+
const graph = createGraph(import_typescript15.default.version);
|
|
3436
3987
|
const nodeMap = /* @__PURE__ */ new Map();
|
|
3437
3988
|
for (const ctrl of controllers) {
|
|
3438
3989
|
const nodeId = `Controller:${ctrl.className}`;
|
|
@@ -3524,6 +4075,7 @@ async function buildCommand(args) {
|
|
|
3524
4075
|
const verbose = args.includes("--verbose");
|
|
3525
4076
|
const quiet = args.includes("--quiet");
|
|
3526
4077
|
const split = args.includes("--split");
|
|
4078
|
+
const showQueryBuilder = args.includes("--show-query-builder");
|
|
3527
4079
|
const splitStrategyIndex = args.indexOf("--split-strategy");
|
|
3528
4080
|
const splitStrategy = splitStrategyIndex !== -1 ? args[splitStrategyIndex + 1] : void 0;
|
|
3529
4081
|
const splitThresholdIndex = args.indexOf("--split-threshold");
|
|
@@ -3543,7 +4095,7 @@ async function buildCommand(args) {
|
|
|
3543
4095
|
outDir: outputDir,
|
|
3544
4096
|
project: projectPath,
|
|
3545
4097
|
adornVersion: ADORN_VERSION,
|
|
3546
|
-
typescriptVersion:
|
|
4098
|
+
typescriptVersion: import_typescript15.default.version
|
|
3547
4099
|
});
|
|
3548
4100
|
if (!stale.stale) {
|
|
3549
4101
|
progress.completePhase("staleness-check");
|
|
@@ -3584,6 +4136,12 @@ async function buildCommand(args) {
|
|
|
3584
4136
|
}
|
|
3585
4137
|
}
|
|
3586
4138
|
progress.startPhase("openapi", "Generating OpenAPI schema");
|
|
4139
|
+
const queryBuilderStats = {
|
|
4140
|
+
totalOperations,
|
|
4141
|
+
detected: 0,
|
|
4142
|
+
fallback: 0,
|
|
4143
|
+
operations: []
|
|
4144
|
+
};
|
|
3587
4145
|
const openapiSpinner = new Spinner("Processing schemas");
|
|
3588
4146
|
if (!quiet) openapiSpinner.start();
|
|
3589
4147
|
const openapi = generateOpenAPI(controllers, checker, {
|
|
@@ -3593,6 +4151,31 @@ async function buildCommand(args) {
|
|
|
3593
4151
|
if (!quiet) {
|
|
3594
4152
|
openapiSpinner.setStatus(`${message} (${current}/${total})`);
|
|
3595
4153
|
}
|
|
4154
|
+
},
|
|
4155
|
+
onQueryBuilderProgress: (info) => {
|
|
4156
|
+
if (info.queryBuilderDetected) {
|
|
4157
|
+
queryBuilderStats.detected++;
|
|
4158
|
+
} else {
|
|
4159
|
+
queryBuilderStats.fallback++;
|
|
4160
|
+
}
|
|
4161
|
+
queryBuilderStats.operations.push({
|
|
4162
|
+
operationId: info.operation,
|
|
4163
|
+
method: info.method,
|
|
4164
|
+
path: info.path,
|
|
4165
|
+
detected: info.queryBuilderDetected,
|
|
4166
|
+
entityName: info.entityName,
|
|
4167
|
+
selectedFields: info.selectedFields,
|
|
4168
|
+
isPaged: info.isPaged
|
|
4169
|
+
});
|
|
4170
|
+
if (showQueryBuilder || verbose) {
|
|
4171
|
+
if (info.queryBuilderDetected) {
|
|
4172
|
+
const fieldsStr = info.selectedFields && info.selectedFields.length > 0 ? ` [select: ${info.selectedFields.join(",")}]` : "";
|
|
4173
|
+
const pagedStr = info.isPaged ? " (paged)" : "";
|
|
4174
|
+
progress.verboseLog(` \u2713 Query builder: ${info.method} ${info.path} \u2192 ${info.entityName}${fieldsStr}${pagedStr}`);
|
|
4175
|
+
} else {
|
|
4176
|
+
progress.verboseLog(` \u25CB No query builder: ${info.method} ${info.path} \u2192 using full entity schema`);
|
|
4177
|
+
}
|
|
4178
|
+
}
|
|
3596
4179
|
}
|
|
3597
4180
|
});
|
|
3598
4181
|
if (!quiet) {
|
|
@@ -3651,6 +4234,17 @@ async function buildCommand(args) {
|
|
|
3651
4234
|
}
|
|
3652
4235
|
}
|
|
3653
4236
|
progress.completePhase("openapi", `Generated ${schemaCount} schema(s)${splitEnabled ? " (split into groups)" : ""}`);
|
|
4237
|
+
if (showQueryBuilder && totalOperations > 0) {
|
|
4238
|
+
log("");
|
|
4239
|
+
log("Query Builder Analysis:");
|
|
4240
|
+
log(` Operations analyzed: ${totalOperations}`);
|
|
4241
|
+
log(` Patterns detected: ${queryBuilderStats.detected} (${Math.round(queryBuilderStats.detected / totalOperations * 100)}%)`);
|
|
4242
|
+
log(` Full schemas used: ${queryBuilderStats.fallback} (${Math.round(queryBuilderStats.fallback / totalOperations * 100)}%)`);
|
|
4243
|
+
if (queryBuilderStats.detected > 0) {
|
|
4244
|
+
const totalFields = queryBuilderStats.operations.filter((op) => op.detected && op.selectedFields).reduce((sum, op) => sum + (op.selectedFields?.length || 0), 0);
|
|
4245
|
+
log(` Fields selected: ${totalFields} total (avg ${Math.round(totalFields / queryBuilderStats.detected)} per query)`);
|
|
4246
|
+
}
|
|
4247
|
+
}
|
|
3654
4248
|
progress.startPhase("manifest", "Generating manifest");
|
|
3655
4249
|
const manifest = generateManifest(controllers, checker, ADORN_VERSION, validationMode);
|
|
3656
4250
|
progress.completePhase("manifest");
|
|
@@ -3732,7 +4326,12 @@ async function buildCommand(args) {
|
|
|
3732
4326
|
schemas: schemaCount,
|
|
3733
4327
|
sourceFiles: projectSourceFiles.length,
|
|
3734
4328
|
artifactsWritten: artifacts.map((a) => a.name),
|
|
3735
|
-
splitEnabled
|
|
4329
|
+
splitEnabled,
|
|
4330
|
+
queryBuilder: {
|
|
4331
|
+
detected: queryBuilderStats.detected,
|
|
4332
|
+
fallback: queryBuilderStats.fallback,
|
|
4333
|
+
total: totalOperations
|
|
4334
|
+
}
|
|
3736
4335
|
};
|
|
3737
4336
|
progress.printSummary(stats);
|
|
3738
4337
|
progress.printArtifacts(artifacts);
|
|
@@ -3760,30 +4359,32 @@ if (command === "build") {
|
|
|
3760
4359
|
console.log(`
|
|
3761
4360
|
adorn-api CLI v${ADORN_VERSION}
|
|
3762
4361
|
|
|
3763
|
-
Commands:
|
|
3764
|
-
|
|
3765
|
-
|
|
4362
|
+
Commands:
|
|
4363
|
+
build Generate OpenAPI and manifest from TypeScript source
|
|
4364
|
+
clean Remove generated artifacts
|
|
3766
4365
|
|
|
3767
|
-
|
|
3768
|
-
|
|
3769
|
-
|
|
3770
|
-
|
|
3771
|
-
|
|
3772
|
-
|
|
3773
|
-
|
|
3774
|
-
|
|
3775
|
-
|
|
3776
|
-
|
|
4366
|
+
Options:
|
|
4367
|
+
-p <path> Path to tsconfig.json (default: ./tsconfig.json)
|
|
4368
|
+
--output <dir> Output directory (default: .adorn)
|
|
4369
|
+
--if-stale Only rebuild if artifacts are stale
|
|
4370
|
+
--validation-mode <mode> Validation mode: none, ajv-runtime, precompiled (default: ajv-runtime)
|
|
4371
|
+
--split Enable automatic schema splitting (default: disabled)
|
|
4372
|
+
--split-strategy <mode> Override splitting strategy: controller, dependency, size, auto (default: auto)
|
|
4373
|
+
--split-threshold <num> Schema count threshold for auto-split (default: 50)
|
|
4374
|
+
--verbose Show detailed progress information
|
|
4375
|
+
--quiet Suppress non-essential output
|
|
4376
|
+
--show-query-builder Show query builder inspection details and statistics
|
|
3777
4377
|
|
|
3778
|
-
Examples:
|
|
3779
|
-
|
|
3780
|
-
|
|
3781
|
-
|
|
3782
|
-
|
|
3783
|
-
|
|
3784
|
-
|
|
3785
|
-
|
|
3786
|
-
|
|
3787
|
-
|
|
4378
|
+
Examples:
|
|
4379
|
+
adorn-api build -p ./tsconfig.json --output .adorn
|
|
4380
|
+
adorn-api build --if-stale
|
|
4381
|
+
adorn-api build --validation-mode precompiled
|
|
4382
|
+
adorn-api build --verbose
|
|
4383
|
+
adorn-api build --show-query-builder # Show query builder analysis details
|
|
4384
|
+
adorn-api build --split # Enable split mode
|
|
4385
|
+
adorn-api build --split-strategy controller # Force controller-based splitting
|
|
4386
|
+
adorn-api build --split-threshold 100 # Increase threshold to 100
|
|
4387
|
+
adorn-api clean
|
|
4388
|
+
`);
|
|
3788
4389
|
}
|
|
3789
4390
|
//# sourceMappingURL=cli.cjs.map
|