How to Disable the ASP.NET v4.0 Extensionless URL feature on IIS 6.0


You can disable the v4.0 ASP.NET extensionless URL feature on IIS6 by setting a DWORD at HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\ASP.NET\4.0.30319.0\EnableExtensionlessUrls = 0.  After changing the value, you will need to restart IIS in order for us to pick up the change, because it is only read once when IIS starts.  Note that for Wow64 (i.e., 32-bit worker process running on 64-bit OS), this registry key must be set at HKEY_LOCAL_MACHINE\SOFTWARE\Wow6432Node\Microsoft\ASP.NET\4.0.30319.0\EnableExtensionlessUrls.

Here’s how the v4.0 ASP.NET extensionless URL features works on IIS 6.  We have an ISAPI Filter named aspnet_filter.dll that appends “/eurl.axd/GUID” to extensionless URLs.  This happens early on in the request processing.  We also have a script mapping so that “*.axd” requests are handled by our ISAPI, aspnet_isapi.dll.  When we append “/eurl.axd/GUID” to extensionless URLs, it causes them to be mapped to our aspnet_isapi.dll, as long as the script map exists as expected.  These requests then enter ASP.NET where we remove “/eurl.axd/GUID” from the URL, that is, we restore the original URL.  The restoration of the original URL happens very early.  Now the URL is extensionless again, and if no further changes are made and you’re using the default <httpHandlers> section in web.config, this will be assigned to the DefaultHttpHandler, since it has path=”*” and is the first handler to match the extensionless URL.  The DefaultHttpHandler will then redirect this request back to IIS, but this time our filter will not append “/eurl.axd/GUID” and the request will be handled as it would be normally.  To do anything interesting with the v4.0 ASP.NET extensionless URL feature, you must change the handler from DefaultHttpHandler to something else, before the MapRequestHandler event fires.

Note that v4.0 aspnet_filter.dll will only enable the extensionless URL feature (by appending eurl.axd to the URL) if the following are true:

  1. EnableExtensionlessUrls is not defined or has a value of 1.
  2. v4.0 aspnet_filter.dll is registered as an ISAPI Filter.
  3. v4.0 aspnet_isapi.dll is script mapped to “.axd” at the web site level (e.g. “/LM/W3SVC/N/ROOT”, where N is the siteID).
  4. v4.0 aspnet_isapi.dll is marked as “Allowed” in the ISAPI Restriction list.
  5. The web site has read and script permission enabled.

I’ve heard that it is not compatible with Ionics ISAPI Rewrite Filter, and it may not be compatible with other URL rewriting components.  Fortunately the ASP.NET feature is easy to disable.  By the way, the most common way for the ASP.NET extensionless URL feature to fail is for it to leave “/eurl.axd/GUID” on the URL.  This happens when our aspnet_filter appends “/eurl.axd/GUID”, but we fail to find the “*.axd” script map, and so the request is not mapped to aspnet_isapi.dll, and therefore never enters ASP.NET and we never restore the original URL.  As a result, you will receive a 404 response and the URL will have “/eurl.axd/GUID” appended.

Thanks,
Thomas

Comments (20)

  1. Ron says:

    Hi Thomas,

    Any suggestions.  I am having this problem with my site.  When trying to go to the site without the "www.", i get my error page bcz of the /eurl.axd/*guid* being appended.  But i am attempting this solution, and did an iisreset at the command line, and I am still having the problem.  I have EnableExtensionlessUrls set to zero?  Thanks,  Ron

  2. tmarq says:

    If you set EnableExtensionlessUrls = 0, and aspnet_filter.dll successfully read it, then it will not append /eurl.axd/GUID.  My guess is that you set the wrong registry key, or you've changed the IIS worker process identity and it does not have permission to read the registry key.  If you think it's a permission issue, then Process Monitor (technet.microsoft.com/…/bb896645.aspx) can be used to confirm this, but it's probably easier just to look at the ACLs on the registry key and ensure that the IIS worker process identity has read access.  It does by default, so if you haven't changed this, then you don't need to do anything.

    If you're not using ASP.NET v4, then you can change the Application Pool so that it does not load v4 CLR.  This will also prevent aspnet_filter.dll from appending /eurl.axd/GUID.

  3. Guilherme Melo says:

    How to disable this using web.config ?

    Thanks.

  4. tmarq says:

    It cannot be disabled via web.config.

  5. Matthijs Woolderink says:

    With the help of Process Monitor I found out that the setting on a 64bit server is located in the different part of the registry.

    So for a 64bit server the setting should be set here:

    HKEY_LOCAL_MACHINESoftwareWow6432NodeMicrosoftASP.NETv4.0.30319.0EnableExtensionlessUrls = 0

  6. Cradz says:

    Thank you.

    I had a mixture of 1.1, 2.0, and 4.0 sites in IIS and ALL would be down when the server restarted and this fixed it.

  7. Svante Seleborg says:

    This 'feature' is not compatible with the 'default content page' feature of IIS6 either. It will cause an extensionless request to enter ASP.NET twice – once with the proper rewrite to the default content page, and once with the original URL and handled by DefaultHttpHandler. If you in turn have added an event handler to for exampel EndRequest to set a Cookie, this will cause the infamous 'Server cannot modify cookies after HTTP headers have been sent.' HttpException.

  8. Cosmin Onea says:

    If I have a .net 4 web application using this feature under the default site and if the web site itself is running under .net 2.0 I always get a 404 – Not Found when I access the app.

    If I change the framework version to 4 on the web site everything works. Is this as expected or is it a bug?

  9. tmarq says:

    Cosmin, sorry you're having trouble with this.  In your case, the feature should work if the v4.0 aspnet_isapi.dll is script mapped to ".axd" at the web site level (e.g. "/LM/W3SVC/N/ROOT", where N is the siteID).  It is expected that all virtual paths below this are also using v4.0.  If you need to have v2.0 on the machine too, then ensure that it is script mapped at the web site level, and that all virtual paths below this are also using v2.0.  In other words, for things to work, you need to choose a version at the web site level (e.g. "/LM/W3SVC/N/ROOT", where N is the siteID), and ensure that all virtual paths below this are also using this same version.  Thanks, Thomas

  10. Kevin Jensen says:

    I was able to deploy properly but my app keeps trying to redirect on [Authorize] controllers to /Account/Login even though i'm using windows authentication as stated in my web.config

    Here is my web.config: http://pastie.org/1568510

  11. Bradley Cotier says:

    Hi

    I am having a problem with this concerning HTTP modules when hitting a IIS6 hosted website using a IWebProxy implementation.Pre-.NET4 any request to the website would result in the module being hit. It should be noted that I had a wildcard assigned to the website which invoked the v2 aspnet_isapi filter.

    However, upon deploying ASP.NET 4 and modifying the website to use .NET4, and also removing the wildcard mapping (as I understand I won't need it anymore), I am seeing that the http module is sometimes hit and sometimes isn't, as below. NB – all of these calls are using the IWebProxy implementation which sends the call to the website hosting the module:

    1) Browse to http://nonproxyurl/extensionlessurl – module is not hit

    2) Browse to http://nonproxyurl/something.mappedfileextension – module is hit

    3) Browse to http://nonproxyurl/something.unmappedfileextension – module is not hit

    4) Browse to http://proxyurl/extensionlessurl – module is hit

    5) Browse to http://proxyurl/something.mappedfileextension – module is hit

    6) Browse to http://proxyurl/something.unmappedfileextension – module is not hit

    The main inconsistency I see is between 1 and 4 where if the proxy website is hit directly with an extensionlessurl then it works but not if it is hit using a non-proxy url (remembering that ALL of these calls are using the IWebProxy implementation).

    My requirement is for ALL calls that are proxied to the website, regardless of whether or not a file extension is known or even present, to result in a hit to the http module. If this means shutting down all new functionality by some means then so be it but there are significant consequences for our project and customer if we can't upgrade the website to .NET 4. This is because all of the assemblies that the site relies on have have been upgraded to .NET4. i.e. – we would effectively have to move the entire code base back to .NET2 CLR if we can't get this to work.

    Many thanks for any help you can give.

    Brad

  12. Nicholas Piasecki says:

    It appears that any Windows Updates that service the .NET Framework 4.0 blow away this registry key.

  13. Vanadiumtech says:

    I ran into a similar issue with v4.0 ASP.Net extension less URL feature on II6 and found a solution through ISAPI Rewrite Module provider, the does not require turning it off.  Theissue and the solution as we experienced it is documented here http://www.vanadiumtech.com/…/Cause-of-eurlaxd.aspx

  14. Y Chan says:

    Is there a permanent fix so that Windows Updates do not blow away the registry key.  PS. We would rather not rely on ISAPI Rewrite solution.

  15. tmarq says:

    The servicing updates of .NET Framework 4.0 were deleting the EnableExtensionlessUrls registry setting, but that problem has been fixed in the later updates.  Unfortunately the earlier servicing updates have the problem, and so you will have to reset the registry key when one of those is installed.

  16. Akira says:

    Thank you, this helped me a lot since we use IIRF. We installed some Windows updates and don't know why this DWORD key was removed =(

    Best regards

  17. Puru says:

    I had similar issue and able resolve using above resolution. Many thanks!

  18. Kerry says:

    Thomas – thank you very much for this detailed explanation of (what I'd consider to be) obscure IIS behavior.  A very helpful post!  However, I have two questions…  

    First, it appears that extensionless URLs must be turned off in order for SQL Reporting Services (2005) to work properly.  However, I'd like to deploy an MVC3 app to the same server.  Is it possible to disable extensionless URLs for a particular website rather than the entire server?

    Second, with extensionless urls enabled (confirmed by hitting localhost/reports and being redirected to a GUID), are you aware of a (mis)configuration that would cause a 401.5 error "You do not have permission to view this directory or page using the credentials that you supplied because your Web browser is sending a WWW-Authenticate header field that the Web server is not configured to accept"?  My reading of the 401.5 is "Denied by custom ISAPI/CGI Web application".  Any guidance would be appreciated.

  19. tmarq says:

    Hi Kerry,

    The extensionless URL feature (EURL) on IIS 6.0 was done in order to enable extensionless URLs out of the box, without making any changes to .NET 4.0 setup.  It works with most applications, but when you run into trouble with it like you are, you obviously start thinking it is the worst thing ever. :)  I cannot argue with that, as it is painful to troubleshoot.

    To answer your questions, the feature can only be enabled/disabled for an entire application pool.  If you wanted it on for one website and off for another, you would have to use different application pools.  The ingredients to enable/disable the feature are mentioned in a list of 1 thru 5 items above, in my blog post.

    I don't recall hearing of an issue with SQL Reporting Services 2005 and EURL.  Does the EURL feature work for requests that are not made to SQL Reporting Services in that same application pool?  You should never be redirected to a GUID–that indicates EURL is not configured correctly or is incompatible with another ISAPI extension or filter that is installed on the box.  See the list above (in my blog post) for all the things that must be true for the feature to work.

    I do not know what is causing the 401.5 error.  Perhaps this KB is relevant:

        support.microsoft.com/…/906474

    There is an alternative way to enable extensionless URLs.  You can use an IIS wildcard mapping as described in the post here:

        haacked.com/…/asp.net-mvc-on-iis-6-walkthrough.aspx

    Be sure to disable EURL with the registry key if you decide to use a wildcard mapping instead.

    I hope the above helps, but if not, you might want to try one of the following web sites:

       http://stackoverflow.com/ – don’t even need to register to ask a question

       http://forums.iis.net/ – official IIS Forums

       http://forums.asp.net/ – official ASP.NET Forums

    By the way, I am no longer on the ASP.NET team, having moved to another team about two years ago.

    Best Regards,

    Thomas

  20. sanjay says:

    Hi Thomas,

    i am using IIS 7.5. The application (built using MVC) has a model form which opens fine most of the time. but when the page refreshes and user clicks on the link to open the pop up it gives error 404. its very intermittent

    Any idea what could be wrong?