Let’s face it: IIS can be a tricky beast. And as SharePoint admins, there’s not a whole lot we can & should be doing in there anyway. SharePoint handles most of it for us, so we can stay blissfully unaware of what’s going on behind the scenes in IIS. But as we all know, occasionally things can & will go wrong, and when they do it helps to have an understanding of what’s happening under the covers. Therefore, I wanted to write up a brief introduction to how SharePoint uses handlers & how you can use IIS failed request tracing to troubleshoot when things go wrong.
So what’s a handler anyway? Well, here’s a good high level overview from technet: “handlers process requests made to sites and applications. Handlers map to resources on the Web server and generate responses for requests. Like modules, handlers are implemented by either native or managed components, such as DLLs or managed code. When a client browser requests a file from the Web server, IIS determines which handler to use based on the ordered list of handler mappings in configuration. If there is an entry that matches the request type and extension (for example, a GET request for an .aspx file respectively), IIS calls the handler mapped to that request combination, and then invokes the associated mapped handler to process the request and return a result to the client browser.”
Sounds simple enough. So how does this apply to SharePoint? Well, have you ever looked at the file system on one of your WFEs & wondered where all the pages are? Sure, the _layouts stuff is there, but where’s the rest of it? And where are all the sites in the virtual directory structure? It may seem like smoke & mirrors, but it’s actually the handlers doing the work taking over your request, pulling pages from the databases, and basically – making SharePoint happen.
So now you’re intrigued, right? How can I see these handlers & their mappings? Easy– open IIS manager & in features view, under the IIS category, look for “handler mappings”. Open it up & take a look.
Now let’s revisit the Technet description of handlers, specifically: “When a client browser requests a file from the Web server, IIS determines which handler to use based on the ordered list of handler mappings in configuration”. Be aware that the default view of handler mappings doesn’t show that ordered list, so you need to look to the Actions pane & click the “view ordered list” option to actually view the ordering of the handler mappings.
Now things start to get interesting. In the ordered list you’ll notice a bunch of SharePoint-y looking things on the top. This technet article has a pretty good table describing those feature page elements to help you understand what you’re looking at. To save you a click, here’s an excerpt:
Element Name | Description |
Name | Displays the name of the handler mapping. |
Path | Displays the file name or file name extension for which the handler processes a response. The value can be either a specific file name, such as WebResource.axd, or a wildcard (*) with a specific extension, such as *.exe. |
State | Displays whether the handler is enabled or disabled based on the access policy set in the Edit Feature Permissions dialog box and the required access setting that is specified by the handler mapping. If a handler requires a type of access that is not enabled in the access policy at that level, the handler is disabled. |
Path Type | Displays one of the following values for the type of path to which the handler is mapped:
|
Handler | Displays the module, such as IsapiModule, or managed type, such as System.Web.Handlers.TraceHandler, that responds to the request as specified in the mapping. |
Entry Type | Displays whether the item is local or inherited. Local items are read from the current configuration file, and inherited items are read from a parent configuration file. |
You’ll notice the SharePoint handlers show up as “Local” entry type, meaning they’re defined in the SharePoint app’s web.config instead of inherited from the inheritance chain. I won’t go into great detail on each of these SharePoint handlers & what it does – just know that they exist & their order is important.
Ok folks, now let’s have some fun with failed request tracing. Here’s the scenario: I’m trying to browse to my site & it doesn’t seem to be redirecting to home.aspx any more. What’s going on!? (ok, ok, I broke it intentionally, but bear with me for this demonstration). So let’s take a look at the IIS logs – I see my GET request for /, but it’s just returning a 404. Hmmm. Ready to get your hands dirty? Let’s set up a failed request tracing rule & see if we can find out what’s going on.
So back in IIS manager features view for your problem webapp, look for failed request tracing rules & open it up. Now, in the actions pane, click “edit site tracing” & make sure it’s enabled. Also note the directory path since that’s where we’ll go to view the logs. Next we need to add a rule.
I’m going to keep it simple & trace all content for this example. If I were troubleshooting an issue with Visio web drawings, for example (they have their own handler defined on the VisioWebAccess subdir – VwaHttpHandler), you may want to use a custom filter for *.vwd to eliminate most of the “noise” you might otherwise get with all content.
On the next page we’ll define the trace conditions. In this case I already know I’m getting a 404, so let’s just filter on that status code. Also note the other options – you can filter on time taken & event severity. Pretty cool stuff.
On the providers page, I'm just going to leave them all enabled, then click finish.
So now our rule is set up & failed request tracing is enabled on our website. Let’s repro the issue & take a look at the failed request log directory. If you’ve set up your rule correctly you should see an xml file there now with the naming convention fr000001.xml. Crack it open & take a look inside. Go to the request details tab & you should see something like this:
Wow, pretty cool, but what the heck am I looking for? Let’s do a search for “Handler_Changed” & see what handlers are being used for this request. Line 19 I see this:
Ok, so looks like we loaded the staticfile handler. This isn’t a SharePoint handler, so obviously it’s not going to be aware of the fact that SharePoint should be pulling home.aspx from the DB & not the file system. So let’s see what else we got. Search again & there’s one more handler_changed in the trace. Line 134 it looks like we switch from StaticFile to ISAPI-dll. Hmm, again, that’s not a SharePoint handler, so how does it know to get the page from the DB? It doesn’t…
Interesting, right? At this point we know we never loaded the SharePoint handler that’s responsible for redirecting to home.aspx & pulling it from the DB. So let’s set up a failed request tracing rule on a webapp where this actually works & see what’s different. I won’t step though the process of creating that rule because it’s essentially the same as what we did above, but instead of filtering on 404’s, let’s filter on the 302 redirect to home.aspx. Here’s our new rule on the working webapp:
Now let’s hit the working site in the browser, let it redirect to home.aspx, and crack open the resulting failed request tracing log file. Again, we want to search for “handler_changed”. Again, 2 matches. Line 19 we load the static file handler. So far, looks the same.
Now let's look at the second one:
Hey, look at that! On line 134 we ditch the staticFile handler & load up OwssvrHandler! That’s SharePoint! Sweet - there’s your difference, and there’s the handler responsible for pulling home.aspx from the DB. Pretty slick, right?
So now we know there’s probably something wrong with the OwssvrHandler on the broken site. Remember that the order of the handlers is important, so maybe someone messed with the ordered list & put static file above owssvrhandler? I know none of you would ever do that (RIGHT?!), but hey, it’s a possibility. So let’s compare the ordered list of handlers from my broken site (top) & working site (bottom).
Notice anything different? That’s right – OwssvrHandler should be at the top of the ordered list, but is missing entirely. And remember that it has an entry type of “local”, meaning that handler should be defined in my webapp’s web.config. Ok, Ok, you caught me – I flat out deleted this from my web.config:
<add name="OwssvrHandler" scriptProcessor="C:\Program Files\Common Files\Microsoft Shared\Web Server Extensions\14\isapi\owssvr.dll" path="/_vti_bin/owssvr.dll" verb="*" modules="IsapiModule" preCondition="integratedMode" />
HOPEFULLY you never encounter this situation, and if you do you likely have far worse problems than a single missing handler, but I hope this dramatization taught you a little something about how SharePoint handlers work & how you can apply IIS failed request tracing to your troubleshooting repertoire.
Until next time – happy troubleshooting!