Normally i wouldn't put a title like this in the question, but i'm pretty sure it's a bug (or by design?)
通常情况下,我不会在问题中加上这样的标题,但我很确定这是一个bug(还是设计出来的?)
I created a brand new ASP.NET MVC 3 Web Application.
我创建了一个全新的ASP。NET MVC 3 Web应用程序。
Then i went to the /Home/About page.
然后我去了/Home/About页面。
The URL for this page is:
本页的网址是:
http://localhost:51419/Home/About
http://localhost:51419 / Home /
Then i changed the URL to this:
然后我将URL改为:
http://localhost:51419/(A(a))/Home/About
http://localhost:51419 /(())/ Home /
And the page worked? Looking at the route values, controller = Home, Action = About. It's ignored the first part?
和页面工作吗?查看路由值,controller = Home, Action = About。它忽略了第一部分?
And if i look at all the links in the source:
如果我看一下来源中的所有链接:
<link href="/(A(a))/Content/Site.css" rel="stylesheet" type="text/css" />
<script src="/(A(a))/Scripts/jquery-1.5.1.min.js" type="text/javascript"></script>
<script src="/(A(a))/Scripts/modernizr-1.7.min.js" type="text/javascript"></script>
<li><a href="/(A(a))/">Home</a></li>
<li><a href="/(A(a))/Home/About">About</a></li>
See how it's maintained that first part? It's like the routing engine thinks it's part of the domain or something?
看到第一部分是如何维护的了吗?就像路由引擎认为它是域的一部分?
I've got a feeling it's a regex thing, because if i change the URL to:
我觉得这是一个regex,因为如果我将URL更改为:
http://localhost:51419/(a(a))/Home/About
http://localhost:51419 /(())/ Home /
(E.g changed the uppercase A to lowercase)
(E。g将大写A改为小写)
It 404's.
它404年的。
Can anyone shed some light on this? Is this a bug or by design?
有人能解释一下吗?这是bug还是设计?
3 个解决方案
#1
5
This appears to be related to Cookieless Sessions in the ASP.NET pipeline. It strips that URL pattern inside CookielessHelper.cs (System.Web.Security) while processing the request:
这似乎与ASP中的无cookie会话有关。净管道。它将URL模式剥离到CookielessHelper中。cs (System.Web.Security)在处理请求时:
// This function is called for all requests -- it must be performant.
// In the common case (i.e. value not present in the URI, it must not
// look at the headers collection
internal void RemoveCookielessValuesFromPath()
{
// See if the path contains "/(XXXXX)/"
string path = _Context.Request.ClientFilePath.VirtualPathString;
// Optimize for the common case where there is no cookie
if (path.IndexOf('(') == -1) {
return;
}
int endPos = path.LastIndexOf(")/", StringComparison.Ordinal);
int startPos = (endPos > 2 ? path.LastIndexOf("/(", endPos - 1, endPos, StringComparison.Ordinal) : -1);
if (startPos < 0) // pattern not found: common case, exit immediately
return;
if (_Headers == null) // Header should always be processed first
GetCookielessValuesFromHeader();
// if the path contains a cookie, remove it
if (IsValidHeader(path, startPos + 2, endPos))
{
// only set _Headers if not already set
if (_Headers == null) {
_Headers = path.Substring(startPos + 2, endPos - startPos - 2);
}
// Rewrite the path
path = path.Substring(0, startPos) + path.Substring(endPos+1);
// remove cookie from ClientFilePath
_Context.Request.ClientFilePath = VirtualPath.CreateAbsolute(path);
// get and append query string to path if it exists
string rawUrl = _Context.Request.RawUrl;
int qsIndex = rawUrl.IndexOf('?');
if (qsIndex > -1) {
path = path + rawUrl.Substring(qsIndex);
}
// remove cookie from RawUrl
_Context.Request.RawUrl = path;
if (!String.IsNullOrEmpty(_Headers)) {
_Context.Request.ValidateCookielessHeaderIfRequiredByConfig(_Headers); // ensure that the path doesn't contain invalid chars
_Context.Response.SetAppPathModifier("(" + _Headers + ")");
// For Cassini and scenarios where aspnet_filter.dll is not used,
// HttpRequest.FilePath also needs to have the cookie removed.
string filePath = _Context.Request.FilePath;
string newFilePath = _Context.Response.RemoveAppPathModifier(filePath);
if (!Object.ReferenceEquals(filePath, newFilePath)) {
_Context.RewritePath(VirtualPath.CreateAbsolute(newFilePath),
_Context.Request.PathInfoObject,
null /*newQueryString*/,
false /*setClientFilePath*/);
}
}
}
}
Your pattern matches this:
你的模式匹配:
///////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////
// Make sure sub-string if of the pattern: A(XXXX)N(XXXXX)P(XXXXX) and so on.
static private bool IsValidHeader(string path, int startPos, int endPos)
{
if (endPos - startPos < 3) // Minimum len is "X()"
return false;
while (startPos <= endPos - 3) { // Each iteration deals with one "A(XXXX)" pattern
if (path[startPos] < 'A' || path[startPos] > 'Z') // Make sure pattern starts with a capital letter
return false;
if (path[startPos + 1] != '(') // Make sure next char is '('
return false;
startPos += 2;
bool found = false;
for (; startPos < endPos; startPos++) { // Find the ending ')'
if (path[startPos] == ')') { // found it!
startPos++; // Set position for the next pattern
found = true;
break; // Break out of this for-loop.
}
if (path[startPos] == '/') { // Can't contain path separaters
return false;
}
}
if (!found) {
return false; // Ending ')' not found!
}
}
if (startPos < endPos) // All chars consumed?
return false;
return true;
}
#2
0
You might want to try adding an IgnoreRoute
to your route mapping - but I admit I'm not sure what format to provide to match all your possible cookieless paths.
您可能想尝试在路由映射中添加一个IgnoreRoute—但是我承认我不确定要提供什么格式来匹配所有可能的无cookie路径。
#3
-1
I agree with @pjumble analysis, but not to his solution.
Disable cookieless authentication for either form authentication or anonymous authentication.
我同意@pjumble的分析,但不同意他的解决方案。对任何形式的身份验证或匿名身份验证禁用无cookie的身份验证。
This will prevent users with cookies disabled to authenticate. But who cares anyway, everyone nowdays have cookies activated as no modern website will work without.
这将防止禁用cookie的用户进行身份验证。但谁在乎呢,现在每个人都有cookies,因为没有任何一个现代网站可以运行。
Add in web.config:
在web . config中添加:
<anonymousIdentification enabled="false" />
<authentication mode="None" />
or
或
<anonymousIdentification enabled="true" cookieless="UseCookies" ... />
<authentication mode="Forms">
<forms name="Auth" cookieless="UseCookies" ... />
</authentication>
#1
5
This appears to be related to Cookieless Sessions in the ASP.NET pipeline. It strips that URL pattern inside CookielessHelper.cs (System.Web.Security) while processing the request:
这似乎与ASP中的无cookie会话有关。净管道。它将URL模式剥离到CookielessHelper中。cs (System.Web.Security)在处理请求时:
// This function is called for all requests -- it must be performant.
// In the common case (i.e. value not present in the URI, it must not
// look at the headers collection
internal void RemoveCookielessValuesFromPath()
{
// See if the path contains "/(XXXXX)/"
string path = _Context.Request.ClientFilePath.VirtualPathString;
// Optimize for the common case where there is no cookie
if (path.IndexOf('(') == -1) {
return;
}
int endPos = path.LastIndexOf(")/", StringComparison.Ordinal);
int startPos = (endPos > 2 ? path.LastIndexOf("/(", endPos - 1, endPos, StringComparison.Ordinal) : -1);
if (startPos < 0) // pattern not found: common case, exit immediately
return;
if (_Headers == null) // Header should always be processed first
GetCookielessValuesFromHeader();
// if the path contains a cookie, remove it
if (IsValidHeader(path, startPos + 2, endPos))
{
// only set _Headers if not already set
if (_Headers == null) {
_Headers = path.Substring(startPos + 2, endPos - startPos - 2);
}
// Rewrite the path
path = path.Substring(0, startPos) + path.Substring(endPos+1);
// remove cookie from ClientFilePath
_Context.Request.ClientFilePath = VirtualPath.CreateAbsolute(path);
// get and append query string to path if it exists
string rawUrl = _Context.Request.RawUrl;
int qsIndex = rawUrl.IndexOf('?');
if (qsIndex > -1) {
path = path + rawUrl.Substring(qsIndex);
}
// remove cookie from RawUrl
_Context.Request.RawUrl = path;
if (!String.IsNullOrEmpty(_Headers)) {
_Context.Request.ValidateCookielessHeaderIfRequiredByConfig(_Headers); // ensure that the path doesn't contain invalid chars
_Context.Response.SetAppPathModifier("(" + _Headers + ")");
// For Cassini and scenarios where aspnet_filter.dll is not used,
// HttpRequest.FilePath also needs to have the cookie removed.
string filePath = _Context.Request.FilePath;
string newFilePath = _Context.Response.RemoveAppPathModifier(filePath);
if (!Object.ReferenceEquals(filePath, newFilePath)) {
_Context.RewritePath(VirtualPath.CreateAbsolute(newFilePath),
_Context.Request.PathInfoObject,
null /*newQueryString*/,
false /*setClientFilePath*/);
}
}
}
}
Your pattern matches this:
你的模式匹配:
///////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////
// Make sure sub-string if of the pattern: A(XXXX)N(XXXXX)P(XXXXX) and so on.
static private bool IsValidHeader(string path, int startPos, int endPos)
{
if (endPos - startPos < 3) // Minimum len is "X()"
return false;
while (startPos <= endPos - 3) { // Each iteration deals with one "A(XXXX)" pattern
if (path[startPos] < 'A' || path[startPos] > 'Z') // Make sure pattern starts with a capital letter
return false;
if (path[startPos + 1] != '(') // Make sure next char is '('
return false;
startPos += 2;
bool found = false;
for (; startPos < endPos; startPos++) { // Find the ending ')'
if (path[startPos] == ')') { // found it!
startPos++; // Set position for the next pattern
found = true;
break; // Break out of this for-loop.
}
if (path[startPos] == '/') { // Can't contain path separaters
return false;
}
}
if (!found) {
return false; // Ending ')' not found!
}
}
if (startPos < endPos) // All chars consumed?
return false;
return true;
}
#2
0
You might want to try adding an IgnoreRoute
to your route mapping - but I admit I'm not sure what format to provide to match all your possible cookieless paths.
您可能想尝试在路由映射中添加一个IgnoreRoute—但是我承认我不确定要提供什么格式来匹配所有可能的无cookie路径。
#3
-1
I agree with @pjumble analysis, but not to his solution.
Disable cookieless authentication for either form authentication or anonymous authentication.
我同意@pjumble的分析,但不同意他的解决方案。对任何形式的身份验证或匿名身份验证禁用无cookie的身份验证。
This will prevent users with cookies disabled to authenticate. But who cares anyway, everyone nowdays have cookies activated as no modern website will work without.
这将防止禁用cookie的用户进行身份验证。但谁在乎呢,现在每个人都有cookies,因为没有任何一个现代网站可以运行。
Add in web.config:
在web . config中添加:
<anonymousIdentification enabled="false" />
<authentication mode="None" />
or
或
<anonymousIdentification enabled="true" cookieless="UseCookies" ... />
<authentication mode="Forms">
<forms name="Auth" cookieless="UseCookies" ... />
</authentication>