I cannot for the life of me understand why this isn't working.
I have a simple ASP.Net MVC Web API controller, with 2 get methods. I have an AngularJS service with 2 corresponding functions. The GetAllRisks works perfectly well. However, the GetRiskByID comes back with an error saying "No HTTP request was found that matches the request "http://localhost:49376/api/RiskApi/GetRiskByID/6" and "No action can be found on the RiskApi controller that matches the request."
The URL is being passed correctly. I have tried various options for the API routing but can't get anywhere. I am sure I am missing something simple but can't see it.
I would really appreciate any thoughts.
Thanks,
Ash
RiskApiController
public class RiskApiController : ApiController
{
private readonly IRiskDataService _riskDataService;
public RiskApiController(IRiskDataService riskDataService)
{
_riskDataService = riskDataService;
}
// GET api/RiskApi
[HttpGet]
public IEnumerable<IRisk> GetAllRisks()
{
return _riskDataService.GetAllRisks().Take(20);
}
// GET api/RiskApi/5
[HttpGet]
public IRisk GetRiskByID(int riskID)
{
IRisk risk = _riskDataService.GetRiskByID(riskID);
if (risk == null)
{
throw new HttpResponseException(Request.CreateResponse(HttpStatusCode.NotFound));
}
return risk;
}
}
service.js
app.service('OpenBoxExtraService', function ($http) {
//Get All Risks
this.getAllRisks = function () {
return $http.get("/api/RiskApi/GetAllRisks");
}
//Get Single Risk by ID
this.getRisk = function (riskID) {
var url = "/api/RiskApi/GetRiskByID/" + riskID;
return $http.get(url);
}
});
WebApiConfig
public static class WebApiConfig
{
public static void Register(HttpConfiguration config)
{
config.Routes.MapHttpRoute(
name: "ActionRoute",
routeTemplate: "api/{controller}/{action}/{id}",
defaults: new { id = RouteParameter.Optional }
);
config.Routes.MapHttpRoute(
name: "DefaultApi",
routeTemplate: "api/{controller}/{id}",
defaults: new { id = RouteParameter.Optional }
);
}
}
/api/RiskApi/foo? It would match the api/{controller}/{id} as well as the api/{controller}/{action}/{id} route since you've got {id} optional on both. The router won't be able to tell if foo is an {id} or an {action} value. It naturally won't be able to send "foo" in as an int for the id, but I'm not sure if the router is intelligent enough to infer that the {action} based route is the one you want. I think it will just fail to route.