10

I want to be able to take over the 404 response from web api (iis) when the resource does not exist.

I have done my research and came across only one solution that made this work, but i am not sure how "safe" it is since the "routeTemplate" is just {*url}

This post is kinda to ask for help and explanation.

My App uses MVC and WebAPI... would this template affect MVC as well? Is there a way to add "api" with {*url} in the template? (to make sure only requests with ".../api/..." get affected)

config.Routes.MapHttpRoute("Error404", "{*url}", new { controller = "Error", action = "Handle404" });

Has anyone come across a cleaner way of doing this and handling 404 in web api?

EDIT 1

The above code DOES affect my MVC routes. How can i add "api" to "{*url}"?... if tried many different ways and no dice.

2
  • Did you try "{api/*url}" or "{api*url}" etc.. ? Commented Oct 26, 2015 at 19:25
  • I had the same issue, site using both web api and MVC. Following the instructions in the article you linked to will break your MVC routing. The solution is to change the route template to "api/{*url} Commented Jun 29, 2017 at 13:42

1 Answer 1

7

Had the exact same issue. After some research and trial and error, I was able to find a working solution.

I went with a RoutePrefix solution and I tried to implement something similar to how the MVC controllers used HandleUnknownAction in a base controller.

With the help from this post: .NET WebAPI Attribute Routing and inheritance to allow for route inheritance, I created a base controller for my web APIs with a HandleUnknownAction method like this:

public abstract class WebApiControllerBase : ApiController {

    [Route("{*actionName}")]
    [AcceptVerbs("GET", "POST", "PUT", "DELETE")]//Include what ever methods you want to handle
    [AllowAnonymous]//So I can use it on authenticated controllers
    [ApiExplorerSettings(IgnoreApi = true)]//To hide this method from helpers
    public virtual HttpResponseMessage HandleUnknownAction(string actionName) {
        var status = HttpStatusCode.NotFound;
        //This is custom code to create my response content
        //....
        var message = status.ToString().FormatCamelCase();
        var content = DependencyService
            .Get<IResponseEnvelopeFactory>()
            .CreateWithOnlyMetadata(status, message);
        //....
        return Request.CreateResponse(status, content);
    }
}

If you don't want to go down the inheritance path, you can always put the method directly into the controller you want to apply the functionality on.

This allows me to use route prefixes that handle custom not found messages that pertain to specific controllers as I have both back-office and public public facing APIs.

If a URL does not apply to an ApiController the default Error controller will handle the not found as usual.

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.