UNPKG

@micro.ts/core

Version:

Microservice framework with Typescript

192 lines (191 loc) 7.52 kB
"use strict"; var __importDefault = (this && this.__importDefault) || function (mod) { return (mod && mod.__esModule) ? mod : { "default": mod }; }; Object.defineProperty(exports, "__esModule", { value: true }); exports.getObjectSchema = exports.getAppSchema = exports.schemas = exports.getServerObject = exports.getServerInfo = void 0; const joi_to_swagger_1 = __importDefault(require("joi-to-swagger")); const joi_typescript_validator_1 = require("joi-typescript-validator"); const decorators_1 = require("../decorators"); const GlobalMetadata_1 = require("../decorators/GlobalMetadata"); function getServerInfo(title, version, description) { return { title, version, description }; } exports.getServerInfo = getServerInfo; function getServerObject(host, port, protocol = 'http', description = '') { return { url: '{protocol}://{host}:{port}', description, variables: { host: { default: host }, port: { default: port.toString() }, protocol: { default: protocol }, }, }; } exports.getServerObject = getServerObject; exports.schemas = new Map(); const controllers = (0, GlobalMetadata_1.getGlobalMetadata)(); function buildControllerSchema(metadata) { const methodSchemas = {}; if (metadata.handlers) { Object.keys(metadata.handlers).forEach((key) => { var _a; const obj = buildHandlerSchema('', ((_a = metadata.options) === null || _a === void 0 ? void 0 : _a.path) || '', metadata.ctor, metadata.handlers[key]); methodSchemas[obj.path] = methodSchemas[obj.path] || {}; const newObj = Object.assign({}, obj); delete newObj.path; Object.assign(methodSchemas[obj.path], newObj); }); } return methodSchemas; } function extractPath(def) { let basePart = def.base; if (basePart && basePart.indexOf('/') !== 0) { basePart = `/${basePart}`; } let controllerPart = def.controller; if (controllerPart.indexOf('/') !== 0) { controllerPart = `/${controllerPart}`; } let handlerPart = def.handler; const params = extractParamNames(handlerPart); handlerPart = params .map((x) => { if (x.param) { return `{${x.name}}`; } return x.name; }) .join('/'); if (handlerPart.indexOf('/') !== 0 && handlerPart.length > 0) { handlerPart = `/${handlerPart}`; } return `${basePart}${controllerPart}${handlerPart}`.replace(/\/\//g, '/'); } function extractParamNames(path, separator = '/') { const spl = path.split(separator); return spl.map((x) => { const value = { name: x, param: false }; if (x.length > 0 && x[0] === ':') { value.name = x.substr(1); value.param = true; } return value; }); } function buildHandlerSchema(basePath, controllerPath, ctor, description) { var _a, _b, _c; const routeDefinition = { base: basePath, controller: controllerPath, controllerCtor: ctor, handler: ((_a = description.metadata) === null || _a === void 0 ? void 0 : _a.path) || '', handlerName: description.name || '', method: ((_b = description.metadata) === null || _b === void 0 ? void 0 : _b.method) || 'get', queueOptions: description.metadata.queueOptions, json: true, timeout: 0, }; return { path: extractPath(routeDefinition), [((_c = description.metadata) === null || _c === void 0 ? void 0 : _c.method) || 'get']: buildMethodParameters(description, ctor.name), }; } function buildMethodParameters(method, controller) { const obj = { responses: { '200': { description: '' } }, }; obj.tags = [controller]; method.params.forEach((param) => { var _a, _b, _c, _d; if ((_a = param.options) === null || _a === void 0 ? void 0 : _a.decoratorType) { // BODY if (param.options.decoratorType === decorators_1.ParamDecoratorType.Body) { obj.requestBody = { content: { 'application/json': { schema: getObjectSchema(param.type) }, }, required: !!((_b = param.options.bodyOptions) === null || _b === void 0 ? void 0 : _b.required), }; } // BODY FIELD // PATH PARAM if (param.options.decoratorType === decorators_1.ParamDecoratorType.ParamField) { obj.parameters = obj.parameters || []; const name = param.options.name; if (!obj.parameters.find((x) => x.name === name && x.id === 'path')) { obj.parameters.push({ name, in: 'path', required: true, schema: { type: param.type.name.toLowerCase(), }, }); } } // FULL PARAMS OBJECT // QUERY PARAM if (param.options.decoratorType === decorators_1.ParamDecoratorType.QueryField) { obj.parameters = obj.parameters || []; const name = param.options.name; if (!obj.parameters.find((x) => x.name === name && x.in === 'query')) { obj.parameters.push({ name, in: 'query', required: !!((_c = param.options.queryParamOptions) === null || _c === void 0 ? void 0 : _c.required), schema: { type: param.type.name.toLowerCase(), }, }); } } // FULL QUERY OBJECT // HEADER PARAM if (param.options.decoratorType === decorators_1.ParamDecoratorType.HeaderField) { obj.parameters = obj.parameters || []; const name = param.options.name; if (!obj.parameters.find((x) => x.name === name && x.in === 'header')) { obj.parameters.push({ name, in: 'header', required: !!((_d = param.options.queryParamOptions) === null || _d === void 0 ? void 0 : _d.required), schema: { type: param.type.name.toLowerCase(), }, }); } } // FULL HEADER OBJECT } }); return obj; } function getAppSchema() { const values = { paths: {}, info: getServerInfo('Test', 'Test', 'Test'), openapi: '3.0.0', servers: [ getServerObject('0.0.0.0', 8080, 'http', 'Public'), getServerObject('0.0.0.0', 8081, 'http', 'Private'), ], }; controllers.controllers.forEach((ct) => { const ctorSchema = buildControllerSchema(ct); Object.assign(values.paths, ctorSchema); }); return values; } exports.getAppSchema = getAppSchema; function getObjectSchema(obj) { if (!exports.schemas.has(obj)) { const joiSchema = (0, joi_typescript_validator_1.getSchema)(obj); const schema = (0, joi_to_swagger_1.default)(joiSchema); exports.schemas.set(obj, schema['swagger']); } return exports.schemas.get(obj); } exports.getObjectSchema = getObjectSchema;