如何用Swashbuckle.AspNetCore在Swagger中展示运行时动态路径参数值
问题背景
我维护着一个Web API,接口URL模板为TestEmail/Render/{templateName},其中templateName的可选值是通过反射在运行时从实现了INotification接口的类型中获取的。对应的控制器代码如下:
public class TestEmailController : Controller { public static IEnumerable<Type> AllNotificationTypes => typeof(INotification).Assembly.GetTypes() .Where(t => typeof(INotification).IsAssignableFrom(t) && !t.IsAbstract); [HttpGet("[controller]/{templateName}")] public async Task<IActionResult> Render(string templateName) { Type templateType = AllNotificationTypes.FirstOrDefault(t => t.Name == templateName); if (templateType == null) return NotFound(); string renderedHtml = ... return Content(renderedHtml, "text/html"); } }
想请教如何通过Swashbuckle.AspNetCore,让这些动态获取的可选参数值在Swagger文档中体现出来?
最终实现方案
受相关思路启发,我通过自定义Swagger操作过滤器完成了需求,具体步骤如下:
1. 在接口方法上标记使用自定义过滤器
给Render接口添加SwaggerOperationFilter特性,指定我们要使用的过滤器类型:
[SwaggerOperationFilter(typeof(TemplateNameOperationFilter))] [HttpGet("[controller]/{templateName}")] public async Task<IActionResult> Render(string templateName) { // 原有业务逻辑代码 .... }
2. 实现自定义操作过滤器
创建TemplateNameOperationFilter类,实现IOperationFilter接口,在Swagger文档生成时动态修改templateName参数的元数据:
public class TemplateNameOperationFilter : IOperationFilter { public void Apply(Operation operation, OperationFilterContext context) { // 定位到templateName参数 var param = (PartialSchema)operation.Parameters.First(o => o.Name == "templateName"); // 将运行时反射得到的所有合法模板名称设置为参数的枚举选项 param.Enum = TestEmailController.AllNotificationTypes.Select(type => (object)type.Name).ToList(); } }
实现原理
IOperationFilter是Swashbuckle提供的扩展点,允许我们在Swagger文档生成流程中,对接口的元数据进行自定义修改- 我们通过
operation.Parameters找到目标参数templateName,将其转换为PartialSchema类型后,把反射获取到的所有INotification实现类名称赋值给Enum属性 - 这样在Swagger UI中,
templateName参数会显示为下拉选择框,列出所有合法的模板名称,用户无需手动输入,同时Swagger JSON文档中也会包含这些枚举值定义
内容的提问来源于stack exchange,提问作者Liero
相关产品推荐
相关产品推荐

