自定义路由场景下Swagger Auto Gen无法识别路由问题求助
自定义Express路由无法被Swagger Auto Gen识别生成API文档
问题描述
我正尝试为自定义Express路由生成基础API文档,该路由并非router.get这类常规Express路由写法,而是通过递归加载目录文件的方式注册路由。目前遇到的问题是Swagger Auto Gen无法识别任何路由,无法生成对应文档。
相关代码示例
路由加载代码
const express = require('express') const fs = require('fs') const path = require('path') const isAuthenticated = require('../../middlewares/authMiddleware') const isAdmin = require('../../middlewares/isAdmin') const { hasPermission } = require('../../controllers/permissions') const router = express.Router() /** * The function recursively loads routes from a directory and adds them to a router object. * @param directory - The directory path where the routes are located. * @param [currentPath] - The current path is a string representing the current directory path being * traversed by the function. It is used to construct the endpoint URL for each route based on the * directory structure. If not provided, it defaults to an empty string. */ function loadRoutes(directory, currentPath = '') { fs.readdirSync(directory, { withFileTypes: true }).forEach((dirent) => { const fullPath = path.join(directory, dirent.name) if (dirent.isDirectory()) { loadRoutes(fullPath, path.join(currentPath, dirent.name)) } else if (dirent.isFile() && !(currentPath === '' && dirent.name === 'index.js')) { const route = require(fullPath) console.log(`Loading route: ${route.metadata.method} ${path.join(currentPath, path.parse(dirent.name).name)}`) const endpoint = route.metadata.url || path.join(currentPath, path.parse(dirent.name).name) const middlewares = route.metadata?.middlewares || [] if (route.metadata.requiresAuth) { if (router[route.metadata.method.toLowerCase()]) { router[route.metadata.method.toLowerCase()](endpoint, isAuthenticated, ...middlewares, route.handler) } } else if (route.metadata.requiresPermission && route.metadata.requiresAuth) { if (hasPermission(route.metadata.permissions)) { if (router[route.metadata.method.toLowerCase()]) { router[route.metadata.method.toLowerCase()](endpoint, isAuthenticated, isAdmin, ...middlewares, route.handler) } } } else { if (router[route.metadata.method.toLowerCase()]) { router[route.metadata.method.toLowerCase()](endpoint, ...middlewares, route.handler) } } } }) } loadRoutes(__dirname) module.exports = router
示例路由
const { PERMISSIONS_MAP } = require('../../../controllers/permissions') const responseHandler = require('../../../modules/responseHandler') const database = require('../../../config/database') const { Products, } = database.models module.exports = { metadata: { method: 'GET', url: '/products/get', version: '1.0.0', requiresAuth: false, permissions: [], requiresPermission: false, middlewares: [] }, handler: async (req, res, next) => { responseHandler(req, res, 200, { products: [] }, null, 'Products retrieved successfully') } }
Swagger生成脚本
const swaggerAutogen = require('swagger-autogen')() const doc = { info: { version: "1.0.0", title: "My API", description: "Documentation automatically generated by the <b>swagger-autogen</b> module." }, host: "localhost:3000", basePath: "/", schemes: ['http', 'https'], consumes: ['application/json'], produces: ['application/json'], tags: [ { "name": "User", "description": "Endpoints" } ], securityDefinitions: { apiKeyAuth: { type: "apiKey", in: "header", // can be "header", "query" or "cookie" name: "X-API-KEY", // name of the header, query parameter or cookie description: "any description..." } }, definitions: { Parents: { father: "Simon Doe", mother: "Marie Doe" }, User: { name: "Jhon Doe", age: 29, parents: { $ref: '#/definitions/Parents' }, diplomas: [ { school: "XYZ University", year: 2020, completed: true, internship: { hours: 290, location: "XYZ Company" } } ] }, AddUser: { $name: "Jhon Doe", $age: 29, about: "" } } } const outputFile = './swagger-output.json' const endpointsFiles = ['./src/routes/v1/index.js'] swaggerAutogen(outputFile, endpointsFiles, doc).then(() => { require('./app.js') // Your project's root file })
内容的提问来源于stack exchange,提问作者Omar Fakhoury
相关产品推荐
相关产品推荐

