问题
I'm migrating a full .NET Framework Web API 2 REST project over to ASP.NET Core 2.2 and getting a bit lost in the routing.
In Web API 2 I was able to overload routes with the same number of parameters based on the parameter type, e.g. I could have Customer.Get(int ContactId)
and Customer.Get(DateTime includeCustomersCreatedSince)
and incoming requests would be routed accordingly.
I haven't been able to achieve the same thing in .NET Core, I either get a 405 error or a 404 and this error instead:
"{\"error\":\"The request matched multiple endpoints. Matches: \r\n\r\n[AssemblyName].Controllers.CustomerController.Get ([AssemblyName])\r\n[AssemblyName].Controllers.CustomerController.Get ([AssemblyName])\"}"
This was working code in my full .NET framework app Web API 2 app:
[RequireHttps]
public class CustomerController : ApiController
{
[HttpGet]
[ResponseType(typeof(CustomerForWeb))]
public async Task<IHttpActionResult> Get(int contactId)
{
// some code
}
[HttpGet]
[ResponseType(typeof(List<CustomerForWeb>))]
public async Task<IHttpActionResult> Get(DateTime includeCustomersCreatedSince)
{
// some other code
}
}
And this is what I converted it to in Core 2.2:
[Produces("application/json")]
[RequireHttps]
[Route("api/[controller]")]
[ApiController]
public class CustomerController : Controller
{
public async Task<ActionResult<CustomerForWeb>> Get([FromQuery] int contactId)
{
// some code
}
public async Task<ActionResult<List<CustomerForWeb>>> Get([FromQuery] DateTime includeCustomersCreatedSince)
{
// some code
}
}
The code above works if I comment out one of Get
methods, but fails as soon as I have two Get
methods. I'd expected the FromQuery to use the parameter name in the request to steer the routing, but that doesn't seem to be the case?
Is it possible to overload a controller method like this where you have the same number of parameters and either route based on the parameter's type or the parameter's name?
回答1:
You cannot do action overloads. The way routing works in ASP.NET Core is different than how it did in ASP.NET Web Api. However, you can simply combine these actions and then branch inside, since all params are optional:
public async Task<ActionResult<CustomerForWeb>> Get(int contactId, DateTime includeCustomersCreatedSince)
{
if (contactId != default)
{
...
}
else if (includedCustomersCreatedSince != default)
{
...
}
}
来源:https://stackoverflow.com/questions/55569250/how-to-overload-controller-methods-with-same-number-of-arguments-in-asp-net-core