我在Visual Studio 2012中的Cassini开发人员服务器中运行,我需要将客户端从旧版.asp
页面重定向到.aspx
页面。
注意:理想情况下,我会将客户端从.asp
重定向到友好 url,然后在内部重写以.aspx
POST /ResetClock.asp
HTTP/1.1 307 Temporary Redirect
Location: //stackoverflow.us/ResetClock
然后在内部:
POST /ResetClock
重写成/ResetClock.ashx
(是的,我把它改成了.ashx
;这就是url重写的优点(。
就像汉塞尔曼所做的那样
这很像斯科特·汉塞尔曼(Scott Hanselman(所做的:
- 请求
/foo.html
- 将客户端重定向到
/foo
- 客户端请求
/foo
- 被重写成
/foo.html
未遂的黑客攻击
我尝试了黑客解决方案;更改.asp
页面以强制重定向到.ashx
(并改天与 url 重写语法作斗争(:
重置时钟.asp
<%
Response.Redirect("ResetClock.aspx")
Response.End
%>
除了卡西尼号根本不提供.asp
页面:
不提供此类页面。
说明:系统不会投放您请求的网页类型,因为该网页已被明确禁止。 扩展名".asp"可能不正确。 请查看下面的 URL 并确保拼写正确。
请求的网址:/网站/获取时间.asp
这指向一个相关问题。我最终使用的解决方案不需要 IIS7.5 上尚不可用的任何内容。而且它不需要任何需要访问 IIS 管理工具的内容;并且必须完全存在于网站(例如web.config
(内。
问题
如何将.asp
重写为更 ASP.net 的东西?
编辑:将GET
改为POST
,以阻止那些想知道为什么307 Temporary Redirect
而不是302 Found
或303 See Other
的吹毛求疵者。
解决方案是创建一个IHttpModule
。HttpModules允许您拦截每个请求,并根据需要做出反应。
第一步是创建IHttpModule
的管道:
class UrlRewriting : IHttpModule
{
public void Init(HttpApplication application)
{
application.BeginRequest += new EventHandler(this.Application_BeginRequest);
application.EndRequest += new EventHandler(this.Application_EndRequest);
}
public void Dispose()
{
//Nothing to do here
}
private void Application_BeginRequest(object sender, EventArgs e)
{
HttpApplication application = (HttpApplication)sender;
HttpContext context = application.Context;
}
private void Application_EndRequest(object sender, EventArgs e)
{
}
}
然后在web.config
文件中注册我们的 HttpHandler:
web.config:
<configuration>
<system.web>
<httpModules>
<add name="UrlRewriting" type="UrlRewriting"/>
</httpModules>
</system.web>
</configuration>
现在我们有一个方法(Application_BeginRequest
(,每次发出请求时都会运行。
如果客户端要求 ASP 页,则发出客户端重定向
业务的首要任务是将客户端重定向到"干净">表单。例如,/File.asp
请求被重定向到/File
:
private void Application_BeginRequest(object sender, EventArgs e)
{
HttpApplication application = (HttpApplication)sender;
HttpContext context = application.Context;
//Redirct any requests to /File.asp into a /File
if (context.Request.Url.LocalPath == VirtualPathUtility.ToAbsolute("~/File.asp"))
{
//Be sure to issue a 307 Temporary Redirect in case the client issued a POST (i.e. a non-GET)
//If we issued 302 Found, a buggy client (e.g. Chrome, IE, Firefox) might convert the POST to a GET.
//If we issued 303 See Other, the client is required to convert a POST to a GET.
//If we issued 307 Temporary Redirect, the client is required to keep the POST method
context.Response.StatusCode = (int)HttpStatusCode.TemporaryRedirect;
context.Response.RedirectLocation = VirtualPathUtility.ToAbsolute("~/File");
context.Response.End();
}
}
然后内部重写
现在客户端将要求/File
,我们必须在内部将其重写为.aspx
,或者在我的情况下,.ashx
文件:
private void Application_BeginRequest(object sender, EventArgs e)
{
HttpApplication application = (HttpApplication)sender;
HttpContext context = application.Context;
//Redirct any requests to /ResetClock.asp into a /File
if (context.Request.Url.LocalPath == VirtualPathUtility.ToAbsolute("~/ResetClock.asp"))
{
//Be sure to issue a 307 Temporary Redirect in case the client issued a POST (i.e. a non-GET)
//If we issued 302 Found, the buggy client might convert the POST to a GET.
//If we issued 303 See Other, the client is required to convert a POST to a GET.
//If we issued 307 Temporary Redirect, the client is required to keep the POST method
context.Response.StatusCode = (int)HttpStatusCode.TemporaryRedirect;
context.Response.RedirectLocation = VirtualPathUtility.ToAbsolute("~/ResetClock");
context.Response.End();
}
//Rewrite clean url into actual handler
if (context.Request.Url.LocalPath == VirtualPathUtility.ToAbsolute("~/ResetClock"))
{
String path = "~/ResetClock.ashx"; //no need to map the path
context.Server.Execute(path, true);
//The other page has been executed
//Do not continue or we will hit the 404 of /ResetClock not being found
context.Response.End();
}
}
IIS 包含一些基本的 URL 重定向
从一些未知版本的IIS开始,他们添加了一种(现在被嘲笑的(URL重写形式。它不会发出客户端重定向,只会发出内部重写。但至少它可以用来解决我的问题(响应内容 ASP.net 的ASP页面(:
网络.config
<configuration>
<system.web>
<urlMappings>
<add url="~/ResetClock.asp" mappedUrl="~/ResetClock.ashx"/>
</urlMappings>
</system.web>
</configuration>
客户端似乎仍然在/ResetClock.asp
找到了资源,但响应的胆量将来自/ResetClock.ashx
。
注意:任何代码都会发布到公共领域。无需署名。