Reputation: 57
When I try to hit my API controller using get url I am getting following error:
Multiple actions were found that match the request:
IsStoreKeyValid on type BlexzWeb.Controllers.ApiDevToolController
GetPageIds on type BlexzWeb.Controllers.ApiDevToolController
The WebApiConfig.cs are like bellow:
public static class WebApiConfig
{
public static void Register(HttpConfiguration config)
{
config.MapHttpAttributeRoutes();
config.Routes.MapHttpRoute(
name: "DefaultApi",
routeTemplate: "api/{controller}/{action}/{id}",
defaults: new { id = RouteParameter.Optional }
);
//code bellow used to return json on api call
GlobalConfiguration.Configuration.Formatters.JsonFormatter.MediaTypeMappings
.Add(new System.Net.Http.Formatting.RequestHeaderMapping("Accept",
"text/html",
StringComparison.InvariantCultureIgnoreCase,
true,
"application/json"));
}
}
Controller code:
public class ApiDevToolController : ApiController
{
private bool IsValid { get; set; }
[HttpGet]
public IHttpActionResult IsStoreKeyValid(string storeName, string storeKey)
{
}
//get list of pageids
[HttpGet]
public IHttpActionResult GetPageIds(string storeName, string storeKey)
{
}
}
Url I am using to hit controller: http://localhost:49817/api/apidevtool/isstorekeyvalid?storeName=test.myblexz.com&storeKey=fdesfhkfg5g437dfgh5u
Whats wrong I am doing here? Any idea how to fix it?
Upvotes: 3
Views: 844
Reputation: 46229
Let us see the source code from webapi ApiControllerActionSelector code of action selector.
private List<CandidateActionWithParams> FindMatchingActions(HttpControllerContext controllerContext, bool ignoreVerbs = false)
{
// If matched with direct route?
IHttpRouteData routeData = controllerContext.RouteData;
IEnumerable<IHttpRouteData> subRoutes = routeData.GetSubRoutes();
IEnumerable<CandidateActionWithParams> actionsWithParameters = (subRoutes == null) ?
GetInitialCandidateWithParameterListForRegularRoutes(controllerContext, ignoreVerbs) :
GetInitialCandidateWithParameterListForDirectRoutes(controllerContext, subRoutes, ignoreVerbs);
// Make sure the action parameter matches the route and query parameters.
List<CandidateActionWithParams> actionsFoundByParams = FindActionMatchRequiredRouteAndQueryParameters(actionsWithParameters);
List<CandidateActionWithParams> orderCandidates = RunOrderFilter(actionsFoundByParams);
List<CandidateActionWithParams> precedenceCandidates = RunPrecedenceFilter(orderCandidates);
// Overload resolution logic is applied when needed.
List<CandidateActionWithParams> selectedCandidates = FindActionMatchMostRouteAndQueryParameters(precedenceCandidates);
return selectedCandidates;
}
We can see if you use register in route for RouteTable
, it will find the execute action by your parameters type by defualt.
I would use RoutePrefix
and Route
attribute to set the route config for web api.
[RoutePrefix("api/ApiDevTool")]
public class ApiDevToolController : ApiController
{
private bool IsValid { get; set; }
[HttpGet]
[Route("IsStoreKeyValid")]
public string IsStoreKeyValid(string storeName, string storeKey)
{
}
//get list of pageids
[HttpGet]
[Route("GetPageIds")]
public string GetPageIds(string storeName, string storeKey)
{
}
}
Upvotes: 1
Reputation: 1153
It happens because your second action name starts with Get... and also it has the same parameter like first action (IsStoreKeyValid(string storeName, string storeKey))
By default, if action is HttpGet then it searches action name which starts with GetSomething and check parameter. More Info MSDN
You need to change the second function name or need to use attribute routing
ex.[Route("pageIds")]
more info attribute routing
Upvotes: 1