来自 ASP.NET MVC 应用程序的重定向不正确 URL 重写
Incorrect redirect from ASP.NET MVC application under URL Rewrite
我在IIS下配置网站:
http://main.domain.com
网站(ASP.NET MVC 5 应用程序,网站绑定到指定主机,端口 80)
- 默认网站绑定到 :80 并启用 ARR/URL 重写模块
在 DNS 设置中指定了通配符绑定 *.domain.com
。
期望的行为是将 http://main.domain.com
作为入口点和一组动态用户子域,如 http://user1.domain.com
、http://user2.domain.com
等
现在使用 link 模拟此行为,例如 http://main.domain.com/user/user1
我已经为 main.domain.com
设置了 URL 重写规则,如下所示:
<rule name="user-redirection" enabled="true" stopProcessing="true">
<match url="^.*$" />
<conditions logicalGrouping="MatchAll" trackAllCaptures="true">
<add input="{HTTP_HOST}" pattern="^([\w\d-]+)\.domain\.com$" />
</conditions>
<action type="Rewrite" url="http://main.domain.com/user/{C:1}/{R:0}" logRewrittenUrl="true" />
</rule>
这里一切正常 - 我可以看到 http://user1.domain.com
的工作方式与之前的 http://main.domain.com/user/user1
一样。
然后我尝试重新实现一个检查指定用户在数据库中是否存在的逻辑。例如,当 user47 不存在时 - 打开 http://main.domain.com/user/user47
link 会导致重定向到 http://main.domain.com
入口点。
在代码端,它是通过将自定义过滤器属性添加到实现所需条件重定向的控制器操作来完成的。我有下一个代码:
public class UserController : Controller {
[CustomRedirectBehavior]
public ActionResult Index()
{
...
}
}
public class CustomRedirectBehaviorAttribute : ActionFilterAttribute {
public override void OnActionExecuting(ActionExecutingContext filterContext)
{
base.OnActionExecuting(filterContext);
...
if (redirectingCondition) {
filterContext.Result = new RedirectResult("http://main.domain.com");
}
}
}
这里....我在浏览器中收到循环重定向错误!可以肯定的是 - 我已经仔细检查了这种行为:
- 当我打开
http://main.domain.com/user/user47
时,我被正确地重定向到 http://main.domain.com
- 当我打开
http://user47.domain.com/
时出现循环重定向错误。
然后为了调查问题,我将重定向回调修改为:
filterContext.Result = new RedirectResult("http://someotherdomain.com/some/other/path");
还有....我可以看到:
- 当我打开
http://main.domain.com/user/user47
时,我被正确地重定向到 http://someotherdomain.com/some/other/path
- 当我打开
http://user47.domain.com/
时,我被重定向到 http://user47.domain.com/some/other/path
!!! (是的,这不是打字错误,我也仔细检查了这种行为)
所以。我需要一个关于如何解决这个问题的想法
我已尝试重现您的情况,看来您确实遇到了重定向循环。所以我在模式中添加了一个否定前瞻组 ((?!main)
),它对我有用。这是我的 web.config 的样子:
<rule name="user-redirection" enabled="true" stopProcessing="true">
<match url="^.*$" />
<conditions logicalGrouping="MatchAll" trackAllCaptures="true">
<add input="{HTTP_HOST}" pattern="^(?!main)([\w\d-]+)\.domain\.com$" />
</conditions>
<action type="Rewrite" url="http://main.domain.com/user/{C:1}" logRewrittenUrl="true" />
</rule>
为了调查您的问题,我尝试了:
- 禁用浏览器缓存。如果您的浏览器使用缓存,您可能看不到您所做的每项规则更改。
- 将操作类型更改为 "Redirect" 而不是 "Rewrite" 并观察 "Developer tools (F12)" 中 "Network" 选项卡中发生的情况。
例如
<action type="Redirect" ...
嗯...终于找到答案了
问题来自正在安装的 应用程序请求路由 (ARR) 模块,以便使用自定义子域进行重写。
在服务器代理设置[=19=中启用代理后,反向重写主机响应headers选项默认设置为真] 区域。禁用此设置会使重定向在 subdomain-based 重写下正常工作。
我在IIS下配置网站:
http://main.domain.com
网站(ASP.NET MVC 5 应用程序,网站绑定到指定主机,端口 80)- 默认网站绑定到 :80 并启用 ARR/URL 重写模块
在 DNS 设置中指定了通配符绑定 *.domain.com
。
期望的行为是将 http://main.domain.com
作为入口点和一组动态用户子域,如 http://user1.domain.com
、http://user2.domain.com
等
现在使用 link 模拟此行为,例如 http://main.domain.com/user/user1
我已经为 main.domain.com
设置了 URL 重写规则,如下所示:
<rule name="user-redirection" enabled="true" stopProcessing="true">
<match url="^.*$" />
<conditions logicalGrouping="MatchAll" trackAllCaptures="true">
<add input="{HTTP_HOST}" pattern="^([\w\d-]+)\.domain\.com$" />
</conditions>
<action type="Rewrite" url="http://main.domain.com/user/{C:1}/{R:0}" logRewrittenUrl="true" />
</rule>
这里一切正常 - 我可以看到 http://user1.domain.com
的工作方式与之前的 http://main.domain.com/user/user1
一样。
然后我尝试重新实现一个检查指定用户在数据库中是否存在的逻辑。例如,当 user47 不存在时 - 打开 http://main.domain.com/user/user47
link 会导致重定向到 http://main.domain.com
入口点。
在代码端,它是通过将自定义过滤器属性添加到实现所需条件重定向的控制器操作来完成的。我有下一个代码:
public class UserController : Controller {
[CustomRedirectBehavior]
public ActionResult Index()
{
...
}
}
public class CustomRedirectBehaviorAttribute : ActionFilterAttribute {
public override void OnActionExecuting(ActionExecutingContext filterContext)
{
base.OnActionExecuting(filterContext);
...
if (redirectingCondition) {
filterContext.Result = new RedirectResult("http://main.domain.com");
}
}
}
这里....我在浏览器中收到循环重定向错误!可以肯定的是 - 我已经仔细检查了这种行为:
- 当我打开
http://main.domain.com/user/user47
时,我被正确地重定向到http://main.domain.com
- 当我打开
http://user47.domain.com/
时出现循环重定向错误。
然后为了调查问题,我将重定向回调修改为:
filterContext.Result = new RedirectResult("http://someotherdomain.com/some/other/path");
还有....我可以看到:
- 当我打开
http://main.domain.com/user/user47
时,我被正确地重定向到http://someotherdomain.com/some/other/path
- 当我打开
http://user47.domain.com/
时,我被重定向到http://user47.domain.com/some/other/path
!!! (是的,这不是打字错误,我也仔细检查了这种行为)
所以。我需要一个关于如何解决这个问题的想法
我已尝试重现您的情况,看来您确实遇到了重定向循环。所以我在模式中添加了一个否定前瞻组 ((?!main)
),它对我有用。这是我的 web.config 的样子:
<rule name="user-redirection" enabled="true" stopProcessing="true">
<match url="^.*$" />
<conditions logicalGrouping="MatchAll" trackAllCaptures="true">
<add input="{HTTP_HOST}" pattern="^(?!main)([\w\d-]+)\.domain\.com$" />
</conditions>
<action type="Rewrite" url="http://main.domain.com/user/{C:1}" logRewrittenUrl="true" />
</rule>
为了调查您的问题,我尝试了:
- 禁用浏览器缓存。如果您的浏览器使用缓存,您可能看不到您所做的每项规则更改。
- 将操作类型更改为 "Redirect" 而不是 "Rewrite" 并观察 "Developer tools (F12)" 中 "Network" 选项卡中发生的情况。
例如
<action type="Redirect" ...
嗯...终于找到答案了
问题来自正在安装的 应用程序请求路由 (ARR) 模块,以便使用自定义子域进行重写。
在服务器代理设置[=19=中启用代理后,反向重写主机响应headers选项默认设置为真] 区域。禁用此设置会使重定向在 subdomain-based 重写下正常工作。