UNPKG

@vulcan-sql/build

Version:

VulcanSQL package for building projects

221 lines 8.16 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.OAS3SpecGenerator = void 0; const tslib_1 = require("tslib"); const specGenerator_1 = require("../../../../models/extensions/specGenerator"); const core_1 = require("@vulcan-sql/core"); const lodash_1 = require("lodash"); let OAS3SpecGenerator = class OAS3SpecGenerator extends specGenerator_1.SpecGenerator { constructor() { super(...arguments); // Follow the OpenAPI specification version 3.0.3 // see https://github.com/OAI/OpenAPI-Specification/blob/main/versions/3.0.3.md this.oaiVersion = '3.0.3'; } getSpec(schemas) { const spec = { openapi: this.getOAIVersion(), info: this.getInfo(), paths: this.getPaths(schemas), }; return spec; } getOAIVersion() { return this.oaiVersion; } getInfo() { return { title: this.getName(), version: this.getVersion(), description: this.getDescription(), }; } getPaths(schemas) { const paths = {}; for (const schema of schemas) { paths[this.convertToOASPath(schema.urlPath)] = this.getPath(schema); } return paths; } getPath(schema) { return { get: this.getOperationObject(schema, 'get'), }; } // "/user/:id" -> "/user/{id}" convertToOASPath(path) { return path.replace(/:([^/]+)/g, (_, param) => { return `{${param}}`; }); } getOperationObject(schema, operation) { return { operationId: `${operation}${schema.urlPath}`, summary: schema.urlPath, description: schema.description, responses: this.getResponsesObject(schema), parameters: this.getParameterObject(schema), }; } getParameterObject(schema) { const parameters = []; const requests = schema.request || []; for (const param of requests) { parameters.push({ name: param.fieldName, in: this.convertFieldInTypeToOASIn(param.fieldIn), schema: this.getSchemaObjectFromParameter(param), required: this.isParameterRequired(param), description: param.description, }); } return parameters; } convertFieldInTypeToOASIn(fieldInType) { switch (fieldInType) { case core_1.FieldInType.HEADER: return 'header'; case core_1.FieldInType.PATH: return 'path'; case core_1.FieldInType.QUERY: return 'query'; default: throw new core_1.ConfigurationError(`FieldInType ${fieldInType} is not supported`); } } getSchemaObjectFromParameter(parameter) { const schema = { type: this.convertFieldDataTypeToOASType(parameter.type), }; for (const constraint of parameter.constraints) { if (constraint instanceof core_1.MinValueConstraint) { schema.minimum = constraint.getMinValue(); schema.exclusiveMinimum = constraint.isExclusive(); } else if (constraint instanceof core_1.MaxValueConstraint) { schema.maximum = constraint.getMaxValue(); schema.exclusiveMaximum = constraint.isExclusive(); } else if (constraint instanceof core_1.MinLengthConstraint) { schema.minLength = constraint.getMinLength(); } else if (constraint instanceof core_1.MaxLengthConstraint) { schema.maxLength = constraint.getMaxLength(); } else if (constraint instanceof core_1.RegexConstraint) { schema.pattern = constraint.getRegex(); } else if (constraint instanceof core_1.EnumConstraint) { schema.enum = constraint.getList(); } else if (constraint instanceof core_1.TypeConstraint) { schema.type = constraint.getType(); } } return schema; } convertFieldDataTypeToOASType(fieldDataType) { switch (fieldDataType) { case core_1.FieldDataType.BOOLEAN: return 'boolean'; case core_1.FieldDataType.NUMBER: return 'number'; case core_1.FieldDataType.STRING: return 'string'; default: throw new core_1.ConfigurationError(`FieldDataType ${fieldDataType} is not supported`); } } isParameterRequired(parameter) { return parameter.constraints.some((constraint) => constraint instanceof core_1.RequiredConstraint); } getResponsesObject(schema) { const clientError = { description: 'Client error', content: { 'application/json': { schema: { type: 'object', properties: { code: { type: 'string' }, message: { type: 'string' }, }, }, examples: this.getErrorCodes(schema.errors || []), }, }, }; return { '200': { description: 'The default response', content: { 'application/json': { schema: this.getSchemaObjectFroResponseProperties(schema.response || []), }, 'text/csv': { schema: { type: 'string', }, }, }, }, '400': (0, lodash_1.isEmpty)(clientError.content['application/json'].examples) ? undefined : clientError, '5XX': { description: 'Server error', }, }; } getSchemaObjectFroResponseProperties(responseProperties) { const required = responseProperties .filter((property) => property.required) .map((property) => property.name); const properties = {}; for (const property of responseProperties) { properties[property.name] = this.getSchemaObjectFroResponseProperty(property); } return { type: 'object', properties, required: required.length === 0 ? undefined : required, }; } getSchemaObjectFroResponseProperty(responseProperty) { const basicContent = { description: responseProperty.description, }; if (responseProperty.type === core_1.FieldDataType.BOOLEAN) { return Object.assign(Object.assign({}, basicContent), { type: 'boolean' }); } else if (responseProperty.type === core_1.FieldDataType.STRING) { return Object.assign(Object.assign({}, basicContent), { type: 'string' }); } else if (responseProperty.type === core_1.FieldDataType.NUMBER) { return Object.assign(Object.assign({}, basicContent), { type: 'number' }); } else { return Object.assign(Object.assign({}, basicContent), this.getSchemaObjectFroResponseProperties(responseProperty.type || [])); } } getErrorCodes(errorInfos) { const examples = {}; for (const errorInfo of errorInfos) { examples[errorInfo.code] = { description: errorInfo.message, value: { code: errorInfo.code, message: errorInfo.message, }, }; } return examples; } }; OAS3SpecGenerator = tslib_1.__decorate([ (0, core_1.VulcanInternalExtension)(), (0, core_1.VulcanExtensionId)(core_1.DocumentSpec.oas3) ], OAS3SpecGenerator); exports.OAS3SpecGenerator = OAS3SpecGenerator; //# sourceMappingURL=oas3SpecGenerator.js.map