Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

ASP.NET MVC: Controller.HandleUnknownAction 404 or 405?

I'm overriding ASP.NET MVC's Controller.HandleUnknownAction(string actionName) method. It's being called when an action is not found and also when an HTTP method is not allowed. How can I distinguish between the two? I'd like to return a 404 when and action is not found and 405 when a method is note allowed.

like image 469
Johnny Oshika Avatar asked Oct 07 '22 23:10

Johnny Oshika


1 Answers

The simplest way I can think of is to create custom action filter. This will allow you to return http status code result if method is not allowed

public class HttpPostFilterAttribute : ActionFilterAttribute
{
    public override void OnActionExecuting(ActionExecutingContext filterContext)
    {
        if (!(filterContext.RequestContext.HttpContext.Request.GetHttpMethodOverride().Equals("post", StringComparison.InvariantCultureIgnoreCase)))
        {
            filterContext.Result = new HttpStatusCodeResult(405);
        }
    }
}

Or better, create more generic version of it, much like AcceptVerbsAttribute

[AttributeUsage(AttributeTargets.Method, AllowMultiple = false, Inherited = true)]
public sealed class AllowMethodsAttribute : ActionFilterAttribute
{
    public ICollection<string> Methods
    {
        get;
        private set;
    }

    public AllowMethodsAttribute(params string[] methods)
    {
        this.Methods = new ReadOnlyCollection<string>(methods);
    }

    public override void OnActionExecuting(ActionExecutingContext filterContext)
    {
        string httpMethodOverride = filterContext.HttpContext.Request.GetHttpMethodOverride();
        if (!this.Methods.Contains(httpMethodOverride, StringComparer.InvariantCultureIgnoreCase))
        {
            filterContext.Result = new HttpStatusCodeResult(405);
        }
    }
}

And use it like

[AllowMethods("GET")]
public ActionResult Index()
{
    ViewBag.Message = "Welcome to ASP.NET MVC!";

    return View();
}

Customizing attribute to take HttpVerbs as parameter is up to you.

like image 66
archil Avatar answered Oct 18 '22 03:10

archil