最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

Multiple Swagger docs in an ASP.NET Core Web API project with different URLs - Stack Overflow

programmeradmin1浏览0评论

I have an ASP.NET Core 8 Web API . I want to have the API docs on a separate swagger page per controller. e.g. all endpoints under AmazonController should be served on ..../v1/swagger/amazon.html. Similarly, all endpoints under EBayController should be served on ...v1/swagger/ebay.html.

Currently, I am using NSwag to generate ApiClient per controller and services.AddOpenApiDocument to configure the OpenAPI docs. The issue is I can add register multiple AddOpenApiDocument in DI with different configurations e.g. using DocumentProcessers to filter out irrelevant endpoints by name in a document, but, the resulting swagger page remains the same. i.e. ...swagger/index.html.

Each document appears as a separate "definition" on the same ...swaggger/index.html page.

I want to keep each controller's docs on its own respective swagger docs page and have its own versioning. Cannot seem to find how to do it best. I am open to all suggestions.

I have an ASP.NET Core 8 Web API . I want to have the API docs on a separate swagger page per controller. e.g. all endpoints under AmazonController should be served on ..../v1/swagger/amazon.html. Similarly, all endpoints under EBayController should be served on ...v1/swagger/ebay.html.

Currently, I am using NSwag to generate ApiClient per controller and services.AddOpenApiDocument to configure the OpenAPI docs. The issue is I can add register multiple AddOpenApiDocument in DI with different configurations e.g. using DocumentProcessers to filter out irrelevant endpoints by name in a document, but, the resulting swagger page remains the same. i.e. ...swagger/index.html.

Each document appears as a separate "definition" on the same ...swaggger/index.html page.

I want to keep each controller's docs on its own respective swagger docs page and have its own versioning. Cannot seem to find how to do it best. I am open to all suggestions.

Share Improve this question edited Feb 7 at 14:46 marc_s 755k184 gold badges1.4k silver badges1.5k bronze badges asked Feb 7 at 14:42 JunaidJunaid 1,0302 gold badges20 silver badges44 bronze badges
Add a comment  | 

1 Answer 1

Reset to default 1

I want to have the API docs on a separate swagger page per controller. e.g. all endpoints under AmazonController should be served on ..../v1/swagger/amazon.html. Similarly, all endpoints under EBayController should be served on ...v1/swagger/ebay.html.

You could register multiple OpenAPI documents in the DI container, each with a filter to include only the relevant controller's endpoints and serve each document on a separate endpoint instead of listing them all on the same Swagger UI page.

Refer to the following sample:

  1. Configure NSwag to Generate Separate Documents

     builder.Services.AddControllers(); 
     // Register multiple OpenAPI documents  
     builder.Services.AddOpenApiDocument(config =>
     {
         config.DocumentName = "todo";
         config.Title = "todo API";
         config.ApiGroupNames = new[] { "todo" }; // Tag controllers with [ApiExplorerSettings(GroupName = "Amazon")]
         config.PostProcess = document =>
         {
             document.Info.Version = "v1";
             document.Info.Title = "todo API";
         };
     });
    
     builder.Services.AddOpenApiDocument(config =>
     {
         config.DocumentName = "values";
         config.Title = "values API";
         config.ApiGroupNames = new[] { "values" };
         config.PostProcess = document =>
         {
             document.Info.Version = "v1";
             document.Info.Title = "values API";
         };
     }); 
     var app = builder.Build();
     app.UseHttpsRedirection();
     app.UseOpenApi(settings =>
     {
         settings.Path = "/v1/swagger/{documentName}.json"; // Serves separate OpenAPI documents
     });
    
     app.UseSwaggerUi3(settings =>
     {
         settings.Path = "/v1/swagger/todo.html";
         settings.DocumentPath = "/v1/swagger/todo.json";
     });
    
     app.UseSwaggerUi3(settings =>
     {
         settings.Path = "/v1/swagger/values.html";
         settings.DocumentPath = "/v1/swagger/values.json";
     });
    
    
     app.UseRouting();
     app.UseAuthorization();
    
     app.MapControllers();
    
     app.Run();
    
  2. Tag Controllers with [ApiExplorerSettings]

     [Route("api/[controller]")]
     [ApiController]
     [ApiExplorerSettings(GroupName = "todo")]
     public class TodoController : ControllerBase
     {
         // GET: api/<TodoController>
         [HttpGet]
         public IEnumerable<string> Get()
         {
             return new string[] { "value1", "value2" };
         }
      ...
    
     [Route("api/[controller]")]
     [ApiController]
     [Authorize]
     [ApiExplorerSettings(GroupName = "values")]
     public class ValuesController : ControllerBase
     {
         // GET: api/<ValuesController>
         [HttpGet]
         public IEnumerable<string> Get()
         {
             return new string[] { "value1", "value2" };
         }
      ...
    

After running the application, the result as below:

Todo controller: https://localhost:7245/v1/swagger/todo.html → Todo API docs

Values controller: https://localhost:7245/v1/swagger/values.html → Todo API docs

And you can view the .json result use https://localhost:7245/v1/swagger/todo.json or https://localhost:7245/v1/swagger/values.json.

Update:

I want to have one more group that should show all the controllers including Amazon, EBay, todos, files, customers, etc. Basically, this one should be the default swagger docs page that gets rendered when I hit swagger/index.html and it should display all endpoints. Would it be necessary to apply the ApiExplorerSettings tag on all controllers and define a name for it?

You can add one more OpenAPI documents as below:

builder.Services.AddOpenApiDocument();
...
if (app.Environment.IsDevelopment())
{
    // Add OpenAPI 3.0 document serving middleware
    // Available at: http://localhost:<port>/swagger/v1/swagger.json
    app.UseOpenApi();

    // Add web UIs to interact with the document
    // Available at: http://localhost:<port>/swagger
    app.UseSwaggerUi3(); // UseSwaggerUI Protected by if (env.IsDevelopment())
}

The Program.cs file like this:

Then, you can display all endpoints in swagger index page(https://localhost:7245/swagger/index.html).

发布评论

评论列表(0)

  1. 暂无评论