[英]Add `host`, `basePath` and `schemes` to swagger.json using Swashbuckle Aspnetcore
I am using official doc step by step method to configure Swagger UI and generate Swagger JSON file in my ASP.NET core API application.我正在使用官方文档逐步方法来配置 Swagger UI 并在我的 ASP.NET 核心 API 应用程序中生成 Swagger JSON 文件。
Get started with Swashbuckle and ASP.NET Core 开始使用 Swashbuckle 和 ASP.NET Core
If I look at my generated swagger.json file - it is missing three important properties host
, basePath
and schemes
如果我查看生成的 swagger.json 文件——它缺少三个重要的属性
host
、 basePath
和schemes
Please help me understand what piece of code can I add so the swagger.json that gets generated will have following mentioned properties/values.请帮助我了解我可以添加哪些代码,以便生成的 swagger.json 将具有以下提到的属性/值。
Here is an ideal swagger.json - give attention to the host
, basePath
and schemes
values which are missing if I follow the documentation code in my application这是一个理想的 swagger.json - 注意
host
、 basePath
和schemes
值,如果我遵循我的应用程序中的文档代码,这些值会丢失
{
"swagger": "2.0",
"info": {
"version": "v1",
"title": "Demo API Title"
},
"host": "some-url-that-is-hosted-on-azure.azurewebsites.net",
"basePath": "/api",
"schemes": ["https"],
"paths": {
"/Account/Test": {
"post": {
"tags": [
"Admin"
],
"summary": "Account test method - POST",
"operationId": "AccountTest",
"consumes": [],
"produces": [
"text/plain",
"application/json",
"text/json"
],
"parameters": [],
"responses": {
"200": {
"description": "Success",
"schema": {
"type": "boolean"
}
}
}
}
}
},
"definitions": {
"NumberSearchResult": {
"type": "object",
"properties": {
"number": {
"type": "string"
},
"location": {
"type": "string"
}
}
}
},
"securityDefinitions": {
"Bearer": {
"name": "Authorization",
"in": "header",
"type": "apiKey",
"description": "Authorization. Example: \"Authorization: Bearer {token}\""
}
},
"security": [
{
"Bearer": []
}
]
}
There are some changes in latest version of Swashbuckle for .netcore最新版本的 Swashbuckle for .netcore 有一些变化
If you wish to change Request URL in Swashbuckle, maybe you are behind API gateway or have custom domain attached to your webapp.如果你想在 Swashbuckle 中更改请求 URL,也许你在 API 网关后面或者有自定义域附加到你的 webapp。 Do this.
做这个。
public class BasePathDocumentFilter: IDocumentFilter { public void Apply(OpenApiDocument swaggerDoc, DocumentFilterContext context) { swaggerDoc.Servers = new List<OpenApiServer>() { new OpenApiServer() { Url = "hxxt://yoursite" } }; } }
services.AddSwaggerGen()
method add document filter like this c.DocumentFilter<BasePathDocumentFilter>();
services.AddSwaggerGen()
方法中添加这样的文档过滤器c.DocumentFilter<BasePathDocumentFilter>();
Swagger / open api 3.0 and higher requires the server object. Swagger/open api 3.0 及更高版本需要服务器对象。 See: https://swagger.io/specification/#server-object
请参阅: https ://swagger.io/specification/#server-object
To set it in your startup like this像这样在您的启动中设置它
app.UseSwagger(c =>
{
c.PreSerializeFilters.Add((swagger, httpReq) =>
{
swagger.Servers = new List<OpenApiServer> { new OpenApiServer { Url = $"{httpReq.Scheme}://{httpReq.Host.Value}" } };
});
});
You can implement and register your own IDocumentFilter
and set the desired values there.您可以实施和注册您自己的
IDocumentFilter
并在那里设置所需的值。
public class MyDocumentFilter : IDocumentFilter
{
public void Apply(SwaggerDocument swaggerDoc, SchemaRegistry schemaRegistry, IApiExplorer apiExplorer)
{
swaggerDoc.Host = "some-url-that-is-hosted-on-azure.azurewebsites.net";
swaggerDoc.BasePath = "/api";
swaggerDoc.Schemes = new List<string> { "https" };
}
}
And then register it via然后通过注册
services.AddSwaggerGen(options =>
{
options.DocumentFilter<MyDocumentFilter>();
});
Edit (09SEP20) Here's some code snippets that applies to version 4.xx of the asp.netcore Swashbuckle library编辑 (09SEP20)以下是一些适用于 asp.netcore Swashbuckle 库 4.xx 版的代码片段
In future I might make another post in case the below is more straightforward with new versions (at time of writing it's at version 5.xx)将来我可能会发表另一篇文章,以防下面的新版本更直接(在撰写本文时是 5.xx 版)
sample appsettings.Development.json示例 appsettings.Development.json
{
"Logging": {
"LogLevel": {
"Default": "Warning",
"Microsoft.Hosting.*": "Information"
}
},
"Swagger": {
"ApiVersion": "localhost",
"ApiName": "v1",
"SwaggerRelativeUrl": "/swagger/v1/swagger.json",
"Title": "SalesforceLocationApi"
}
}
sample c# code示例 C# 代码
namespace My.Api.Settings
{
public class SwaggerSettings
{
public string? ApiName { get; set; }
public string? ApiVersion { get; set; }
public string? SwaggerRelativeUrl { get; set; }
public string? Title { get; set; }
}
}
using Microsoft.AspNetCore.Authentication;
using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Diagnostics;
using Microsoft.AspNetCore.Hosting;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Http.Extensions;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using Swashbuckle.AspNetCore.SwaggerGen;
using Swashbuckle.AspNetCore.SwaggerUI;
using System;
using System.Reflection;
namespace My.Api
{
public class Startup
{
private readonly IConfiguration _configuration;
public Startup(IConfiguration configuration)
{
_configuration = configuration;
}
public void ConfigureServices(IServiceCollection services)
{
services.AddControllers(ConfigureControllers);
services
.AddSingleton<IHttpContextAccessor, HttpContextAccessor>()
.AddSwaggerGen(SetupUpSwaggerGen);
}
public void Configure(IApplicationBuilder application, IWebHostEnvironment environment, ILoggerFactory loggerFactory, IMapper mapper)
{
if (environment.IsDevelopment())
{
application.UseDeveloperExceptionPage();
}
else
{
application.UseExceptionHandler();
}
application
.UseHttpsRedirection()
.UseSwagger()
.UseSwaggerUI(SetUpSwaggerUi)
.UseRouting()
.UseAuthorization()
.UseEndpoints(endpoints => endpoints.MapControllers());
}
#region Helpers
private void SetupUpSwaggerGen(SwaggerGenOptions options)
{
var swaggerSettings = _configuration.GetSection("Swagger").Get<SwaggerSettings>();
SwaggerConfig.SetUpSwaggerGen(options, swaggerSettings);
}
private void SetUpSwaggerUi(SwaggerUIOptions options)
{
var swaggerSettings = _configuration.GetSection("Swagger").Get<SwaggerSettings>();
SwaggerConfig.SetUpSwaggerUi(options, swaggerSettings.SwaggerRelativeUrl, swaggerSettings.ApiName);
}
#endregion
}
}
using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.OpenApi.Models;
using Swashbuckle.AspNetCore.SwaggerGen;
using Swashbuckle.AspNetCore.SwaggerUI;
using System;
using System.IO;
using System.Linq;
using System.Reflection;
namespace My.Api
{
public class SwaggerConfig
{
internal class SwaggerDocumentFilter : IDocumentFilter
{
private readonly string _swaggerDocHost;
public SwaggerDocumentFilter(IHttpContextAccessor httpContextAccessor)
{
var host = httpContextAccessor.HttpContext.Request.Host.Value;
var scheme = httpContextAccessor.HttpContext.Request.Scheme;
_swaggerDocHost = $"{scheme}://{host}";
}
public void Apply(OpenApiDocument swaggerDoc, DocumentFilterContext context)
{
swaggerDoc.Servers.Add(new OpenApiServer { Url = _swaggerDocHost });
}
}
internal static void SetUpSwaggerGen(SwaggerGenOptions options, SwaggerSettings swaggerSettings)
{
options.DocumentFilter<SwaggerDocumentFilter>();
options.SwaggerDoc(swaggerSettings.ApiName, new OpenApiInfo { Title = swaggerSettings.Title, Version = swaggerSettings.ApiVersion });
options.CustomSchemaIds(type => $"{type?.Namespace?.Split('.').Last()}.{type?.Name}"); //E.g. Acme.Dtos.Gas.Meter.cs --> Gas.Meter
AddXmlComments(options);
}
internal static void SetUpSwaggerUi(SwaggerUIOptions options, string? swaggerRelativeUrl, string? apiName)
{
options.SwaggerEndpoint(swaggerRelativeUrl, apiName);
}
private static void AddXmlComments(SwaggerGenOptions options)
{
var xmlFile = $"{Assembly.GetExecutingAssembly().GetName().Name}.xml";
var xmlPath = Path.Combine(AppContext.BaseDirectory, xmlFile);
options.IncludeXmlComments(xmlPath);
}
}
}
I'm using Swashbuckle.AspNetCore Nuget version 4.0.1我正在使用 Swashbuckle.AspNetCore Nuget 版本 4.0.1
I needed to dynamically add the host depending on where the app is hosted.我需要根据应用程序的托管位置动态添加主机。
This was my fix这是我的修复
So in .net core 3 and Open Api - Nswag.AspNetCore version 13.3.2 nuget.所以在 .net 核心 3 和 Open Api - Nswag.AspNetCore 版本 13.3.2 nuget 中。
app.UseOpenApi( configure => {
configure.PostProcess = (doc, httpReq) =>
{
doc.Servers.Clear(); //... remove local host, added via asp .net core
doc.Servers.Add(new OpenApiServer { Url = "[YOUR SERVER URL]" }); //... add server
};
});
pulled from this github answer: https://github.com/RicoSuter/NSwag/issues/2441#issuecomment-583721522从这个 github 答案中提取: https ://github.com/RicoSuter/NSwag/issues/2441#issuecomment-583721522
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.