如何将Swagger与来自Web API操作方法的动态参数一起使用?

时间:2019-01-19 13:13:23

标签: c# asp.net-web-api nswag

我以非标准的方式编写Web API控制器,并以动态对象的形式获取参数。

这会引起NSwag问题。由于方法定义中没有参数,因此NSwag无法生成所需的内容。

我想知道在这种情况下是否可以使用NSwag。也许有些属性可以添加到方法中,以便NSwag能够生成API?

[HttpPost]
[ActionName("create-account")]
public IHttpActionResult CreateAccount()
{
    var body = Request.Content.ReadAsStringAsync().Result;

    dynamic json = Utils.GetJsonBody(body);

    if (!Utils.GetJsonPropertyValueByPropertyName<String>(json, "email", out String email))
    {
        return Content(HttpStatusCode.BadRequest, "Please provide a valid email.".AsApiMessageResult());
    }

    if (!Utils.GetJsonPropertyValueByPropertyName<String>(json, "name", out String name))
    {
        return Content(HttpStatusCode.BadRequest, "Please provide an account name.".AsApiMessageResult());
    }

    if (!Utils.GetJsonPropertyValueByPropertyName<String>(json, "domain", out String domain))
    {
        return Content(HttpStatusCode.BadRequest, "Please provide a valid domain.".AsApiMessageResult());
    } 

1 个答案:

答案 0 :(得分:4)

关于Swagger的事情是它使用方法的签名来生成其代码工作方式的文档。绕过所有普通的Web API并选择读取原始的HTTP请求意味着Swagger无法看到您在做什么,这使其很难自动确定您的代码在做什么。您在读取原始请求和使用动态数据时所采用的技术还有许多其他缺点。

  • 您不会为对象获得Intellisense
  • It's not functional意味着很难通过查看方法来判断输入和输出的含义,这很难理解
  • 很难对代码进行单元测试,因为现在您必须为Web API控制器建立HTTP请求
  • 与使用适当的对象做事相比,它需要更多的代码

相反,我们应该定义一个适当的模型来发布到我们的API。这将使Web API能够完成其工作,模型绑定程序将处理将请求转换为CreateAccountRequest实例的情况。

public class CreateAccountRequest
{
    public string Email { get; set; }

    public string Name { get; set; }

    public string Domain { get; set; }
}

然后,我们可以让我们的action方法将此类的实例作为参数。

[HttpPost]
[ActionName("create-account")]
public IHttpActionResult CreateAccount(CreateAccountRequest request)
{
    //now here you can validate the request if you want
}

Swagger现在应该能够理解此方法,从而允许NSwag生成有用的客户端。

请注意,您应该研究Web API为model validation提供的内置工具,而不是执行自定义C#验证。然后,您所需要做的就是检查ModelState,而不是手动检查每个参数。其他工具也可以查看模型的属性,从而改善工具体验。