Search code examples
c#asp.net-web-apiasp.net-web-api-routing

HTTP 404 on invoking my WebAPI method


I'm trying to invoke my WebAPI method as defined below by using fiddler, but I'm getting the following exception. Please let me know what I'm missing here, as I'm not able to hit the method defined.

Method prototype:

[Route("api/tournament/{tournamentId}/{matchId}/{teamId}/{userEmail}/PostMatchBet")]
public HttpResponseMessage PostMatchBet(int tournamentId, int matchId, int teamId, string userEmail)

The method is defined within Tournament WebAPI controller and trying to access method with HTTP verb set to post as follows,

http://localhost:59707/api/tournament/PostMatchBet?tournamentId=1&matchId=1&teamId=8&userEmail=abc@gmail.com

Please let me know what am I missing here.

Exception detail: "MessageDetail":"No action was found on the controller 'Tournament' that matches the request."


Solution

  • Make sure route configuration is done correctly.

    public static class WebApiConfig 
        public static void Register(HttpConfiguration config) {
            // Attribute routing.
            config.MapHttpAttributeRoutes();
    
            // Convention-based routing.
            config.Routes.MapHttpRoute(
                name: "DefaultActionApi",
                routeTemplate: "api/{controller}/{action}/{id}",
                defaults: new { id = RouteParameter.Optional }
            );
    
            config.Routes.MapHttpRoute(
                name: "DefaultApi",
                routeTemplate: "api/{controller}/{id}",
                defaults: new { id = RouteParameter.Optional }
            );
        }
    }
    

    Make sure action has correct verb and route. You are mixing convention-based and attribute routing. decide which one you want to use and stick with that.

    for this POST URL to work...

    http://localhost:59707/api/tournament/PostMatchBet?tournamentId=1&matchId=1&teamId=8&userEmail=abc@gmail.com
    

    it would match a convention-based route template like

    api/{controller}/{action}
    

    mapped to this action.

    public class TournamentController : ApiController {
        [HttpPost]
        public HttpResponseMessage PostMatchBet(int tournamentId, int matchId, int teamId, string userEmail) { ... }
    }
    

    If doing attribute routing then controller needs to be updated to...

    [RoutePrefix("api/tournament")]
    public class TournamentController : ApiController {
        //POST api/tournament/postmatchbet{? matching query strings}
        [HttpPost]
        [Route("PostMatchBet")]
        public HttpResponseMessage PostMatchBet(int tournamentId, int matchId, int teamId, string userEmail) { ... }
    }