19

I have a MVC.NET application with one route as follows:

routes.MapRoute("member", "member/{id}/{*name}", new { controller = "member", action = "Details", id = "" }, new { id = @"\d+" });

Thus, a link could be something like this: http://domain/member/123/any_kind_of_username

This works fine in general but if the path contains illegal characters (e.g. a double qoute: http://domain/member/123/my_"user"_name) I get a "System.ArgumentException: Illegal characters in path."

After much googling the best suggestions seems to be to make sure that the url doesn't contain any such characters. Unfortunately, that is out of my control in this case.

Is there a way to work around this?

hbruce
  • 934
  • 4
  • 11
  • 21
  • 2
    presumably they are called illegal characters because you can't use them... – Mitch Wheat Jan 18 '10 at 15:53
  • 1
    @Mitch - Well, a double quote, for example, works fine for Apache so I can't see why IIS wouldn't allow it. @Oded - The problem is that I'm not in control of these urls. – hbruce Jan 18 '10 at 16:02

4 Answers4

10

Scott Hanselman posted a good summary on allowing illegal characters in the path.

If you really want to allow characters that are restricted, remove them from the list by editing your web.config (this will probably only work in .NET 4 and on IIS7):

<system.web>
    <httpRuntime requestValidationMode="2.0" relaxedUrlToFileSystemMapping="true" requestPathInvalidCharacters="&lt;,&gt;,*,%,:,&amp;,\" />
</system.web>

You may also need to do as hbruce suggests:

<system.webServer>
    <security>
        <requestFiltering allowDoubleEscaping="true"/>
    </security>
</system.webServer>

There are still some certain paths that will not work, (such as /search/% ) as you will get the 400 "Bad Request - Invalid URL" message. The only workaround I've found is to use that part as a querystring: /search?q=% with the above steps.

Community
  • 1
  • 1
bkaid
  • 51,465
  • 22
  • 112
  • 128
4

Turns out you could avoid this by setting allowDoubleEscaping="false" in for requestFiltering in web.Config. I.e:

<configuration>
  <system.webServer>
    <security>
      <requestFiltering allowDoubleEscaping="false" />
    </security>
  </system.webServer>
</configuration>

Perhaps not the perfect solution (any suggestions for a better one is much appreciated), but it solves the problem.

hbruce
  • 934
  • 4
  • 11
  • 21
  • 1
    fairly serious side-effect -- you can no longer use characters like `+` in URLs if you enable this setting. see: http://stackoverflow.com/questions/1453218/is-enabling-double-escaping-dangerous – Jeff Atwood Apr 28 '10 at 13:10
0

You should URL-encode the URL at the client end before submitting it. Try using the UrlHelper.Encode method.

Vince Bowdren
  • 8,326
  • 3
  • 31
  • 56
  • 1
    Sorry, same thing here as with the other suggestions so far. I'm afraid I'm not in control of the urls at the clients end. – hbruce Jan 19 '10 at 07:17
  • 3
    I'm getting that even when encoded URI is sent from client – IsmailS Jul 21 '15 at 13:17
  • "suggestions seems to be to make sure that the url doesn't contain any such characters. Unfortunately, that is out of my control in this case." – Chris Moschini Jun 30 '18 at 13:59
-1

What about an ampersand (&) in the url? For example: mysite.com/JellyBeans/PB&J, where "PB&J" is a parameter value in a controller action method. How do you get around MVC and the ASP.NET engine from treating that as an illegal char in the base url string? Encoding that with a %26 doesn't appear to work. Odd thing, when launching VS debug the local web server (VS built in web server) handles that case fine (both as an & and a %26), but when deployed to a web server running IIS7 the url results in a "Bad Request".

Justin Schwartzenberger
  • 2,576
  • 2
  • 17
  • 20
  • 2
    The VS.NET builtin webserver is quite buggy and non-standards compliant. If you run into any odd behavior, you're best off ignoring it and just using IIS. – Eamon Nerbonne Oct 12 '10 at 07:30
  • This is a follow-up question best posted as a new question and if linked here, linked in a comment, not an Answer. In this case it's likely already been asked, so finding the existing Question is best instead of asking again. – Chris Moschini Jun 30 '18 at 11:16