IIS把双恩codeD正斜杠在不同的网址上比它在后续请求的第一个请求 [英] IIS treats double-encoded forward slashes in URLs differently on the first request than it does on subsequent requests

查看:108
本文介绍了IIS把双恩codeD正斜杠在不同的网址上比它在后续请求的第一个请求的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

最近我的团队被要求实施的HttpModule一个ASP.NET MVC应用程序处理的双恩codeD网址上的IIS 7和.NET 3.5。下面是问题的症结所在:

我们有时会说有一个看上去像这样的双烯codeD斜线网址:

  http://www.example.com/%252fbar%5cbaz/foo
 

有其他的格式,我们必须处理为好,但他们都有一个共同点,他们有一个双连接codeD斜杠。

要解决这个问题,我们写了一个HTTP模块时,一个URL有双重连接codeD斜杠,只有行动,我们重定向到一个理智的URL。的细节并不重要,但有两个位,其

  1. 我们无法控制的事实,这些URL具有双恩codeD斜杠
  2. 在我们还没有ugpraded到.NET 4.0然而,也不是在眼前的地平线上。

下面的问题:

在IIS启动的第一个请求显示不同的URL比第二个请求呢。

如果我们从上面的例子中使用的URL,第一个请求到IIS看起来像:

http://www.example.com/bar/baz/foo

和第二个请求将如下所示:

http://www.example.com/%252fbar%5cbaz/foo

这是通过检查 Application.Request.Url.AbsolutePath 属性在调试完成。

下面是应该重现该问题的最小的code例子(创建一个新的MVC应用程序,并注册了以下HTTP模块):

 公共类ForwardSlashHttpModule:IHttpModule的
{
    内部IHttpApplication申请{搞定;组; }

    公共无效的Dispose()
    {
        应用= NULL;
    }

    公共无效的Ini​​t(HttpApplication的情况下)
    {
        初始化(新HttpApplicationAdapter(上下文));
    }

    内部空隙初始化(IHttpApplication上下文)
    {
        应用=背景;
        context.BeginRequest + = context_BeginRequest;
    }

    内部空隙context_BeginRequest(对象发件人,EventArgs的)
    {
        VAR URL = Application.Request.Url.AbsolutePath; //<  - 问题点
        //做的东西与地址在这里。
    }
}
 

然后,调用本地主机上的同一网址:

  http://www.example.com/%252fbar%5c/foo
 

  

注:确保在 context_BeginRequest 使该行前插入 Debugger.Launch()叫你马上就能看到它第一次启动IIS

当你执行的第一个请求,你应该看到:

http://example.com/bar/foo

在后续的请求,你应该看到:

http://example.com//bar/foo

我的问题是:这是在IIS中的错误?为什么叫时,它提供了不同的网址 Application.Request.Url.AbsolutePath 的第一次,但没有任何后续请求?

另外:不要紧,第一个请求是否是一个双连接codeD URL或没有,第二个请求总是会适当由IIS(或至少处理,在适当的处理双恩codeD斜线即可)。这是第一个要求就是这个问题。

更新

我尝试了几种不同的属性,看看如果在第一次请求有不同的值:

首先请求

 字符串U = Application.Request.Url.AbsoluteUri;
http://example.com/foo/baz/bar/
字符串x = Application.Request.Url.OriginalString;
http://example.com:80/foo/baz/bar
字符串Y = Application.Request.RawUrl;
/%2ffo /巴兹/条
布尔Z = Application.Request.Url.IsWellFormedOriginalString();
真正
 

唯一有趣的事情是, Application.Request.RawUrl 发出单一连接codeD正斜杠(%2F ),并将转换的EN codeD反斜杠(%5C )到forwardslash(虽然一切人这么做过也一样)。

RawUrl 仍是部分连接codeD上的第一个请求。

第二个请求

 字符串U = Application.Request.Url.AbsoluteUri;
http://example.com//foo/baz/bar
字符串x = Application.Request.Url.OriginalString;
http://example.com:80/%2ffoo/baz/bar
字符串Y = Application.Request.RawUrl;
/%2ffoo /巴兹/条
布尔Z = Application.Request.Url.IsWellFormedOriginalString();
假
 

这是第二个请求有趣的点:

  • IsWellFormedOriginalString()。在第一个要求是
  • 的RawUrl是相同的(可能有用)。
  • 绝对URI 是不同的。在第二次请求,它有两个正斜杠。

更新

  Application.Request.ServerVariables [网址] = /报价/ GC / V12 / CMX
Application.Request.ServerVariables [CACHE_URL] = http://example.com:80/%2ffoo/baz/bar
 

开放题

  • 这似乎是在IIS或.NET的错误。是吗?
  • 第一个的请求后,由申请这只影响了 IISRESET
  • 除了使用RawUrl(因为我们不得不担心很多其他的问题,如果我们分析的原始地址,而不是使用.NET提供了'安全'的网址),还有什么其他的方法有哪些让我们来处理这个?

请注意,该问题的物理冲击低:对于它是一个实际的问题,第一个请求从客户端的web服务器将必须是针对上述特定URL,这种事情发生的几率相对较低。

解决方案

Request.Url可德$ C $早已CD - 我不相信它为你在做什么

请参阅内部细节处: <一href="http://stackoverflow.com/questions/3986736/querystring-with-url-en$c$cd-ampersand-$p$pmaturely-de$c$cd-within-request-url">Querystring与URL-EN codeD符号prematurely德$ C $内Request.Url

CD

该解决方案是直接通过Request.RawUrl访问值

我知道你的概率与路径,但似乎同样的事情是怎么回事。请尝试RawUrl - 看看它是否适合你,而不是

Recently my team was asked to implement an HttpModule for an ASP.NET MVC application that handled double-encoded URLs on IIS 7 and .NET 3.5. Here's the crux of the problem:

We sometimes get URLs that have double-encoded forward slashes that look like so:

http://www.example.com/%252fbar%5cbaz/foo

There are other formats that we have to handle as well, but they all have something in common, they have a double-encoded forward slash.

To fix this, we wrote an HttpModule that only acts when a URL has a double encoded forward slash, and we redirect it to a sane URL. The details aren't important, but there are two bits that are:

  1. We can't control the fact that these URLs have double-encoded forward slashes
  2. And we have not ugpraded to .NET 4.0 yet, nor is it on the immediate horizon.

Here's the problem:

The first request after IIS starts up shows a different URL than the second request does.

If we used the URL from the above example, the first request to IIS would look like:

http://www.example.com/bar/baz/foo

and the second request would look like:

http://www.example.com/%252fbar%5cbaz/foo

This was done by inspecting the Application.Request.Url.AbsolutePath property while debugging.

Here's the smallest code example that should reproduce the problem (create a new MVC application, and register the following HttpModule):

public class ForwardSlashHttpModule : IHttpModule
{
    internal IHttpApplication Application { get; set; }

    public void Dispose()
    {
        Application = null;
    }

    public void Init(HttpApplication context)
    {
        Initialize(new HttpApplicationAdapter(context));
    }

    internal void Initialize(IHttpApplication context)
    {
        Application = context;
        context.BeginRequest += context_BeginRequest;
    }

    internal void context_BeginRequest(object sender, EventArgs e)
    {
        var url = Application.Request.Url.AbsolutePath; //<-- Problem point
        //Do stuff with Url here.
    }
}

Then, call the same URL on localhost:

http://www.example.com/%252fbar%5c/foo

NB: Make sure to insert a Debugger.Launch() call before the line in context_BeginRequest so that you'll be able to see it the first time IIS launches

When you execute the first request, you should see:

http://example.com/bar/foo

on subsequent requests, you should see:

http://example.com//bar/foo.

My question is: Is this a bug in IIS? Why does it provide different URLs when calling Application.Request.Url.AbsolutePath the first time, but not for any subsequent request?

Also: It doesn't matter whether the first request is for a double encoded URL or not, the second request will always be handled appropriately by IIS (or at least, as appropriate as handling double-encoded forward slashes can be). It's that very first request that is the problem.

Update

I tried a few different properties to see if one had different values on the first request:

First Request

string u = Application.Request.Url.AbsoluteUri;
"http://example.com/foo/baz/bar/"
string x = Application.Request.Url.OriginalString;
"http://example.com:80/foo/baz/bar"
string y = Application.Request.RawUrl;
"/%2ffo/baz/bar"
bool z = Application.Request.Url.IsWellFormedOriginalString();
true

The only interesting thing is that the Application.Request.RawUrl emits a single-encoded Forward slash (%2f), and translates the encoded backslash (%5c) to a forwardslash (although everything else does that as well).

The RawUrl is still partially encoded on the first request.

Second Request

string u = Application.Request.Url.AbsoluteUri;
"http://example.com//foo/baz/bar"
string x = Application.Request.Url.OriginalString;
"http://example.com:80/%2ffoo/baz/bar"
string y = Application.Request.RawUrl;
"/%2ffoo/baz/bar"
bool z = Application.Request.Url.IsWellFormedOriginalString();
false

Interesting points from the second request:

  • IsWellFormedOriginalString() is false. On the first request it was true.
  • The RawUrl is the same (potentially helpful).
  • The AbsoluteUri is different. On the second request, it has two forward slashes.

Update

Application.Request.ServerVariables["URL"] = /quotes/gc/v12/CMX
Application.Request.ServerVariables["CACHE_URL"] = http://example.com:80/%2ffoo/baz/bar

Open Questions

  • This seems like a bug in either IIS or .NET. Is it?
  • This only matters for the very first request made by an application after an iisreset
  • Besides using RawUrl (as we'd have to worry about a lot of other problems if we parsed the Raw Url instead of using the 'safe' URL provided by .NET), what other methods are there for us to handle this?

Keep in mind, the physical impact of this problem is low: For it to be an actual problem, the first request to the web server from a client would have to be for the above specific URL, and the chances of that happening are relatively low.

解决方案

Request.Url can be decoded already - I wouldn't trust it for what you are doing.

See the internal details at: Querystring with url-encoded ampersand prematurely decoded within Request.Url

The solution is to access the values directly via Request.RawUrl.

I realize your prob is with the path, but it seems the same thing is going on. Try the RawUrl - see if it works for you instead.

这篇关于IIS把双恩codeD正斜杠在不同的网址上比它在后续请求的第一个请求的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆