swagger-typescript-api 生成ts类型 生成api文件

2,114 阅读1分钟

安装swagger-typescript-api

npm install -g swagger-typescript-api

1. 生成ts类型

1.新建swagger.json, 复制一段api-json 打开swaager文档地址,F12,有一个api-docs,复制response到json文件中。或者使用url

2.新建myApi.ts文件,为空。

3.执行命令

npx swagger-typescript-api -p ./swagger.json -o ./src -n myApi.ts

// ./swagger.json(执行时报错,换成绝对路径),这里也可直接替换成api-docs的url
npx swagger-typescript-api -p http://XXXXXX/api-docs -o ./src -n myApi.ts

4.查看myApi.ts文件

image.png

2.默认模板,生成ts类型和api文件

npx swagger-typescript-api -p http://XXXXXX/api-docs -o ./src/api --axios --modular --module-name-index 1 --single-http-client

查看/src/api/中生成多个文件

data-contracts.ts 文件是ts类型,内容同上面myApi.ts文件。

其余是以swagger中各模块生成的api文件

/* eslint-disable */
/* tslint:disable */
/*
 * ---------------------------------------------------------------
 * ## THIS FILE WAS GENERATED VIA SWAGGER-TYPESCRIPT-API        ##
 * ##                                                           ##
 * ## AUTHOR: acacode                                           ##
 * ## SOURCE: https://github.com/acacode/swagger-typescript-api ##
 * ---------------------------------------------------------------
 */

import { ResponseEntity } from "./data-contracts";
import { HttpClient, RequestParams } from "./http-client";

export class Download<SecurityDataType = unknown> {
  http: HttpClient<SecurityDataType>;

  constructor(http: HttpClient<SecurityDataType>) {
    this.http = http;
  }

  /**
   * No description
   *
   * @tags 文件服务
   * @name DownloadUsingGet
   * @summary 文件下载
   * @request GET:/file/download/{id}
   */
  downloadUsingGet = (id: number, params: RequestParams = {}) =>
    this.http.request<ResponseEntity, void>({
      path: `/file/download/${id}`,
      method: "GET",
      ...params,
    });
}

3.自定义api文件模板,适用自己项目

  1. 新建文件夹 swaggerTemplate,自定义模板文件。(默认模板路径是D:\workspace\projectname\node_modules\swagger-typescript-api\templates\default)

新建文件/swaggerTemplate/api.ejs

<%
const { utils, route, config, modelTypes } = it;
const { _, pascalCase, require } = utils;
const apiClassName = pascalCase(route.moduleName);
const routes = route.routes;
const dataContracts = _.map(modelTypes, "name");
%>

<% if (dataContracts.length) { %>
import { <%~ dataContracts.join(", ") %> } from "./<%~ config.fileNames.dataContracts %>"
<% } %>

import { HttpClient, RequestParams, ContentType, HttpResponse } from "./<%~ config.fileNames.httpClient %>";

import { request, RequestConfig } from "./request";

class <%= apiClassName %>Service{
    <% for (const route of routes) { %>
        <%~ includeFile('./procedure-call.ejs', { ...it, route }) %>
    <% } %>
}

export default <%= apiClassName %>Service;

  1. 新建/swaggerTemplate/procedure-call.ejs
<%
const { utils, route, config } = it;
const { requestBodyInfo, responseBodyInfo, specificArgNameResolver } = route;
const { _, getInlineParseContent, getParseContent, parseSchema, getComponentByRef, require } = utils;
const { parameters, path, method, payload, query, formData, security, requestParams } = route.request;
const { type, errorType, contentTypes } = route.response;
const { HTTP_CLIENT, RESERVED_REQ_PARAMS_ARG_NAMES } = config.constants;
const routeDocs = includeFile("@base/route-docs", { config, route, utils });
const queryName = (query && query.name) || "query";
const pathParams = _.values(parameters);
const pathParamsNames = _.map(pathParams, "name");

const isFetchTemplate = config.httpClientType === HTTP_CLIENT.FETCH;

const requestConfigParam = {
    name: specificArgNameResolver.resolve(RESERVED_REQ_PARAMS_ARG_NAMES),
    optional: true,
    type: "RequestParams",
    defaultValue: "{}",
}

const argToTmpl = ({ name, optional, type, defaultValue }) => `${name}${!defaultValue && optional ? '?' : ''}: ${type}${defaultValue ? ` = ${defaultValue}` : ''}`;

const rawWrapperArgs = config.extractRequestParams ?
    _.compact([
        requestParams && {
          name: pathParams.length ? `{ ${_.join(pathParamsNames, ", ")}, ...${queryName} }` : queryName,
          optional: false,
          type: getInlineParseContent(requestParams),
        },
        ...(!requestParams ? pathParams : []),
        payload,
        requestConfigParam,
    ]) :
    _.compact([
        ...pathParams,
        query,
        payload,
        requestConfigParam,
    ])

const wrapperArgs = _
    // Sort by optionality
    .sortBy(rawWrapperArgs, [o => o.optional])
    .map(argToTmpl)
    .join(', ')

// RequestParams["type"]
const requestContentKind = {
    "JSON": "ContentType.Json",
    "URL_ENCODED": "ContentType.UrlEncoded",
    "FORM_DATA": "ContentType.FormData",
    "TEXT": "ContentType.Text",
}
// RequestParams["format"]
const responseContentKind = {
    "JSON": '"json"',
    "IMAGE": '"blob"',
    "FORM_DATA": isFetchTemplate ? '"formData"' : '"document"'
}

const bodyTmpl = _.get(payload, "name") || null;
const queryTmpl = (query != null && queryName) || null;
const bodyContentKindTmpl = requestContentKind[requestBodyInfo.contentKind] || null;
const responseFormatTmpl = responseContentKind[responseBodyInfo.success && responseBodyInfo.success.schema && responseBodyInfo.success.schema.contentKind] || null;
const securityTmpl = security ? 'true' : null;

const describeReturnType = () => {
    if (!config.toJS) return "";

    switch(config.httpClientType) {
        case HTTP_CLIENT.AXIOS: {
          return `Promise<AxiosResponse<${type}>>`
        }
        default: {
          return `Promise<HttpResponse<${type}, ${errorType}>`
        }
    }
}

%>
/**
<%~ routeDocs.description %>

 *<% /* Here you can add some other JSDoc tags */ %>

<%~ routeDocs.lines %>

 */
export const <%~ route.routeName.usage %> = (<%~ wrapperArgs %>)<%~ config.toJS ? `: ${describeReturnType()}` : "" %> =>
    <%~ config.singleHttpClient ? 'this.http.request' : 'http' %>.<%~ _.lowerCase(method) %><<%~ type %>, <%~ errorType %>>(`<%~ path %>`,{
       'data' : { 
            <%~ bodyTmpl ? `data: ${bodyTmpl},` : '' %>
            ...<%~ _.get(requestConfigParam, "name") %>
        }
    })

3.新建文件generateApi.js,与swaggerTemplate同级

const { generateApi } = require("swagger-typescript-api");
// import { generateApi } from "swagger-typescript-api";
const path = require("path");

generateApi({
  output: path.resolve(process.cwd(), "./src/services"),
  url: "http://XXXXXXXX/api-docs",
  httpClientType: false,
  modular: true,
  templates: path.resolve(process.cwd(), "./src/swaggerTemplate"),
  hooks: {
    onCreateRoute: (routeData) => {
      // console.log('@@@@@@@@@@@@@@@@@@@@@@@@@', routeData);
      //增加接口请求前缀
      routeData.request.path = `/api${routeData.request.path}`;
    },
    onFormatRouteName: (routeInfo, templateRouteName) => {
      //自定义路由名称
      return templateRouteName.replace(/Using\w*/, "").replace(/[{}]/, "");
    },
  },
});

4.power shell中 执行命令

node generateApi.js

4. 补充

yApi 也可以导出swagger.json数据。

最为简单的mock数据方式,yapi中接口编辑功能支持配置mock类型,可mock数据,mock语法参考mock.js (mockjs.com/examples.ht…)

image.png

参考链接:

juejin.cn/post/729534… juejin.cn/post/728704… blog.csdn.net/qq_34527715… blog.csdn.net/m0_63986895… article.juejin.cn/post/723954…