0

My route config looks like this

public static void RegisterRoutes(RouteCollection routes)
{
    routes.IgnoreRoute("{resource}.axd/{*pathInfo}");

    routes.MapRoute(
        name: "Default",
        url: "{controller}/{action}/{id}",
        defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional }
    );
}

I have my user controller divided by action into separate files, so all GET operations are in the GetUserController.cs file, PUT operations in PutUserController.cs and so on...

The GET file has a partial class like this

[RoutePrefix("api/users/{userId:Guid}/locations")]
public partial class UsersController : MyCustomApiController
{    
    [Route("{locationId:Guid}/list")]
    [HttpPost]
    public async Task<IHttpActionResult> GetUsers(Guid userId, Guid locationId, [FromBody] Contracts.UserRequest request)
    { 
    }
}

The PUT file has a partial class like this

public partial class UsersController : MyCustomApiController
{    
    [Route("{locationId:Guid}/insert")]
    [HttpPut]
    public async Task<IHttpActionResult> InsertUser(Guid userId, Guid locationId, [FromBody] Contracts.UserRequest request)
    { 
    }
}

No matter what I do, I always get a 404 Error. I am testing with Postman using Content-Type as application/json The URL I am using is http://localhost:52450/api/users/3F3E0740-1BCB-413A-93E9-4C9290CB2C22/locations/4F3E0740-1BCB-413A-93E9-4C9290CB2C22/list with a POST since I couldn't use GET to post a complex type for the first method

and

http://localhost:52450/api/users/3F3E0740-1BCB-413A-93E9-4C9290CB2C22/locations/4F3E0740-1BCB-413A-93E9-4C9290CB2C22/insert with a PUT

What other routes do I need to setup in the route config if at all?

EDIT

Strangely another controller which is also a partial class seems to work with the same configuration

[RoutePrefix("api/products")]
public partial class ProductController : MyCustomApiController
{

    [Route("insert")]
    [HttpPut]
    public async Task<IHttpActionResult> InsertProduct([FromBody] InsertProductRequest request)
    {
    }
}

This is the global.asax.cs that wires up everything.

protected void Application_Start(object sender, EventArgs e)
{

    AreaRegistration.RegisterAllAreas();

    GlobalConfiguration.Configure(WebApiConfig.Register);
    RouteConfig.RegisterRoutes(RouteTable.Routes);
    FilterConfig.RegisterFilters(GlobalFilters.Filters);

    // Only allow Tls1.2!
    ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12;


}
Nkosi
  • 235,767
  • 35
  • 427
  • 472
user20358
  • 14,182
  • 36
  • 114
  • 186

2 Answers2

0

That is the wrong config file for configuring Web API routes.

//global.asax.cs
GlobalConfiguration.Configure(WebApiConfig.Register); // <-- WEB API
RouteConfig.RegisterRoutes(RouteTable.Routes); // <-- MVC

Check the WebApiConfig.cs to configure web API routes.

public static class WebApiConfig
{
    public static void Register(HttpConfiguration config)
    {
        // Attribute routing.
        config.MapHttpAttributeRoutes();

        // Convention-based routing.
        config.Routes.MapHttpRoute(
            name: "DefaultApi",
            routeTemplate: "api/{controller}/{id}",
            defaults: new { id = RouteParameter.Optional }
        );
    }
}

Also your route constraint for Guid is wrong. It should be {parameterName:guid}

[RoutePrefix("api/users/{userId:guid}/locations")]
public partial class UsersController : MyCustomApiController { 
    [HttpPost]
    [Route("{locationId:guid}/list")]
    public async Task<IHttpActionResult> GetUsers(Guid userId, Guid locationId, [FromBody] Contracts.UserRequest request) { ... }
}

Source: Attribute Routing in ASP.NET Web API 2

Nkosi
  • 235,767
  • 35
  • 427
  • 472
  • Thanks for the reply. I dont have the prefix on the other partial file. That got copied in the question by mistake. I have corrected that. On your second tip, the config.MapHttpAttributeRoutes() in the WebApiConfig.cs calls the `RegisterRoutes` method in the `Routeconfig.cs` – user20358 Feb 28 '17 at 18:35
  • @user20358, No it does not. Look carefully. Two different registration for MVC and Web API – Nkosi Feb 28 '17 at 18:39
  • Thats strange. I have another controller in the same project that works. Its also a partial class. Will update my main question with those details. Also, I put a breakpoint in my route config and the registerroutes in routeconfig.cs was called from WebApiConfig.cs – user20358 Feb 28 '17 at 18:46
  • @user20358, Unless you changed something i can assure you that is not the case. Show your startup. – Nkosi Feb 28 '17 at 18:55
  • There is no startup.cs Its just the global.asax that I will add to the main question – user20358 Feb 28 '17 at 19:19
  • This is a project that I have inherited and don't think I can change much :( – user20358 Feb 28 '17 at 19:22
0

You can try to do like this in you WebApiConfig :

  config.MapHttpAttributeRoutes();
  var corsAttr = new EnableCorsAttribute("*", "*", "*");
  config.EnableCors(corsAttr);
Samvel Petrosov
  • 7,580
  • 2
  • 22
  • 46