UNPKG

manifest

Version:

The backend for AI code editors

376 lines (375 loc) 16.9 kB
"use strict"; var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) { var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d; if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc); else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r; return c > 3 && r && Object.defineProperty(target, key, r), r; }; var __metadata = (this && this.__metadata) || function (k, v) { if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v); }; Object.defineProperty(exports, "__esModule", { value: true }); exports.OpenApiCrudService = void 0; const common_1 = require("@nestjs/common"); const common_2 = require("../../../../common/src"); const constants_1 = require("../../constants"); const open_api_utils_service_1 = require("./open-api-utils.service"); let OpenApiCrudService = class OpenApiCrudService { constructor(openApiUtilsService) { this.openApiUtilsService = openApiUtilsService; } generateEntityPaths(entityManifests) { const paths = {}; entityManifests .filter((entityManifest) => !entityManifest.single) .forEach((entityManifest) => { paths[`/${constants_1.API_PATH}/${constants_1.COLLECTIONS_PATH}/${entityManifest.slug}`] = {}; paths[`/${constants_1.API_PATH}/${constants_1.COLLECTIONS_PATH}/${entityManifest.slug}/{id}`] = {}; paths[`/${constants_1.API_PATH}/${constants_1.COLLECTIONS_PATH}/${entityManifest.slug}/select-options`] = {}; if (this.isNotForbidden(entityManifest.policies.create)) { Object.assign(paths[`/${constants_1.API_PATH}/${constants_1.COLLECTIONS_PATH}/${entityManifest.slug}`], this.generateCreatePath(entityManifest)); } if (this.isNotForbidden(entityManifest.policies.read)) { Object.assign(paths[`/${constants_1.API_PATH}/${constants_1.COLLECTIONS_PATH}/${entityManifest.slug}`], this.generateListPath(entityManifest)); Object.assign(paths[`/${constants_1.API_PATH}/${constants_1.COLLECTIONS_PATH}/${entityManifest.slug}/{id}`], this.generateDetailPath(entityManifest)); Object.assign(paths[`/${constants_1.API_PATH}/${constants_1.COLLECTIONS_PATH}/${entityManifest.slug}/select-options`], this.generateListSelectOptionsPath(entityManifest)); } if (this.isNotForbidden(entityManifest.policies.update)) { Object.assign(paths[`/${constants_1.API_PATH}/${constants_1.COLLECTIONS_PATH}/${entityManifest.slug}/{id}`], this.generateUpdatePath(entityManifest), this.generatePatchPath(entityManifest)); } if (this.isNotForbidden(entityManifest.policies.delete)) { Object.assign(paths[`/${constants_1.API_PATH}/${constants_1.COLLECTIONS_PATH}/${entityManifest.slug}/{id}`], this.generateDeletePath(entityManifest)); } }); entityManifests .filter((entityManifest) => entityManifest.single) .forEach((entityManifest) => { if (this.isNotForbidden(entityManifest.policies.read)) { paths[`/${constants_1.API_PATH}/${constants_1.SINGLES_PATH}/${entityManifest.slug}`] = { ...this.generateDetailPath(entityManifest, true) }; } if (this.isNotForbidden(entityManifest.policies.update)) { paths[`/${constants_1.API_PATH}/${constants_1.SINGLES_PATH}/${entityManifest.slug}`] = { ...this.generateDetailPath(entityManifest, true), ...this.generatePatchPath(entityManifest, true) }; } }); return paths; } generateListPath(entityManifest) { return { get: { summary: `List ${entityManifest.namePlural}`, description: `Retrieves a paginated list of ${entityManifest.namePlural}. In addition to the general parameters below, each property of the ${entityManifest.nameSingular} can be used as a filter: https://manifest.build/docs/rest-api#filters`, tags: [(0, common_2.upperCaseFirstLetter)(entityManifest.namePlural)], security: this.openApiUtilsService.getSecurityRequirements(entityManifest.policies.read), parameters: [ { name: 'page', in: 'query', description: 'The page number', required: false, schema: { type: 'integer', default: 1 } }, { name: 'perPage', in: 'query', description: 'The number of items per page', required: false, schema: { type: 'integer', default: 10 } }, { name: 'orderBy', in: 'query', description: 'The field to order by', required: false, schema: { type: 'string' } }, { name: 'order', in: 'query', description: 'The order direction', required: false, schema: { type: 'string', enum: ['ASC', 'DESC'] } }, { name: 'relations', in: 'query', description: 'The relations to include. For several relations, use a comma-separated list', required: false, schema: { type: 'string' } } ], responses: { '200': { description: 'OK', content: { 'application/json': { schema: { $ref: '#/components/schemas/Paginator' } } } } } } }; } generateListSelectOptionsPath(entityManifest) { return { get: { summary: `List ${entityManifest.namePlural} for select options`, description: `Retrieves a list of ${entityManifest.namePlural} for select options. The response is an array of objects with the properties 'id' and 'label'. Used in the admin panel to fill select dropdowns.`, tags: [(0, common_2.upperCaseFirstLetter)(entityManifest.namePlural)], security: [ { Admin: [] } ], responses: { '200': { description: `List of ${entityManifest.namePlural} for select options`, content: { 'application/json': { schema: { type: 'array', items: { $ref: `#/components/schemas/SelectOption` } } } } } } } }; } generateCreatePath(entityManifest) { return { post: { summary: `Create a new ${entityManifest.nameSingular}`, description: `Creates a new ${entityManifest.nameSingular} passing the properties in the request body as JSON.`, tags: [(0, common_2.upperCaseFirstLetter)(entityManifest.namePlural)], requestBody: { content: { 'application/json': { schema: { type: 'object' } } } }, security: this.openApiUtilsService.getSecurityRequirements(entityManifest.policies.create), responses: { '201': { description: `OK` }, '400': { description: `Bad request` } } } }; } generateDetailPath(entityManifest, single) { return { get: { summary: `Get a single ${entityManifest.nameSingular}`, description: `Retrieves the details of a single ${entityManifest.nameSingular} by its ID.`, tags: [ (0, common_2.upperCaseFirstLetter)(entityManifest.namePlural || entityManifest.nameSingular) ], parameters: single ? [] : [ { name: 'id', in: 'path', description: `The ID of the ${entityManifest.nameSingular}`, required: true, schema: { type: 'string', format: 'uuid', example: '123e4567-e89b-12d3-a456-426614174000' } } ], security: this.openApiUtilsService.getSecurityRequirements(entityManifest.policies.read), responses: { '200': { description: `OK`, content: { 'application/json': { schema: { type: 'object' } } } }, '404': { description: `The ${entityManifest.nameSingular} was not found` } } } }; } generateUpdatePath(entityManifest, single) { return { put: { summary: `Update an existing ${entityManifest.nameSingular} (full replace)`, description: `Updates a single ${entityManifest.nameSingular} by its ID. The properties to update are passed in the request body as JSON. This operation fully replaces the entity and its relations. Leaving a property out will remove it.`, tags: [ (0, common_2.upperCaseFirstLetter)(entityManifest.namePlural || entityManifest.nameSingular) ], requestBody: { content: { 'application/json': { schema: { type: 'object' } } } }, parameters: single ? [] : [ { name: 'id', in: 'path', description: `The ID of the ${entityManifest.nameSingular}`, required: true, schema: { type: 'string', format: 'uuid', example: '123e4567-e89b-12d3-a456-426614174000' } } ], security: this.openApiUtilsService.getSecurityRequirements(entityManifest.policies.update), responses: { '200': { description: `OK`, content: { 'application/json': { schema: { type: 'object' } } } }, '404': { description: `Not found` } } } }; } generatePatchPath(entityManifest, single) { return { patch: { summary: `Update an existing ${entityManifest.nameSingular} (partial update)`, description: `Updates a single ${entityManifest.nameSingular} by its ID. The properties to update are passed in the request body as JSON. This operation partially updates the entity and its relations. Leaving a property out will not remove it.`, tags: [ (0, common_2.upperCaseFirstLetter)(entityManifest.namePlural || entityManifest.nameSingular) ], requestBody: { content: { 'application/json': { schema: { type: 'object' } } } }, parameters: single ? [] : [ { name: 'id', in: 'path', description: `The ID of the ${entityManifest.nameSingular}`, required: true, schema: { type: 'string', format: 'uuid', example: '123e4567-e89b-12d3-a456-426614174000' } } ], security: this.openApiUtilsService.getSecurityRequirements(entityManifest.policies.update), responses: { '200': { description: `OK`, content: { 'application/json': { schema: { type: 'object' } } } }, '404': { description: `Not found` } } } }; } generateDeletePath(entityManifest) { return { delete: { summary: `Delete an existing ${entityManifest.nameSingular}`, description: `Deletes a single ${entityManifest.nameSingular} by its ID.`, tags: [(0, common_2.upperCaseFirstLetter)(entityManifest.namePlural)], parameters: [ { name: 'id', in: 'path', description: `The ID of the ${entityManifest.nameSingular}`, required: true, schema: { type: 'string', format: 'uuid', example: '123e4567-e89b-12d3-a456-426614174000' } } ], security: this.openApiUtilsService.getSecurityRequirements(entityManifest.policies.delete), responses: { '200': { description: `OK` }, '404': { description: `The ${entityManifest.nameSingular} was not found` } } } }; } isNotForbidden(policies) { return policies.every((policy) => { return policy.access !== 'forbidden'; }); } }; exports.OpenApiCrudService = OpenApiCrudService; exports.OpenApiCrudService = OpenApiCrudService = __decorate([ (0, common_1.Injectable)(), __metadata("design:paramtypes", [open_api_utils_service_1.OpenApiUtilsService]) ], OpenApiCrudService);