@nestia/sdk 14.0.0 → 14.0.2
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/README.md +1 -1
- package/assets/bundle/distribute/build-sdk.cjs +28 -0
- package/assets/bundle/distribute/package.json +7 -3
- package/assets/bundle/distribute/tsconfig.json +15 -105
- package/lib/INestiaConfig.d.ts +74 -34
- package/lib/NestiaSdkApplication.d.ts +60 -0
- package/lib/NestiaSdkApplication.js +121 -32
- package/lib/NestiaSdkApplication.js.map +1 -1
- package/lib/NestiaSwaggerComposer.d.ts +21 -0
- package/lib/NestiaSwaggerComposer.js +32 -13
- package/lib/NestiaSwaggerComposer.js.map +1 -1
- package/lib/analyses/AccessorAnalyzer.d.ts +26 -0
- package/lib/analyses/AccessorAnalyzer.js +26 -0
- package/lib/analyses/AccessorAnalyzer.js.map +1 -1
- package/lib/analyses/ConfigAnalyzer.d.ts +41 -0
- package/lib/analyses/ConfigAnalyzer.js +52 -77
- package/lib/analyses/ConfigAnalyzer.js.map +1 -1
- package/lib/analyses/ImportAnalyzer.d.ts +25 -0
- package/lib/analyses/ImportAnalyzer.js +25 -0
- package/lib/analyses/ImportAnalyzer.js.map +1 -1
- package/lib/analyses/ParameterNameAnalyzer.d.ts +44 -0
- package/lib/analyses/ParameterNameAnalyzer.js +63 -0
- package/lib/analyses/ParameterNameAnalyzer.js.map +1 -0
- package/lib/analyses/PathAnalyzer.d.ts +93 -1
- package/lib/analyses/PathAnalyzer.js +160 -23
- package/lib/analyses/PathAnalyzer.js.map +1 -1
- package/lib/analyses/ReflectControllerAnalyzer.d.ts +32 -0
- package/lib/analyses/ReflectControllerAnalyzer.js +24 -1
- package/lib/analyses/ReflectControllerAnalyzer.js.map +1 -1
- package/lib/analyses/ReflectHttpOperationAnalyzer.d.ts +29 -0
- package/lib/analyses/ReflectHttpOperationAnalyzer.js +35 -24
- package/lib/analyses/ReflectHttpOperationAnalyzer.js.map +1 -1
- package/lib/analyses/ReflectHttpOperationExceptionAnalyzer.d.ts +31 -0
- package/lib/analyses/ReflectHttpOperationExceptionAnalyzer.js +21 -0
- package/lib/analyses/ReflectHttpOperationExceptionAnalyzer.js.map +1 -1
- package/lib/analyses/ReflectHttpOperationParameterAnalyzer.d.ts +31 -0
- package/lib/analyses/ReflectHttpOperationParameterAnalyzer.js +143 -23
- package/lib/analyses/ReflectHttpOperationParameterAnalyzer.js.map +1 -1
- package/lib/analyses/ReflectHttpOperationResponseAnalyzer.d.ts +32 -0
- package/lib/analyses/ReflectHttpOperationResponseAnalyzer.js +27 -2
- package/lib/analyses/ReflectHttpOperationResponseAnalyzer.js.map +1 -1
- package/lib/analyses/ReflectMcpOperationAnalyzer.d.ts +29 -0
- package/lib/analyses/ReflectMcpOperationAnalyzer.js +35 -11
- package/lib/analyses/ReflectMcpOperationAnalyzer.js.map +1 -1
- package/lib/analyses/ReflectMetadataAnalyzer.d.ts +47 -0
- package/lib/analyses/ReflectMetadataAnalyzer.js +47 -0
- package/lib/analyses/ReflectMetadataAnalyzer.js.map +1 -1
- package/lib/analyses/ReflectWebSocketOperationAnalyzer.d.ts +29 -0
- package/lib/analyses/ReflectWebSocketOperationAnalyzer.js +27 -5
- package/lib/analyses/ReflectWebSocketOperationAnalyzer.js.map +1 -1
- package/lib/analyses/SecurityAnalyzer.d.ts +25 -0
- package/lib/analyses/SecurityAnalyzer.js +39 -19
- package/lib/analyses/SecurityAnalyzer.js.map +1 -1
- package/lib/analyses/SwaggerExampleAnalyzer.d.ts +31 -0
- package/lib/analyses/SwaggerExampleAnalyzer.js +36 -0
- package/lib/analyses/SwaggerExampleAnalyzer.js.map +1 -0
- package/lib/analyses/TypedHttpRouteAnalyzer.d.ts +41 -3
- package/lib/analyses/TypedHttpRouteAnalyzer.js +196 -172
- package/lib/analyses/TypedHttpRouteAnalyzer.js.map +1 -1
- package/lib/analyses/TypedMcpRouteAnalyzer.d.ts +29 -0
- package/lib/analyses/TypedMcpRouteAnalyzer.js +152 -20
- package/lib/analyses/TypedMcpRouteAnalyzer.js.map +1 -1
- package/lib/analyses/TypedWebSocketRouteAnalyzer.d.ts +19 -0
- package/lib/analyses/TypedWebSocketRouteAnalyzer.js +20 -1
- package/lib/analyses/TypedWebSocketRouteAnalyzer.js.map +1 -1
- package/lib/decorators/OperationMetadata.d.ts +6 -0
- package/lib/decorators/OperationMetadata.js +6 -0
- package/lib/decorators/OperationMetadata.js.map +1 -1
- package/lib/executable/internal/CommandParser.d.ts +19 -0
- package/lib/executable/internal/CommandParser.js +19 -0
- package/lib/executable/internal/CommandParser.js.map +1 -1
- package/lib/executable/internal/NestiaConfigLoader.d.ts +56 -0
- package/lib/executable/internal/NestiaConfigLoader.js +48 -42
- package/lib/executable/internal/NestiaConfigLoader.js.map +1 -1
- package/lib/executable/internal/NestiaSdkCommand.d.ts +60 -0
- package/lib/executable/internal/NestiaSdkCommand.js +95 -3
- package/lib/executable/internal/NestiaSdkCommand.js.map +1 -1
- package/lib/executable/internal/NestiaSdkWatcher.d.ts +81 -0
- package/lib/executable/internal/NestiaSdkWatcher.js +125 -41
- package/lib/executable/internal/NestiaSdkWatcher.js.map +1 -1
- package/lib/executable/internal/NestiaSwaggerWatch.d.ts +80 -0
- package/lib/executable/internal/NestiaSwaggerWatch.js +308 -0
- package/lib/executable/internal/NestiaSwaggerWatch.js.map +1 -0
- package/lib/executable/sdk.js +16 -1
- package/lib/executable/sdk.js.map +1 -1
- package/lib/factories/ExpressionFactory.d.ts +18 -0
- package/lib/factories/ExpressionFactory.js +21 -2
- package/lib/factories/ExpressionFactory.js.map +1 -1
- package/lib/factories/IdentifierFactory.d.ts +24 -0
- package/lib/factories/IdentifierFactory.js +24 -0
- package/lib/factories/IdentifierFactory.js.map +1 -1
- package/lib/factories/LiteralFactory.d.ts +22 -4
- package/lib/factories/LiteralFactory.js +33 -11
- package/lib/factories/LiteralFactory.js.map +1 -1
- package/lib/factories/StatementFactory.d.ts +28 -1
- package/lib/factories/StatementFactory.js +28 -1
- package/lib/factories/StatementFactory.js.map +1 -1
- package/lib/factories/TypeFactory.d.ts +24 -0
- package/lib/factories/TypeFactory.js +15 -0
- package/lib/factories/TypeFactory.js.map +1 -1
- package/lib/generates/CloneGenerator.d.ts +22 -0
- package/lib/generates/CloneGenerator.js +26 -5
- package/lib/generates/CloneGenerator.js.map +1 -1
- package/lib/generates/E2eGenerator.d.ts +19 -0
- package/lib/generates/E2eGenerator.js +19 -0
- package/lib/generates/E2eGenerator.js.map +1 -1
- package/lib/generates/SdkGenerator.d.ts +38 -0
- package/lib/generates/SdkGenerator.js +43 -5
- package/lib/generates/SdkGenerator.js.map +1 -1
- package/lib/generates/SwaggerGenerator.d.ts +36 -6
- package/lib/generates/SwaggerGenerator.js +190 -40
- package/lib/generates/SwaggerGenerator.js.map +1 -1
- package/lib/generates/internal/E2eFileProgrammer.d.ts +19 -0
- package/lib/generates/internal/E2eFileProgrammer.js +20 -1
- package/lib/generates/internal/E2eFileProgrammer.js.map +1 -1
- package/lib/generates/internal/FilePrinter.d.ts +57 -0
- package/lib/generates/internal/FilePrinter.js +74 -0
- package/lib/generates/internal/FilePrinter.js.map +1 -1
- package/lib/generates/internal/ImportDictionary.d.ts +93 -1
- package/lib/generates/internal/ImportDictionary.js +103 -2
- package/lib/generates/internal/ImportDictionary.js.map +1 -1
- package/lib/generates/internal/SdkAliasCollection.d.ts +121 -1
- package/lib/generates/internal/SdkAliasCollection.js +132 -11
- package/lib/generates/internal/SdkAliasCollection.js.map +1 -1
- package/lib/generates/internal/SdkDistributionComposer.d.ts +19 -0
- package/lib/generates/internal/SdkDistributionComposer.js +149 -52
- package/lib/generates/internal/SdkDistributionComposer.js.map +1 -1
- package/lib/generates/internal/SdkFileProgrammer.d.ts +18 -0
- package/lib/generates/internal/SdkFileProgrammer.js +101 -12
- package/lib/generates/internal/SdkFileProgrammer.js.map +1 -1
- package/lib/generates/internal/SdkHttpCloneProgrammer.d.ts +29 -0
- package/lib/generates/internal/SdkHttpCloneProgrammer.js +33 -0
- package/lib/generates/internal/SdkHttpCloneProgrammer.js.map +1 -1
- package/lib/generates/internal/SdkHttpCloneReferencer.d.ts +19 -0
- package/lib/generates/internal/SdkHttpCloneReferencer.js +78 -25
- package/lib/generates/internal/SdkHttpCloneReferencer.js.map +1 -1
- package/lib/generates/internal/SdkHttpFunctionProgrammer.d.ts +19 -0
- package/lib/generates/internal/SdkHttpFunctionProgrammer.js +40 -23
- package/lib/generates/internal/SdkHttpFunctionProgrammer.js.map +1 -1
- package/lib/generates/internal/SdkHttpNamespaceProgrammer.d.ts +19 -0
- package/lib/generates/internal/SdkHttpNamespaceProgrammer.js +46 -34
- package/lib/generates/internal/SdkHttpNamespaceProgrammer.js.map +1 -1
- package/lib/generates/internal/SdkHttpParameterProgrammer.d.ts +142 -1
- package/lib/generates/internal/SdkHttpParameterProgrammer.js +175 -6
- package/lib/generates/internal/SdkHttpParameterProgrammer.js.map +1 -1
- package/lib/generates/internal/SdkHttpRouteProgrammer.d.ts +20 -0
- package/lib/generates/internal/SdkHttpRouteProgrammer.js +36 -32
- package/lib/generates/internal/SdkHttpRouteProgrammer.js.map +1 -1
- package/lib/generates/internal/SdkHttpSimulationProgrammer.d.ts +38 -0
- package/lib/generates/internal/SdkHttpSimulationProgrammer.js +66 -18
- package/lib/generates/internal/SdkHttpSimulationProgrammer.js.map +1 -1
- package/lib/generates/internal/SdkImportWizard.d.ts +63 -0
- package/lib/generates/internal/SdkImportWizard.js +63 -0
- package/lib/generates/internal/SdkImportWizard.js.map +1 -1
- package/lib/generates/internal/SdkMcpRouteProgrammer.d.ts +17 -2
- package/lib/generates/internal/SdkMcpRouteProgrammer.js +72 -24
- package/lib/generates/internal/SdkMcpRouteProgrammer.js.map +1 -1
- package/lib/generates/internal/SdkPathTemplate.d.ts +36 -0
- package/lib/generates/internal/SdkPathTemplate.js +65 -0
- package/lib/generates/internal/SdkPathTemplate.js.map +1 -0
- package/lib/generates/internal/SdkRouteDirectory.d.ts +10 -0
- package/lib/generates/internal/SdkRouteDirectory.js +10 -0
- package/lib/generates/internal/SdkRouteDirectory.js.map +1 -1
- package/lib/generates/internal/SdkTypeProgrammer.d.ts +54 -1
- package/lib/generates/internal/SdkTypeProgrammer.js +111 -27
- package/lib/generates/internal/SdkTypeProgrammer.js.map +1 -1
- package/lib/generates/internal/SdkTypeTagProgrammer.d.ts +53 -1
- package/lib/generates/internal/SdkTypeTagProgrammer.js +407 -67
- package/lib/generates/internal/SdkTypeTagProgrammer.js.map +1 -1
- package/lib/generates/internal/SdkWebSocketCloneProgrammer.d.ts +40 -0
- package/lib/generates/internal/SdkWebSocketCloneProgrammer.js +149 -142
- package/lib/generates/internal/SdkWebSocketCloneProgrammer.js.map +1 -1
- package/lib/generates/internal/SdkWebSocketNamespaceProgrammer.d.ts +19 -0
- package/lib/generates/internal/SdkWebSocketNamespaceProgrammer.js +46 -36
- package/lib/generates/internal/SdkWebSocketNamespaceProgrammer.js.map +1 -1
- package/lib/generates/internal/SdkWebSocketParameterProgrammer.d.ts +114 -1
- package/lib/generates/internal/SdkWebSocketParameterProgrammer.js +120 -5
- package/lib/generates/internal/SdkWebSocketParameterProgrammer.js.map +1 -1
- package/lib/generates/internal/SdkWebSocketRouteProgrammer.d.ts +18 -0
- package/lib/generates/internal/SdkWebSocketRouteProgrammer.js +75 -33
- package/lib/generates/internal/SdkWebSocketRouteProgrammer.js.map +1 -1
- package/lib/generates/internal/SwaggerDescriptionComposer.d.ts +42 -0
- package/lib/generates/internal/SwaggerDescriptionComposer.js +44 -1
- package/lib/generates/internal/SwaggerDescriptionComposer.js.map +1 -1
- package/lib/generates/internal/SwaggerOperationComposer.d.ts +18 -0
- package/lib/generates/internal/SwaggerOperationComposer.js +37 -8
- package/lib/generates/internal/SwaggerOperationComposer.js.map +1 -1
- package/lib/generates/internal/SwaggerOperationParameterComposer.d.ts +40 -1
- package/lib/generates/internal/SwaggerOperationParameterComposer.js +230 -25
- package/lib/generates/internal/SwaggerOperationParameterComposer.js.map +1 -1
- package/lib/generates/internal/SwaggerOperationResponseComposer.d.ts +21 -0
- package/lib/generates/internal/SwaggerOperationResponseComposer.js +58 -7
- package/lib/generates/internal/SwaggerOperationResponseComposer.js.map +1 -1
- package/lib/internal/legacy.d.ts +342 -31
- package/lib/internal/legacy.js +207 -31
- package/lib/internal/legacy.js.map +1 -1
- package/lib/structures/INestiaProject.d.ts +10 -0
- package/lib/structures/INestiaSdkInput.d.ts +30 -0
- package/lib/structures/IOperationMetadata.d.ts +77 -0
- package/lib/structures/IReflectController.d.ts +10 -0
- package/lib/structures/IReflectHttpOperation.d.ts +10 -0
- package/lib/structures/IReflectHttpOperationException.d.ts +13 -2
- package/lib/structures/IReflectHttpOperationParameter.d.ts +55 -3
- package/lib/structures/IReflectHttpOperationSuccess.d.ts +15 -3
- package/lib/structures/IReflectImport.d.ts +10 -0
- package/lib/structures/IReflectMcpOperation.d.ts +19 -0
- package/lib/structures/IReflectMcpOperationParameter.d.ts +9 -0
- package/lib/structures/IReflectOperationError.d.ts +28 -0
- package/lib/structures/IReflectOperationError.js +22 -2
- package/lib/structures/IReflectOperationError.js.map +1 -1
- package/lib/structures/IReflectType.d.ts +9 -0
- package/lib/structures/IReflectWebSocketOperation.d.ts +10 -0
- package/lib/structures/IReflectWebSocketOperationParameter.d.ts +55 -0
- package/lib/structures/ITypedApplication.d.ts +10 -0
- package/lib/structures/ITypedHttpRoute.d.ts +18 -0
- package/lib/structures/ITypedHttpRouteException.d.ts +13 -1
- package/lib/structures/ITypedHttpRouteParameter.d.ts +48 -1
- package/lib/structures/ITypedHttpRouteSuccess.d.ts +13 -1
- package/lib/structures/ITypedMcpRoute.d.ts +11 -0
- package/lib/structures/ITypedWebSocketRoute.d.ts +18 -0
- package/lib/transform.d.ts +6 -0
- package/lib/transform.js +6 -0
- package/lib/transform.js.map +1 -1
- package/lib/utils/ArrayUtil.d.ts +31 -1
- package/lib/utils/ArrayUtil.js +32 -11
- package/lib/utils/ArrayUtil.js.map +1 -1
- package/lib/utils/EmittedJavaScriptPatcher.d.ts +20 -0
- package/lib/utils/EmittedJavaScriptPatcher.js +65 -46
- package/lib/utils/EmittedJavaScriptPatcher.js.map +1 -1
- package/lib/utils/FileRetriever.d.ts +29 -0
- package/lib/utils/FileRetriever.js +29 -0
- package/lib/utils/FileRetriever.js.map +1 -1
- package/lib/utils/HttpResponseContentTypeUtil.d.ts +41 -0
- package/lib/utils/HttpResponseContentTypeUtil.js +31 -0
- package/lib/utils/HttpResponseContentTypeUtil.js.map +1 -1
- package/lib/utils/MapUtil.d.ts +64 -1
- package/lib/utils/MapUtil.js +24 -3
- package/lib/utils/MapUtil.js.map +1 -1
- package/lib/utils/PathUtil.d.ts +31 -0
- package/lib/utils/PathUtil.js +38 -0
- package/lib/utils/PathUtil.js.map +1 -1
- package/lib/utils/SdkBundlePath.d.ts +2 -0
- package/lib/utils/SdkBundlePath.js +10 -0
- package/lib/utils/SdkBundlePath.js.map +1 -0
- package/lib/utils/SdkInputFilter.d.ts +31 -0
- package/lib/utils/SdkInputFilter.js +115 -0
- package/lib/utils/SdkInputFilter.js.map +1 -0
- package/lib/utils/SourceFinder.d.ts +45 -0
- package/lib/utils/SourceFinder.js +74 -16
- package/lib/utils/SourceFinder.js.map +1 -1
- package/lib/utils/StringUtil.d.ts +77 -2
- package/lib/utils/StringUtil.js +166 -4
- package/lib/utils/StringUtil.js.map +1 -1
- package/lib/utils/TemporaryDirectory.d.ts +60 -0
- package/lib/utils/TemporaryDirectory.js +112 -0
- package/lib/utils/TemporaryDirectory.js.map +1 -0
- package/lib/utils/TsConfigReader.d.ts +42 -0
- package/lib/utils/TsConfigReader.js +98 -14
- package/lib/utils/TsConfigReader.js.map +1 -1
- package/lib/utils/TtscExecutor.d.ts +23 -1
- package/lib/utils/TtscExecutor.js +22 -0
- package/lib/utils/TtscExecutor.js.map +1 -1
- package/lib/utils/VersioningStrategy.d.ts +39 -2
- package/lib/utils/VersioningStrategy.js +46 -13
- package/lib/utils/VersioningStrategy.js.map +1 -1
- package/lib/validators/TextPlainValidator.d.ts +19 -0
- package/lib/validators/TextPlainValidator.js +19 -0
- package/lib/validators/TextPlainValidator.js.map +1 -1
- package/native/go.mod +1 -1
- package/native/go.sum +2 -2
- package/native/sdk/register.go +12 -2
- package/native/sdk/sdk_http_rules.go +210 -0
- package/native/sdk/sdk_metadata_json.go +79 -4
- package/native/sdk/sdk_transform.go +1157 -414
- package/package.json +8 -6
- package/src/INestiaConfig.ts +74 -34
- package/src/NestiaSdkApplication.ts +129 -41
- package/src/NestiaSwaggerComposer.ts +32 -14
- package/src/analyses/AccessorAnalyzer.ts +26 -0
- package/src/analyses/ConfigAnalyzer.ts +52 -90
- package/src/analyses/ImportAnalyzer.ts +25 -0
- package/src/analyses/ParameterNameAnalyzer.ts +75 -0
- package/src/analyses/PathAnalyzer.ts +167 -23
- package/src/analyses/ReflectControllerAnalyzer.ts +34 -1
- package/src/analyses/ReflectHttpOperationAnalyzer.ts +36 -14
- package/src/analyses/ReflectHttpOperationExceptionAnalyzer.ts +31 -0
- package/src/analyses/ReflectHttpOperationParameterAnalyzer.ts +153 -39
- package/src/analyses/ReflectHttpOperationResponseAnalyzer.ts +38 -7
- package/src/analyses/ReflectMcpOperationAnalyzer.ts +38 -3
- package/src/analyses/ReflectMetadataAnalyzer.ts +47 -0
- package/src/analyses/ReflectWebSocketOperationAnalyzer.ts +40 -7
- package/src/analyses/SecurityAnalyzer.ts +45 -20
- package/src/analyses/SwaggerExampleAnalyzer.ts +39 -0
- package/src/analyses/TypedHttpRouteAnalyzer.ts +263 -198
- package/src/analyses/TypedMcpRouteAnalyzer.ts +180 -20
- package/src/analyses/TypedWebSocketRouteAnalyzer.ts +20 -0
- package/src/decorators/OperationMetadata.ts +6 -0
- package/src/executable/internal/CommandParser.ts +19 -0
- package/src/executable/internal/NestiaConfigLoader.ts +66 -50
- package/src/executable/internal/NestiaSdkCommand.ts +96 -3
- package/src/executable/internal/NestiaSdkWatcher.ts +172 -44
- package/src/executable/internal/NestiaSwaggerWatch.ts +359 -0
- package/src/executable/sdk.ts +24 -1
- package/src/factories/ExpressionFactory.ts +23 -2
- package/src/factories/IdentifierFactory.ts +24 -0
- package/src/factories/LiteralFactory.ts +51 -13
- package/src/factories/StatementFactory.ts +28 -1
- package/src/factories/TypeFactory.ts +24 -0
- package/src/generates/CloneGenerator.ts +26 -5
- package/src/generates/E2eGenerator.ts +19 -0
- package/src/generates/SdkGenerator.ts +43 -12
- package/src/generates/SwaggerGenerator.ts +229 -46
- package/src/generates/internal/E2eFileProgrammer.ts +20 -0
- package/src/generates/internal/FilePrinter.ts +71 -0
- package/src/generates/internal/ImportDictionary.ts +120 -2
- package/src/generates/internal/SdkAliasCollection.ts +144 -15
- package/src/generates/internal/SdkDistributionComposer.ts +181 -56
- package/src/generates/internal/SdkFileProgrammer.ts +126 -16
- package/src/generates/internal/SdkHttpCloneProgrammer.ts +55 -0
- package/src/generates/internal/SdkHttpCloneReferencer.ts +97 -23
- package/src/generates/internal/SdkHttpFunctionProgrammer.ts +47 -30
- package/src/generates/internal/SdkHttpNamespaceProgrammer.ts +53 -64
- package/src/generates/internal/SdkHttpParameterProgrammer.ts +295 -13
- package/src/generates/internal/SdkHttpRouteProgrammer.ts +37 -31
- package/src/generates/internal/SdkHttpSimulationProgrammer.ts +122 -18
- package/src/generates/internal/SdkImportWizard.ts +63 -0
- package/src/generates/internal/SdkMcpRouteProgrammer.ts +150 -33
- package/src/generates/internal/SdkPathTemplate.ts +88 -0
- package/src/generates/internal/SdkRouteDirectory.ts +10 -0
- package/src/generates/internal/SdkTypeProgrammer.ts +137 -36
- package/src/generates/internal/SdkTypeTagProgrammer.ts +536 -78
- package/src/generates/internal/SdkWebSocketCloneProgrammer.ts +185 -142
- package/src/generates/internal/SdkWebSocketNamespaceProgrammer.ts +62 -68
- package/src/generates/internal/SdkWebSocketParameterProgrammer.ts +205 -5
- package/src/generates/internal/SdkWebSocketRouteProgrammer.ts +89 -48
- package/src/generates/internal/SwaggerDescriptionComposer.ts +47 -1
- package/src/generates/internal/SwaggerOperationComposer.ts +38 -6
- package/src/generates/internal/SwaggerOperationParameterComposer.ts +318 -36
- package/src/generates/internal/SwaggerOperationResponseComposer.ts +74 -11
- package/src/internal/legacy-augmentation.d.ts +16 -0
- package/src/internal/legacy.ts +407 -49
- package/src/structures/INestiaProject.ts +10 -0
- package/src/structures/INestiaSdkInput.ts +30 -0
- package/src/structures/IOperationMetadata.ts +83 -0
- package/src/structures/IReflectController.ts +10 -0
- package/src/structures/IReflectHttpOperation.ts +10 -0
- package/src/structures/IReflectHttpOperationException.ts +17 -2
- package/src/structures/IReflectHttpOperationParameter.ts +56 -2
- package/src/structures/IReflectHttpOperationSuccess.ts +19 -3
- package/src/structures/IReflectImport.ts +10 -0
- package/src/structures/IReflectMcpOperation.ts +19 -0
- package/src/structures/IReflectMcpOperationParameter.ts +9 -0
- package/src/structures/IReflectOperationError.ts +31 -2
- package/src/structures/IReflectType.ts +9 -0
- package/src/structures/IReflectWebSocketOperation.ts +10 -0
- package/src/structures/IReflectWebSocketOperationParameter.ts +55 -0
- package/src/structures/ITypedApplication.ts +10 -0
- package/src/structures/ITypedHttpRoute.ts +18 -0
- package/src/structures/ITypedHttpRouteException.ts +14 -1
- package/src/structures/ITypedHttpRouteParameter.ts +48 -1
- package/src/structures/ITypedHttpRouteSuccess.ts +14 -1
- package/src/structures/ITypedMcpRoute.ts +12 -0
- package/src/structures/ITypedWebSocketRoute.ts +18 -0
- package/src/transform.ts +6 -0
- package/src/utils/ArrayUtil.ts +32 -13
- package/src/utils/EmittedJavaScriptPatcher.ts +70 -47
- package/src/utils/FileRetriever.ts +29 -0
- package/src/utils/HttpResponseContentTypeUtil.ts +41 -0
- package/src/utils/MapUtil.ts +68 -3
- package/src/utils/PathUtil.ts +38 -0
- package/src/utils/SdkBundlePath.ts +11 -0
- package/src/utils/SdkInputFilter.ts +108 -0
- package/src/utils/SourceFinder.ts +76 -18
- package/src/utils/StringUtil.ts +182 -5
- package/src/utils/TemporaryDirectory.ts +108 -0
- package/src/utils/TsConfigReader.ts +124 -26
- package/src/utils/TtscExecutor.ts +23 -1
- package/src/utils/VersioningStrategy.ts +51 -16
- package/src/validators/TextPlainValidator.ts +19 -0
- package/lib/generates/internal/SwaggerReadonlyArrayEmender.d.ts +0 -9
- package/lib/generates/internal/SwaggerReadonlyArrayEmender.js +0 -178
- package/lib/generates/internal/SwaggerReadonlyArrayEmender.js.map +0 -1
- package/lib/validators/HttpHeadersValidator.d.ts +0 -11
- package/lib/validators/HttpHeadersValidator.js +0 -15
- package/lib/validators/HttpHeadersValidator.js.map +0 -1
- package/lib/validators/HttpQueryValidator.d.ts +0 -10
- package/lib/validators/HttpQueryValidator.js +0 -14
- package/lib/validators/HttpQueryValidator.js.map +0 -1
- package/src/generates/internal/SwaggerReadonlyArrayEmender.ts +0 -264
- package/src/validators/HttpHeadersValidator.ts +0 -12
- package/src/validators/HttpQueryValidator.ts +0 -11
|
@@ -18,34 +18,40 @@ import { ITypedHttpRoute } from "../structures/ITypedHttpRoute";
|
|
|
18
18
|
import { ITypedHttpRouteException } from "../structures/ITypedHttpRouteException";
|
|
19
19
|
import { ITypedHttpRouteParameter } from "../structures/ITypedHttpRouteParameter";
|
|
20
20
|
import { ITypedHttpRouteSuccess } from "../structures/ITypedHttpRouteSuccess";
|
|
21
|
+
import { ITypedMcpRoute } from "../structures/ITypedMcpRoute";
|
|
21
22
|
import { PathUtil } from "../utils/PathUtil";
|
|
23
|
+
import { StringUtil } from "../utils/StringUtil";
|
|
22
24
|
|
|
25
|
+
/**
|
|
26
|
+
* Turns reflected HTTP operations into typed routes, one per path, and builds
|
|
27
|
+
* the shared dictionary of the JSON components HTTP and MCP routes use.
|
|
28
|
+
*
|
|
29
|
+
* @evidence contracts/common.md#principled-implementation Each operation's metadata is resolved against its own components and validated by the policy of its position, the routes carry the typed parameters, the success response, and the exceptions, and the dictionary of the routes is built after component names that collide with different definitions are renamed per controller.
|
|
30
|
+
* @evidence contracts/common.md#clear-and-simple-design Two public functions and private collectors for the component rename.
|
|
31
|
+
* @evidence contracts/common.md#prohibited-implementation-shortcuts The rename mutates only component definitions owned by analysis; consumers emit resolved structural types rather than modifying foreign cache fields or replacing names in strings.
|
|
32
|
+
* @evidence contracts/common.md#meaningful-documentation The comment states its purpose.
|
|
33
|
+
* efficient algorithms: This namespace groups operations; analyze and routeDictionary own the algorithms.
|
|
34
|
+
* reuse equivalent work: The namespace itself coordinates no completed or in-flight work.
|
|
35
|
+
* bound retention and release resources: The namespace owns no cache, handle or running task.
|
|
36
|
+
* @evidenceExclude contracts/portability.md#os-neutral-implementation TypedHttpRouteAnalyzer analyzes reflected route metadata; it does not resolve native file identity or launch a process. Source resolution and file emission belong to their filesystem owners.
|
|
37
|
+
*/
|
|
23
38
|
export namespace TypedHttpRouteAnalyzer {
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
objects: uniqueComponents(individual.flatMap((c) => c.objects)),
|
|
38
|
-
arrays: uniqueComponents(individual.flatMap((c) => c.arrays)),
|
|
39
|
-
tuples: uniqueComponents(individual.flatMap((c) => c.tuples)),
|
|
40
|
-
aliases: uniqueComponents(individual.flatMap((c) => c.aliases)),
|
|
41
|
-
});
|
|
42
|
-
return components.dictionary;
|
|
43
|
-
};
|
|
44
|
-
|
|
39
|
+
/**
|
|
40
|
+
* Returns the typed routes of one operation, one per path, or none when the
|
|
41
|
+
* metadata violates a policy; the violations are pushed to the errors.
|
|
42
|
+
*
|
|
43
|
+
* @evidence contracts/common.md#principled-implementation Each metadata is resolved against its own components and validated with the policy of its position (JSON, query, header, or text), the `@setHeader` and `@assignHeaders` tags become header directives, and the route splits the parameters by category.
|
|
44
|
+
* @evidence contracts/common.md#clear-and-simple-design One function.
|
|
45
|
+
* @evidence contracts/common.md#prohibited-implementation-shortcuts The policies come from the validators of the package.
|
|
46
|
+
* @evidence contracts/common.md#meaningful-documentation The comment states the result and the errors.
|
|
47
|
+
* efficient algorithms: Each supplied parameter and exception is cast once, policy validation belongs to MetadataFactory, and route splitting maps only the supplied paths.
|
|
48
|
+
* reuse equivalent work: Independently supplied operation metadata and position-specific validation have no shared completed or in-flight request.
|
|
49
|
+
* bound retention and release resources: Metadata dictionaries and local diagnostics belong to this synchronous operation and its returned routes; no process, handle or persistent history is retained.
|
|
50
|
+
* @evidenceExclude contracts/portability.md#os-neutral-implementation TypedHttpRouteAnalyzer.analyze analyzes reflected route metadata; it does not resolve native file identity or launch a process. Source resolution and file emission belong to their filesystem owners.
|
|
51
|
+
*/
|
|
45
52
|
export const analyze = (props: {
|
|
46
53
|
controller: IReflectController;
|
|
47
54
|
errors: IReflectOperationError[];
|
|
48
|
-
dictionary: IMetadataDictionary;
|
|
49
55
|
operation: IReflectHttpOperation;
|
|
50
56
|
paths: string[];
|
|
51
57
|
}): ITypedHttpRoute[] => {
|
|
@@ -54,10 +60,9 @@ export namespace TypedHttpRouteAnalyzer {
|
|
|
54
60
|
next: {
|
|
55
61
|
metadata: IMetadataSchema;
|
|
56
62
|
components: IMetadataComponents;
|
|
57
|
-
validate
|
|
63
|
+
validate?: MetadataFactory.Validator;
|
|
58
64
|
},
|
|
59
65
|
from: string,
|
|
60
|
-
escape: boolean,
|
|
61
66
|
): MetadataSchema => {
|
|
62
67
|
const components: MetadataComponents = MetadataComponents.from(
|
|
63
68
|
next.components,
|
|
@@ -66,16 +71,13 @@ export namespace TypedHttpRouteAnalyzer {
|
|
|
66
71
|
next.metadata,
|
|
67
72
|
components.dictionary,
|
|
68
73
|
);
|
|
69
|
-
const metaErrors: MetadataFactory.IError[] =
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
functor: next.validate, // @todo -> CHECK IN TYPIA
|
|
77
|
-
metadata,
|
|
78
|
-
});
|
|
74
|
+
const metaErrors: MetadataFactory.IError[] =
|
|
75
|
+
next.validate === undefined
|
|
76
|
+
? []
|
|
77
|
+
: MetadataFactory.validate({
|
|
78
|
+
functor: next.validate,
|
|
79
|
+
metadata,
|
|
80
|
+
});
|
|
79
81
|
if (metaErrors.length)
|
|
80
82
|
errors.push({
|
|
81
83
|
file: props.controller.file,
|
|
@@ -108,28 +110,18 @@ export namespace TypedHttpRouteAnalyzer {
|
|
|
108
110
|
example: value.example,
|
|
109
111
|
examples: value.examples,
|
|
110
112
|
type: value.type,
|
|
111
|
-
metadata: cast(value, `exception (status: ${key})
|
|
113
|
+
metadata: cast(value, `exception (status: ${key})`),
|
|
112
114
|
},
|
|
113
115
|
]),
|
|
114
116
|
);
|
|
115
117
|
const parameters: ITypedHttpRouteParameter[] =
|
|
116
118
|
props.operation.parameters.map((p) => ({
|
|
117
119
|
...p,
|
|
118
|
-
metadata: cast(
|
|
119
|
-
p,
|
|
120
|
-
`parameter (name: ${JSON.stringify(p.name)})`,
|
|
121
|
-
p.category === "body" &&
|
|
122
|
-
(p.contentType === "application/json" || p.encrypted === true),
|
|
123
|
-
),
|
|
120
|
+
metadata: cast(p, `parameter (name: ${JSON.stringify(p.name)})`),
|
|
124
121
|
}));
|
|
125
122
|
const success: ITypedHttpRouteSuccess = {
|
|
126
123
|
...props.operation.success,
|
|
127
|
-
metadata: cast(
|
|
128
|
-
props.operation.success,
|
|
129
|
-
"success",
|
|
130
|
-
props.operation.success.encrypted ||
|
|
131
|
-
props.operation.success.contentType === "application/json",
|
|
132
|
-
),
|
|
124
|
+
metadata: cast(props.operation.success, "success"),
|
|
133
125
|
setHeaders: props.operation.jsDocTags
|
|
134
126
|
.filter(
|
|
135
127
|
(t) =>
|
|
@@ -137,18 +129,23 @@ export namespace TypedHttpRouteAnalyzer {
|
|
|
137
129
|
t.text[0]!.text &&
|
|
138
130
|
(t.name === "setHeader" || t.name === "assignHeaders"),
|
|
139
131
|
)
|
|
140
|
-
.map((t) =>
|
|
141
|
-
|
|
132
|
+
.map((t) => {
|
|
133
|
+
// the words of the first line; the next lines only describe
|
|
134
|
+
const words: string[] = t
|
|
135
|
+
.text![0]!.text.split("\n")[0]!
|
|
136
|
+
.trim()
|
|
137
|
+
.split(/\s+/);
|
|
138
|
+
return t.name === "setHeader"
|
|
142
139
|
? {
|
|
143
|
-
type: "setter",
|
|
144
|
-
source:
|
|
145
|
-
target:
|
|
140
|
+
type: "setter" as const,
|
|
141
|
+
source: words[0]!,
|
|
142
|
+
target: words[1],
|
|
146
143
|
}
|
|
147
144
|
: {
|
|
148
|
-
type: "assigner",
|
|
149
|
-
source:
|
|
150
|
-
}
|
|
151
|
-
),
|
|
145
|
+
type: "assigner" as const,
|
|
146
|
+
source: words[0]!,
|
|
147
|
+
};
|
|
148
|
+
}),
|
|
152
149
|
};
|
|
153
150
|
if (errors.length) {
|
|
154
151
|
props.errors.push(...errors);
|
|
@@ -159,6 +156,7 @@ export namespace TypedHttpRouteAnalyzer {
|
|
|
159
156
|
({
|
|
160
157
|
...props.operation,
|
|
161
158
|
controller: props.controller,
|
|
159
|
+
key: props.operation.name,
|
|
162
160
|
path,
|
|
163
161
|
accessor: [...PathUtil.accessors(path), props.operation.name],
|
|
164
162
|
exceptions,
|
|
@@ -184,8 +182,21 @@ export namespace TypedHttpRouteAnalyzer {
|
|
|
184
182
|
);
|
|
185
183
|
};
|
|
186
184
|
|
|
185
|
+
/**
|
|
186
|
+
* Returns the dictionary of the components the routes actually use, after
|
|
187
|
+
* renaming components whose names collide with different definitions.
|
|
188
|
+
*
|
|
189
|
+
* @evidence contracts/common.md#principled-implementation Objects, aliases and recursive arrays/tuples share their emitted accessor-path slots, while finite and object-mediated collections remain kind-specific inline groups. Different semantic classes in one slot receive unique controller-qualified names, and the emitted dictionary follows escaped returns rather than original-only toJSON declarations.
|
|
190
|
+
* @evidence contracts/common.md#clear-and-simple-design One function over private collectors.
|
|
191
|
+
* @evidence contracts/common.md#prohibited-implementation-shortcuts Finite partition refinement preserves semantic discriminators and user payloads while component edges reference equivalence classes. Only actual component ordinals are omitted; no foreign name cache or generated text is rewritten.
|
|
192
|
+
* @evidence contracts/common.md#meaningful-documentation The comment states the result and the rename.
|
|
193
|
+
* efficient algorithms: Each refinement round encodes each distinct component body with constant-sized component edges. The partition only splits and stabilizes within the distinct component count, avoiding exponential expansion of shared DAGs.
|
|
194
|
+
* reuse equivalent work: One local partition compares all routes together, reuses graph node colors for shared children and supplies all collision groups; equivalent same-slot definitions reuse one emitted representative.
|
|
195
|
+
* bound retention and release resources: Collected nodes, partitions and visited sets are local to this synchronous call and are released with it; the returned dictionary retains only its reachable emitted representatives.
|
|
196
|
+
* @evidenceExclude contracts/portability.md#os-neutral-implementation TypedHttpRouteAnalyzer.routeDictionary analyzes reflected route metadata; it does not resolve native file identity or launch a process. Source resolution and file emission belong to their filesystem owners.
|
|
197
|
+
*/
|
|
187
198
|
export const routeDictionary = (
|
|
188
|
-
routes: Array<ITypedHttpRoute>,
|
|
199
|
+
routes: Array<ITypedHttpRoute | ITypedMcpRoute>,
|
|
189
200
|
): IMetadataDictionary => {
|
|
190
201
|
renameDuplicateComponents(routes);
|
|
191
202
|
const dictionary: IMetadataDictionary = {
|
|
@@ -194,20 +205,9 @@ export namespace TypedHttpRouteAnalyzer {
|
|
|
194
205
|
arrays: new Map(),
|
|
195
206
|
tuples: new Map(),
|
|
196
207
|
};
|
|
197
|
-
for (const route of routes)
|
|
198
|
-
for (const
|
|
199
|
-
|
|
200
|
-
...route.queryParameters,
|
|
201
|
-
...route.headerParameters,
|
|
202
|
-
...(route.queryObject ? [route.queryObject] : []),
|
|
203
|
-
...(route.body ? [route.body] : []),
|
|
204
|
-
...(route.headerObject ? [route.headerObject] : []),
|
|
205
|
-
])
|
|
206
|
-
enrollMetadata(dictionary, p.metadata);
|
|
207
|
-
for (const e of Object.values(route.exceptions))
|
|
208
|
-
enrollMetadata(dictionary, e.metadata);
|
|
209
|
-
enrollMetadata(dictionary, route.success.metadata);
|
|
210
|
-
}
|
|
208
|
+
for (const route of routes)
|
|
209
|
+
for (const metadata of routeMetadatas(route))
|
|
210
|
+
enrollMetadata(dictionary, metadata);
|
|
211
211
|
return dictionary;
|
|
212
212
|
};
|
|
213
213
|
}
|
|
@@ -221,21 +221,51 @@ type ComponentType =
|
|
|
221
221
|
|
|
222
222
|
interface IComponentEntry {
|
|
223
223
|
kind: ComponentKind;
|
|
224
|
-
route: ITypedHttpRoute;
|
|
224
|
+
route: ITypedHttpRoute | ITypedMcpRoute;
|
|
225
225
|
signature: string;
|
|
226
226
|
type: ComponentType;
|
|
227
227
|
}
|
|
228
228
|
|
|
229
|
-
const renameDuplicateComponents = (
|
|
229
|
+
const renameDuplicateComponents = (
|
|
230
|
+
routes: Array<ITypedHttpRoute | ITypedMcpRoute>,
|
|
231
|
+
): void => {
|
|
230
232
|
const entries: IComponentEntry[] = [];
|
|
231
233
|
for (const route of routes)
|
|
232
234
|
for (const metadata of routeMetadatas(route))
|
|
233
235
|
collectComponentEntries(entries, route, metadata);
|
|
236
|
+
// Original toJSON definitions participate in semantic comparison but do not
|
|
237
|
+
// become emitted declarations unless another route uses them directly.
|
|
238
|
+
const comparisonEntries: IComponentEntry[] = [];
|
|
239
|
+
for (const route of routes)
|
|
240
|
+
for (const metadata of routeMetadatas(route))
|
|
241
|
+
collectComponentEntries(
|
|
242
|
+
comparisonEntries,
|
|
243
|
+
route,
|
|
244
|
+
metadata,
|
|
245
|
+
createCollectVisited(),
|
|
246
|
+
true,
|
|
247
|
+
);
|
|
248
|
+
const signatures = componentSignatures(comparisonEntries);
|
|
249
|
+
for (const entry of entries) entry.signature = signatures.get(entry.type)!;
|
|
234
250
|
|
|
235
|
-
const used: Set<string> = new Set(
|
|
251
|
+
const used: Set<string> = new Set(
|
|
252
|
+
entries.map((e) => StringUtil.accessorsOf(e.type.name).join(".")),
|
|
253
|
+
);
|
|
236
254
|
const groups: Map<string, IComponentEntry[]> = new Map();
|
|
237
255
|
for (const entry of entries) {
|
|
238
|
-
|
|
256
|
+
// Named recursive collections also need a declaration to break cycles.
|
|
257
|
+
// Ordinary arrays and tuples remain inline forms without their own slot.
|
|
258
|
+
const slot =
|
|
259
|
+
entry.kind === "objects" ||
|
|
260
|
+
entry.kind === "aliases" ||
|
|
261
|
+
entry.type.recursive
|
|
262
|
+
? "declarations"
|
|
263
|
+
: entry.kind;
|
|
264
|
+
const name =
|
|
265
|
+
slot === "declarations"
|
|
266
|
+
? StringUtil.accessorsOf(entry.type.name).join(".")
|
|
267
|
+
: entry.type.name;
|
|
268
|
+
const key: string = `${slot}:${name}`;
|
|
239
269
|
const group: IComponentEntry[] | undefined = groups.get(key);
|
|
240
270
|
if (group === undefined) groups.set(key, [entry]);
|
|
241
271
|
else group.push(entry);
|
|
@@ -258,55 +288,100 @@ const renameDuplicateComponents = (routes: ITypedHttpRoute[]): void => {
|
|
|
258
288
|
`${prefix}.${oldName}`,
|
|
259
289
|
);
|
|
260
290
|
renamed.set(entry.signature, name);
|
|
261
|
-
used.add(name);
|
|
291
|
+
used.add(StringUtil.accessorsOf(name).join("."));
|
|
262
292
|
return name;
|
|
263
293
|
})();
|
|
264
294
|
(entry.type as { name: string }).name = next;
|
|
265
295
|
}
|
|
266
296
|
}
|
|
267
|
-
for (const route of routes)
|
|
268
|
-
for (const metadata of routeMetadatas(route))
|
|
269
|
-
clearMetadataNameCache(metadata);
|
|
270
297
|
};
|
|
271
298
|
|
|
272
|
-
const routeMetadatas = (
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
299
|
+
const routeMetadatas = (
|
|
300
|
+
route: ITypedHttpRoute | ITypedMcpRoute,
|
|
301
|
+
): MetadataSchema[] =>
|
|
302
|
+
route.protocol === "mcp"
|
|
303
|
+
? [route.inputMetadata, route.outputMetadata].filter(
|
|
304
|
+
(m): m is MetadataSchema => m !== undefined,
|
|
305
|
+
)
|
|
306
|
+
: [
|
|
307
|
+
...[
|
|
308
|
+
...route.pathParameters,
|
|
309
|
+
...route.queryParameters,
|
|
310
|
+
...route.headerParameters,
|
|
311
|
+
...(route.queryObject ? [route.queryObject] : []),
|
|
312
|
+
...(route.body ? [route.body] : []),
|
|
313
|
+
...(route.headerObject ? [route.headerObject] : []),
|
|
314
|
+
].map((p) => p.metadata),
|
|
315
|
+
...Object.values(route.exceptions).map((e) => e.metadata),
|
|
316
|
+
route.success.metadata,
|
|
317
|
+
];
|
|
284
318
|
|
|
285
319
|
const collectComponentEntries = (
|
|
286
320
|
entries: IComponentEntry[],
|
|
287
|
-
route: ITypedHttpRoute,
|
|
321
|
+
route: ITypedHttpRoute | ITypedMcpRoute,
|
|
288
322
|
metadata: MetadataSchema,
|
|
289
323
|
visited: ICollectVisited = createCollectVisited(),
|
|
324
|
+
includeOriginal: boolean = false,
|
|
290
325
|
): void => {
|
|
291
326
|
if (visited.schemas.has(metadata)) return;
|
|
292
327
|
visited.schemas.add(metadata);
|
|
293
328
|
|
|
294
329
|
if (metadata.rest !== null)
|
|
295
|
-
collectComponentEntries(
|
|
330
|
+
collectComponentEntries(
|
|
331
|
+
entries,
|
|
332
|
+
route,
|
|
333
|
+
metadata.rest,
|
|
334
|
+
visited,
|
|
335
|
+
includeOriginal,
|
|
336
|
+
);
|
|
296
337
|
if (metadata.escaped !== null) {
|
|
297
|
-
|
|
298
|
-
|
|
338
|
+
if (includeOriginal)
|
|
339
|
+
collectComponentEntries(
|
|
340
|
+
entries,
|
|
341
|
+
route,
|
|
342
|
+
metadata.escaped.original,
|
|
343
|
+
visited,
|
|
344
|
+
includeOriginal,
|
|
345
|
+
);
|
|
346
|
+
collectComponentEntries(
|
|
347
|
+
entries,
|
|
348
|
+
route,
|
|
349
|
+
metadata.escaped.returns,
|
|
350
|
+
visited,
|
|
351
|
+
includeOriginal,
|
|
352
|
+
);
|
|
299
353
|
}
|
|
354
|
+
for (const template of metadata.templates)
|
|
355
|
+
for (const elem of template.row ?? template)
|
|
356
|
+
collectComponentEntries(entries, route, elem, visited, includeOriginal);
|
|
300
357
|
for (const func of metadata.functions) {
|
|
301
358
|
for (const p of func.parameters)
|
|
302
|
-
collectComponentEntries(entries, route, p.type, visited);
|
|
303
|
-
collectComponentEntries(
|
|
359
|
+
collectComponentEntries(entries, route, p.type, visited, includeOriginal);
|
|
360
|
+
collectComponentEntries(
|
|
361
|
+
entries,
|
|
362
|
+
route,
|
|
363
|
+
func.output,
|
|
364
|
+
visited,
|
|
365
|
+
includeOriginal,
|
|
366
|
+
);
|
|
304
367
|
}
|
|
305
368
|
for (const set of metadata.sets)
|
|
306
|
-
collectComponentEntries(
|
|
369
|
+
collectComponentEntries(
|
|
370
|
+
entries,
|
|
371
|
+
route,
|
|
372
|
+
set.value,
|
|
373
|
+
visited,
|
|
374
|
+
includeOriginal,
|
|
375
|
+
);
|
|
307
376
|
for (const map of metadata.maps) {
|
|
308
|
-
collectComponentEntries(entries, route, map.key, visited);
|
|
309
|
-
collectComponentEntries(
|
|
377
|
+
collectComponentEntries(entries, route, map.key, visited, includeOriginal);
|
|
378
|
+
collectComponentEntries(
|
|
379
|
+
entries,
|
|
380
|
+
route,
|
|
381
|
+
map.value,
|
|
382
|
+
visited,
|
|
383
|
+
includeOriginal,
|
|
384
|
+
);
|
|
310
385
|
}
|
|
311
386
|
for (const array of metadata.arrays)
|
|
312
387
|
if (visited.arrays.has(array.type as MetadataArrayType) === false) {
|
|
@@ -319,6 +394,7 @@ const collectComponentEntries = (
|
|
|
319
394
|
route,
|
|
320
395
|
(array.type as MetadataArrayType as MetadataArrayType).value,
|
|
321
396
|
visited,
|
|
397
|
+
includeOriginal,
|
|
322
398
|
);
|
|
323
399
|
}
|
|
324
400
|
for (const tuple of metadata.tuples)
|
|
@@ -329,7 +405,7 @@ const collectComponentEntries = (
|
|
|
329
405
|
);
|
|
330
406
|
for (const elem of (tuple.type as MetadataTupleType as MetadataTupleType)
|
|
331
407
|
.elements)
|
|
332
|
-
collectComponentEntries(entries, route, elem, visited);
|
|
408
|
+
collectComponentEntries(entries, route, elem, visited, includeOriginal);
|
|
333
409
|
}
|
|
334
410
|
for (const alias of metadata.aliases)
|
|
335
411
|
if (visited.aliases.has(alias.type as MetadataAliasType) === false) {
|
|
@@ -342,6 +418,7 @@ const collectComponentEntries = (
|
|
|
342
418
|
route,
|
|
343
419
|
(alias.type as MetadataAliasType as MetadataAliasType).value,
|
|
344
420
|
visited,
|
|
421
|
+
includeOriginal,
|
|
345
422
|
);
|
|
346
423
|
}
|
|
347
424
|
for (const obj of metadata.objects)
|
|
@@ -352,31 +429,96 @@ const collectComponentEntries = (
|
|
|
352
429
|
);
|
|
353
430
|
for (const p of (obj.type as MetadataObjectType as MetadataObjectType)
|
|
354
431
|
.properties) {
|
|
355
|
-
collectComponentEntries(
|
|
356
|
-
|
|
432
|
+
collectComponentEntries(
|
|
433
|
+
entries,
|
|
434
|
+
route,
|
|
435
|
+
p.key,
|
|
436
|
+
visited,
|
|
437
|
+
includeOriginal,
|
|
438
|
+
);
|
|
439
|
+
collectComponentEntries(
|
|
440
|
+
entries,
|
|
441
|
+
route,
|
|
442
|
+
p.value,
|
|
443
|
+
visited,
|
|
444
|
+
includeOriginal,
|
|
445
|
+
);
|
|
357
446
|
}
|
|
358
447
|
}
|
|
359
448
|
};
|
|
360
449
|
|
|
361
450
|
const componentEntry = <T extends ComponentType>(
|
|
362
|
-
route: ITypedHttpRoute,
|
|
451
|
+
route: ITypedHttpRoute | ITypedMcpRoute,
|
|
363
452
|
kind: ComponentKind,
|
|
364
453
|
type: T,
|
|
365
454
|
): IComponentEntry => ({
|
|
366
455
|
kind,
|
|
367
456
|
route,
|
|
368
|
-
signature:
|
|
457
|
+
signature: "",
|
|
369
458
|
type,
|
|
370
459
|
});
|
|
371
460
|
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
461
|
+
/**
|
|
462
|
+
* Refines a finite component graph until no semantic equivalence class splits.
|
|
463
|
+
* Component edges carry class numbers, so shared children are never expanded as
|
|
464
|
+
* trees. Ordinary payloads retain separate object/array representations. Each
|
|
465
|
+
* round preserves the previous partition and can only split its classes; at
|
|
466
|
+
* most the number of distinct components rounds are necessary.
|
|
467
|
+
*/
|
|
468
|
+
const componentSignatures = (
|
|
469
|
+
entries: IComponentEntry[],
|
|
470
|
+
): Map<ComponentType, string> => {
|
|
471
|
+
const kinds = new Map<ComponentType, ComponentKind>();
|
|
472
|
+
for (const entry of entries) kinds.set(entry.type, entry.kind);
|
|
473
|
+
const nodes = [...kinds.keys()];
|
|
474
|
+
let colors = new Map(nodes.map((node) => [node, 0]));
|
|
475
|
+
let classes = nodes.length ? 1 : 0;
|
|
476
|
+
while (nodes.length) {
|
|
477
|
+
const intern = new Map<string, number>();
|
|
478
|
+
const next = new Map<ComponentType, number>();
|
|
479
|
+
for (const node of nodes) {
|
|
480
|
+
const ancestors = new WeakMap<object, number>();
|
|
481
|
+
let depth = 0;
|
|
482
|
+
const encode = (value: unknown, root = false): unknown => {
|
|
483
|
+
if (value === null || typeof value !== "object") return value;
|
|
484
|
+
if (!root && kinds.has(value as ComponentType))
|
|
485
|
+
return ["component", colors.get(value as ComponentType)];
|
|
486
|
+
const position = ancestors.get(value);
|
|
487
|
+
if (position !== undefined) return ["payload-cycle", position];
|
|
488
|
+
ancestors.set(value, depth++);
|
|
489
|
+
const result = Array.isArray(value)
|
|
490
|
+
? ["array", value.map((child) => encode(child))]
|
|
491
|
+
: [
|
|
492
|
+
"object",
|
|
493
|
+
Object.entries(value)
|
|
494
|
+
.filter(
|
|
495
|
+
([key, child]) =>
|
|
496
|
+
child !== undefined && !(root && key === "index"),
|
|
497
|
+
)
|
|
498
|
+
.map(([key, child]) => [key, encode(child)]),
|
|
499
|
+
];
|
|
500
|
+
ancestors.delete(value);
|
|
501
|
+
--depth;
|
|
502
|
+
return result;
|
|
503
|
+
};
|
|
504
|
+
const signature = JSON.stringify([
|
|
505
|
+
colors.get(node),
|
|
506
|
+
kinds.get(node),
|
|
507
|
+
encode(node, true),
|
|
508
|
+
]);
|
|
509
|
+
let color = intern.get(signature);
|
|
510
|
+
if (color === undefined) {
|
|
511
|
+
color = intern.size;
|
|
512
|
+
intern.set(signature, color);
|
|
513
|
+
}
|
|
514
|
+
next.set(node, color);
|
|
515
|
+
}
|
|
516
|
+
colors = next;
|
|
517
|
+
if (intern.size === classes) break;
|
|
518
|
+
classes = intern.size;
|
|
519
|
+
}
|
|
520
|
+
return new Map(nodes.map((node) => [node, String(colors.get(node))]));
|
|
521
|
+
};
|
|
380
522
|
|
|
381
523
|
const normalizeComponentNamespace = (name: string): string => {
|
|
382
524
|
const next: string = name.replace(/[^A-Za-z0-9_$]/g, "_");
|
|
@@ -384,63 +526,9 @@ const normalizeComponentNamespace = (name: string): string => {
|
|
|
384
526
|
};
|
|
385
527
|
|
|
386
528
|
const escapeComponentName = (used: Set<string>, name: string): string =>
|
|
387
|
-
used.has(name)
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
metadata: MetadataSchema,
|
|
391
|
-
visited: WeakSet<MetadataSchema> = new WeakSet(),
|
|
392
|
-
): void => {
|
|
393
|
-
if (visited.has(metadata)) return;
|
|
394
|
-
visited.add(metadata);
|
|
395
|
-
(metadata as unknown as { name_?: string }).name_ = undefined;
|
|
396
|
-
|
|
397
|
-
if (metadata.rest !== null) clearMetadataNameCache(metadata.rest, visited);
|
|
398
|
-
if (metadata.escaped !== null) {
|
|
399
|
-
clearMetadataNameCache(metadata.escaped.original, visited);
|
|
400
|
-
clearMetadataNameCache(metadata.escaped.returns, visited);
|
|
401
|
-
}
|
|
402
|
-
for (const func of metadata.functions) {
|
|
403
|
-
for (const p of func.parameters) clearMetadataNameCache(p.type, visited);
|
|
404
|
-
clearMetadataNameCache(func.output, visited);
|
|
405
|
-
}
|
|
406
|
-
for (const set of metadata.sets) {
|
|
407
|
-
(set as unknown as { name_?: string }).name_ = undefined;
|
|
408
|
-
clearMetadataNameCache(set.value, visited);
|
|
409
|
-
}
|
|
410
|
-
for (const map of metadata.maps) {
|
|
411
|
-
(map as unknown as { name_?: string }).name_ = undefined;
|
|
412
|
-
clearMetadataNameCache(map.key, visited);
|
|
413
|
-
clearMetadataNameCache(map.value, visited);
|
|
414
|
-
}
|
|
415
|
-
for (const array of metadata.arrays) {
|
|
416
|
-
(array as unknown as { name_?: string }).name_ = undefined;
|
|
417
|
-
clearMetadataNameCache(
|
|
418
|
-
(array.type as MetadataArrayType as MetadataArrayType).value,
|
|
419
|
-
visited,
|
|
420
|
-
);
|
|
421
|
-
}
|
|
422
|
-
for (const tuple of metadata.tuples) {
|
|
423
|
-
(tuple as unknown as { name_?: string }).name_ = undefined;
|
|
424
|
-
for (const elem of (tuple.type as MetadataTupleType as MetadataTupleType)
|
|
425
|
-
.elements)
|
|
426
|
-
clearMetadataNameCache(elem, visited);
|
|
427
|
-
}
|
|
428
|
-
for (const alias of metadata.aliases) {
|
|
429
|
-
(alias as unknown as { name_?: string }).name_ = undefined;
|
|
430
|
-
clearMetadataNameCache(
|
|
431
|
-
(alias.type as MetadataAliasType as MetadataAliasType).value,
|
|
432
|
-
visited,
|
|
433
|
-
);
|
|
434
|
-
}
|
|
435
|
-
for (const obj of metadata.objects) {
|
|
436
|
-
(obj as unknown as { name_?: string }).name_ = undefined;
|
|
437
|
-
for (const p of (obj.type as MetadataObjectType as MetadataObjectType)
|
|
438
|
-
.properties) {
|
|
439
|
-
clearMetadataNameCache(p.key, visited);
|
|
440
|
-
clearMetadataNameCache(p.value, visited);
|
|
441
|
-
}
|
|
442
|
-
}
|
|
443
|
-
};
|
|
529
|
+
used.has(StringUtil.accessorsOf(name).join("."))
|
|
530
|
+
? escapeComponentName(used, `_${name}`)
|
|
531
|
+
: name;
|
|
444
532
|
|
|
445
533
|
interface ICollectVisited {
|
|
446
534
|
aliases: WeakSet<MetadataAliasType>;
|
|
@@ -458,27 +546,6 @@ const createCollectVisited = (): ICollectVisited => ({
|
|
|
458
546
|
tuples: new WeakSet<MetadataTupleType>(),
|
|
459
547
|
});
|
|
460
548
|
|
|
461
|
-
const uniqueComponents = <T extends { name: string }>(input: T[]): T[] => {
|
|
462
|
-
const dict: Record<string, T> = {};
|
|
463
|
-
for (const elem of input) {
|
|
464
|
-
const oldbie: T | undefined = dict[elem.name];
|
|
465
|
-
if (oldbie === undefined) dict[elem.name] = elem;
|
|
466
|
-
else if (
|
|
467
|
-
elem.name.includes(".") ||
|
|
468
|
-
componentScore(oldbie) < componentScore(elem)
|
|
469
|
-
)
|
|
470
|
-
dict[elem.name] = elem;
|
|
471
|
-
}
|
|
472
|
-
return Object.values(dict);
|
|
473
|
-
};
|
|
474
|
-
|
|
475
|
-
const componentScore = (input: unknown): number =>
|
|
476
|
-
JSON.stringify(input, (key, value) =>
|
|
477
|
-
// Resolved-reference back-edges close cycles on recursive schemas;
|
|
478
|
-
// skip them when scoring component "richness".
|
|
479
|
-
key === "type" ? undefined : value,
|
|
480
|
-
).length;
|
|
481
|
-
|
|
482
549
|
const enrollMetadata = (
|
|
483
550
|
dictionary: IMetadataDictionary,
|
|
484
551
|
metadata: MetadataSchema,
|
|
@@ -490,9 +557,11 @@ const enrollMetadata = (
|
|
|
490
557
|
if (metadata.rest !== null)
|
|
491
558
|
enrollMetadata(dictionary, metadata.rest, visited);
|
|
492
559
|
if (metadata.escaped !== null) {
|
|
493
|
-
enrollMetadata(dictionary, metadata.escaped.original, visited);
|
|
494
560
|
enrollMetadata(dictionary, metadata.escaped.returns, visited);
|
|
495
561
|
}
|
|
562
|
+
for (const template of metadata.templates)
|
|
563
|
+
for (const elem of template.row ?? template)
|
|
564
|
+
enrollMetadata(dictionary, elem, visited);
|
|
496
565
|
for (const func of metadata.functions) {
|
|
497
566
|
for (const p of func.parameters)
|
|
498
567
|
enrollMetadata(dictionary, p.type, visited);
|
|
@@ -542,17 +611,13 @@ const enroll = <
|
|
|
542
611
|
dict: Map<string, T>,
|
|
543
612
|
elem: T,
|
|
544
613
|
): boolean => {
|
|
614
|
+
// Collision refinement established equivalence for every remaining same-name
|
|
615
|
+
// entry in this kind; selecting another representative cannot add meaning.
|
|
545
616
|
const oldbie: T | undefined = dict.get(elem.name);
|
|
546
617
|
if (oldbie === elem) return false;
|
|
547
618
|
if (oldbie === undefined) {
|
|
548
619
|
dict.set(elem.name, elem);
|
|
549
620
|
return true;
|
|
550
|
-
} else if (
|
|
551
|
-
elem.name.includes(".") ||
|
|
552
|
-
componentScore(oldbie) < componentScore(elem)
|
|
553
|
-
) {
|
|
554
|
-
dict.set(elem.name, elem);
|
|
555
|
-
return true;
|
|
556
621
|
}
|
|
557
622
|
return false;
|
|
558
623
|
};
|