Netcore webapi action swagger response返回参数使用匿名类型
问题:action中返回匿名对象时,swagger只能按强类型生成返回值描述
解决办法:使用roslyn在内存中动态执行代码,使用json.net反序列化匿名对象,向swagger返回动态匿名对象
效果:




Swaager在描述控制器的方法时,可以使用以下方法
<response code="400">如果id为空</response>
或
[ProducesResponseType(typeof(ResponseT<User>),
200)]
Openapi json如下

生成效果如下图

上述方法必须存在强类型user
代码
@@@code
[AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, AllowMultiple = true, Inherited = true)]
public class AnonymousTypeProducesResponseTypeAttribute : Microsoft.AspNetCore.Mvc.ProducesResponseTypeAttribute
{
public AnonymousTypeProducesResponseTypeAttribute(string typeJson, int statusCode) : base(getAnonymousType(typeJson), statusCode)
{
}
/// <summary>
///
/// </summary>
/// <param name="typeJson">匿名类型描述串
/// </param>
/// <example>new {id=1,name=""}</example>
/// <param name="statusCode"></param>
static System.Type getAnonymousType(string typeJson)
{
var code = @"
public class Result {
public System.Type GetType2(){
var t = Newtonsoft.Json.JsonConvert.DeserializeAnonymousType(""{}"", #T#);
return t.GetType();
}
}
".Replace("#T#", typeJson.Replace("'", @""""));
List<PortableExecutableReference> refList = new List<PortableExecutableReference>();
refList.Add(MetadataReference.CreateFromFile(typeof(object).Assembly.Location));
refList.Add(MetadataReference.CreateFromFile(typeof(Newtonsoft.Json.JsonConvert).Assembly.Location));
refList.Add(MetadataReference.CreateFromFile(typeof(System.Runtime.AssemblyTargetedPatchBandAttribute).Assembly.Location));
refList.Add(MetadataReference.CreateFromFile(System.IO.Path.Combine(System.IO.Path.GetDirectoryName(typeof(object).Assembly.Location), "netstandard.dll")));
var tree = CSharpSyntaxTree.ParseText(code);
var compilation = CSharpCompilation.Create("test")
.WithOptions(new CSharpCompilationOptions(OutputKind.DynamicallyLinkedLibrary))
.AddReferences(refList.ToArray()).AddSyntaxTrees(tree);
using (var stream = new MemoryStream())
{
var emitResult = compilation.Emit(stream);
if (emitResult.Success)
{
stream.Seek(0, SeekOrigin.Begin);
var assembly = Assembly.Load(stream.ToArray());
var typeResult = assembly.GetType("Result");
var m = Activator.CreateInstance(typeResult);
var Type = m.GetType();
return typeResult.GetMethod("GetType2").Invoke(m, null) as Type;
}
}
return null;
}
}
@@#
使用
@@@code
[HttpGet("Dept/Get")]
[AnonymousTypeProducesResponseType(@"new {Code=0,Msg='',Data=new []{new {id=0,name=''}}}", 200)]
public object DeptGet()
{
return new
{
Code = 0,
Msg = string.Empty,
Data = _context. Group.Select(r => new
{
id = r. ID,
name = r. Name
}).ToList()
};
}
@@#
另一种借助元组实现的方法
花了大量时间获取属性名没有结果,泛型传递时的方法获取 不到TupleElementNamesAttribute,只能走动态方法获取 返回值 ,再利用TupleElementNamesAttribute获取 名称
@@@code
public class ResponseT<T>
{
//有效 [JsonProperty("haaa")]
public int Code { get; set; }
// 无效 [JsonConverter(typeof(Q.DevExtreme.Tpl.Json.IPAddressConverter))]
public string Msg { get; set; }
public T Data { get; set; }
public T[] GetData()
{
//泛型,丢失名称信息,没有TupleElementNamesAttribute属性
return new[] { Data };
}
public (int a, string b) GetData2()
{
//可以使用下列方法获得名称
//Type t = typeof(C);
//MethodInfo method = t.GetMethod(nameof(C.M));
//var attr = method.ReturnParameter.GetCustomAttribute<TupleElementNamesAttribute>();
//string[] names = attr.TransformNames;
return (1, "2");
}
}
@@#
使用
@@@code
[ProducesResponseType(typeof(ResponseT<(int id,string name)>), 400)]
@@E
Netcore webapi action swagger response返回参数使用匿名类型的更多相关文章
- 使用ActionFilterAttribute 记录 WebApi Action 请求和返回结果记录
使用ActionFilterAttribute 记录 WebApi Action 请求和返回结果记录 C#进阶系列——WebApi 异常处理解决方案 [ASP.NET Web API教程]4.3 AS ...
- Web API系列(四) 使用ActionFilterAttribute 记录 WebApi Action 请求和返回结果记录
转自:https://www.cnblogs.com/hnsongbiao/p/7039666.html 需要demo在github中下载: https://github.com/shan333cha ...
- Asp.NetCore WebApi 引入Swagger
一.创建一个Asp.NetCore WebApi 项目 二.引入NuGet包 SwashBuckle.AspNetCore 三.在项目属性配置中设置 四.修改项目的启动文件Startup.cs 1). ...
- .NetCore WebApi利用Swagger文档实现选择文件上传
介绍 实现这个功能主要还是依赖过滤器 在Swagger中利用 IOperationFilter 操作来实现文件上传 与之前处理结合Idr4授权一样的处理方式,不同的是授权处理的是Security,而文 ...
- .NetCore WebApi——基于JWT的简单身份认证与授权(Swagger)
上接:.NetCore WebApi——Swagger简单配置 任何项目都有权限这一关键部分.比如我们有许多接口.有的接口允许任何人访问,另有一些接口需要认证身份之后才可以访问:以保证重要数据不会泄露 ...
- .NetCore WebApi——Swagger简单配置
在前后端分离的大环境下,API接口文档成为了前后端交流的一个重点.Swagger让开发人员摆脱了写接口文档的痛苦. 官方网址:https://swagger.io/ 在.Net Core WebApi ...
- .NetCore WebApi —— Swagger版本控制
目录: .NetCore WebApi——Swagger简单配置 .NetCore WebApi——基于JWT的简单身份认证与授权(Swagger) .NetCore WebApi —— Swagge ...
- VS2012 Unit Test(Void, Action, Func) —— 对无返回值、使用Action或Func作为参数、多重载的方法进行单元测试
[提示] 1. 阅读文本前希望您具备如下知识:了解单元测试,了解Dynamic,熟悉泛型(协变与逆变)和Lambda,熟悉.NET Framework提供的 Action与Func委托.2.如果您对单 ...
- 对无返回值、使用Action或Func作为参数、多重载的方法进行单元测试
VS2012 Unit Test(Void, Action, Func) —— 对无返回值.使用Action或Func作为参数.多重载的方法进行单元测试 [提示] 1. 阅读文本前希望您具备如下知识: ...
随机推荐
- react-app 编写测试
jest Enzyme 文档 为什么要写测试 单元测试(unit testing)指的是以软件的单元(unit)为单位,对软件进行测试.单元可以是一个函数,也可以是一个模块或组件.它的基本特征就是,只 ...
- 手把手教你Centos7 部署 gitlab社区版
一.前置说明: 操作系统:Centos 7 物理内存:>=2G 本人亲测,如果安装低版本的gitlab,比如我这里所使用的v8.17.0,物理内存1G,swap 2G虚拟内存即可部署.高版本的所 ...
- 图文详解:Kafka到底有哪些秘密让我对它情有独钟呢?
- CSS实现页面切换时的滑动效果
最近在开发手机端APP页面功能时遇到一个需求:某个页面查询的数据有三种分类,需要展示在同一页面上,用户通过点击分类标签来查看不同类型的数据, 期望效果是 用户点击标签切换时另一个页面能够以一个平滑切入 ...
- Kubernetes-6.Service
docker version:20.10.2 kubernetes version:1.20.1 本文概述Kubernetes Service的基本原理和使用. 服务 Service是将运行在一组Po ...
- 剑指 Offer 64. 求1+2+…+n + 递归
剑指 Offer 64. 求1+2+-+n Offer_64 题目描述 题解分析 使用&&逻辑短路规则来终止循环 package com.walegarrett.offer; /** ...
- windows基线检测脚本编写指南-powershell版
前言: 因为工作的原因,要写windows下的基线检查脚本.之前没接触过,在网上找了半天也没找到现成的,无奈只好自己研究,最后还是成功完成了工作. 在我编写之后发现windows下的基线基本就是检 ...
- Kilo 使用教程
写了这么多篇 WireGuard 相关的保姆教程,今天终于牵扯到 Kubernetes 了,不然怎么对得起"云原生"这三个字.如果看到这篇文章的你仍然是个 WireGuard 新手 ...
- JAVA-标识符、变量、数据类型
标识符和关键字 所有的标识符否应该以字母a ~ z和 A ~Z ,美元符($).下划线(_)开始. 首字符之后可以是字母a ~ z和 A ~Z ,美元符($).下划线(_)的任意字符组合. 注 ...
- uni-app(二)接口请求封装,全局输出api
在项目 main.js 同级创建 utils 文件夹, utils里创建 config.js文件,存储重要参数 // 获取平台信息 const { system, } = uni.getSystemI ...