0

通过使用 ExpandoObject 作为参数,我创建了一种非常简洁的方法来为我的 Web.API 项目实现 PATCH 方法。如下图所示:

[HttpPatch, Route("api/employee/{id:int}")]
public IHttpActionResult Update(int id, [FromBody] ExpandoObject employee)
    {
        var source = Repository.FindEmployeeById(id);
        Patch(employee, source);
        Repository.SaveEmployee(source);
        return Ok(source);
    }

但是,在生成文档时,ApiExplorer 不知道如何处理 ExpandoObject,这是完全可以理解的。有人对如何操作 ApiExplorer 以提供一些合理的文档有任何想法吗?

我的想法是可能引入一个新属性,该属性指向预期的实际类型:

public IHttpActionResult Update(int id, [FromBody, Mimics(typeof(Employee))] ExpandoObject employee) 
{ 
    ... 
}

但我不知道从哪里开始,欢迎任何想法或建议。

4

1 回答 1

0

因此,为了让 Api Explorer 与我们开发的 Http Patch 机制一起玩,这一直是一些深夜的来源。说实话,我可能应该写一些适当的文章来全面解释整个想法背后的机制。但是对于那些因为希望 Api 浏览器在文档中使用不同类型而登陆此页面的人来说,这是您需要查看的地方:

打开 HelpPageConfigurationExtensions.cs 并找到以下方法:

//File: Areas/HelpPage/HelpPageConfigurationExtensions.cs
private static void GenerateRequestModelDescription(HelpPageApiModel apiModel, ModelDescriptionGenerator modelGenerator, HelpPageSampleGenerator sampleGenerator)
{
    ....
}

这是您可以使用参数信息的位置,并且还使您能够用其他内容替换/替换参数信息。我最终执行了以下操作来处理我的 ExpandoObject 参数问题:

if (apiParameter.Source == ApiParameterSource.FromBody)
{
    Type parameterType = apiParameter.ParameterDescriptor.ParameterType;

    // do something different when dealing with parameters 
    // of type ExpandObject.
    if (parameterType == typeof(ExpandoObject))
    {
         // if a request-type-attribute is defined, assume the parameter
         // is the supposed to mimic the type defined.
         var requestTypeAttribute = apiParameter.ParameterDescriptor.GetCustomAttributes<RequestTypeAttribute>().FirstOrDefault();
         if (requestTypeAttribute != null)
         {
             parameterType = requestTypeAttribute.RequestType;
         }
    }
}

只是,请注意 RequestTypeAttribute 是我设计的。我的 WebApi 端点现在看起来像这样:

public IHttpActionResult Update(int id, 
    [FromBody, RequestType(typeof(Employee))] ExpandoObject employee)

感谢所有花时间研究问题的人。

于 2016-03-31T12:56:07.310 回答