ASP.NET MVC Custom view engine not called

I am trying to implement a custom view engine to serve mobile views based on a user agent. I am following Scott Hanselman's approach from this blog post .

I inherited from WebFormsViewEngine and overridden the FindView method just as Scott describes in his blog.

Then I added a few lines to my Global.asax Application_Start method to clear the view engine collection and add a new instance of my view engine.

After some testing, it turned out that MVC was ignoring my view engine. When it couldn't find my custom views based on the browser user agent I resorted to hard-coding the custom path to add to the view and still managed to revert to the default view. I set a breakpoint in my FindView method and of course it was not called at all.

How can I get my custom view engine to work? Any help would be much appreciated.

The view engine looks like this:

public class MyViewEngine: WebFormsViewEngine
{
    public override ViewEngineResult FindView (ControllerContext controllerContext, string viewName, string masterName, bool useCache)
    {
         ViewEngineResult result = null;

         //Serve a special view for iPhones
         if (UserAgentIs(controllerContext, "iPhone"))
         {
              result = base.FindView(controllerContext, "Mobile/iPhone/" + viewName, masterName, useCache);
         }

         //If no special view is found, fall back to the default view
         if (result == null || result.View == null)
         {
              result = base.FindView(controllerContext, viewName, masterName, useCache);
         }

         return result;
    }

    private bool UserAgentIs(ControllerContext controllerContext, string userAgentToTest)
    {
         return (controllerContext.HttpContext.Request.UserAgent.IndexOf(userAgentToTest, StringComparison.OrdinalIgnoreCase) > 0);
    }
}

      

And in my Global.asax:

protected void Application_Start()
{
    RegisterRoutes(RouteTable.Routes);
    ViewEngines.Engines.Clear();
    ViewEngines.Engines.Add(new MyViewEngine());
}

      

When this setting didn't work, I even tried to simplify the FindView method:

public override ViewEngineResult FindView (ControllerContext controllerContext, string viewName, string masterName, bool useCache)
    {
         ViewEngineResult result = null;
         result = base.FindView(controllerContext, "Mobile/iPhone/" + viewName, masterName, useCache);
         return result;
    }

      

And that didn't work either. It still returns the default view. And yes, the browse page and the home page that this statement should find do exist. I'm pretty dumb as to why this doesn't work.

+2


source to share


1 answer


Well, this is, of course, awkward:

When I wrote my view engine I followed a blog post from Scott Hanselman (see my original post for a link). I applied my view engine class, then figured I'd just copy and paste Scott's code into my class and modify it as needed. I accidentally copied his C class definition code into my class by creating a nested class. So my view engine did not actually contain an override for the FindView method, and naturally the one that was the nested class will never be called!

Lesson: When using code found on the web, don't copy and paste! Always enter it yourself.



Thanks to everyone who checked this question and tried to help me.

I will now stand in a corner of shame and embarrassment!

+2


source







All Articles