【发布时间】:2009-07-13 15:32:58
【问题描述】:
如何确定并强制用户仅使用 HTTPS 查看我的网站?我知道它可以通过 IIS 完成,但想知道它是如何以编程方式完成的。
【问题讨论】:
如何确定并强制用户仅使用 HTTPS 查看我的网站?我知道它可以通过 IIS 完成,但想知道它是如何以编程方式完成的。
【问题讨论】:
你可以这样写HttpModule:
/// <summary>
/// Used to correct non-secure requests to secure ones.
/// If the website backend requires of SSL use, the whole requests
/// should be secure.
/// </summary>
public class SecurityModule : IHttpModule
{
public void Dispose() { }
public void Init(HttpApplication application)
{
application.BeginRequest += new EventHandler(application_BeginRequest);
}
protected void application_BeginRequest(object sender, EventArgs e)
{
HttpApplication application = ((HttpApplication)(sender));
HttpRequest request = application.Request;
HttpResponse response = application.Response;
// if the secure connection is required for backend and the current
// request doesn't use SSL, redirecting the request to be secure
if ({use SSL} && !request.IsSecureConnection)
{
string absoluteUri = request.Url.AbsoluteUri;
response.Redirect(absoluteUri.Replace("http://", "https://"), true);
}
}
}
{use SSL} 是一个是否使用 SSL 的条件。
编辑:当然,不要忘记将模块定义添加到web.config:
<system.web>
<httpModules>
<!--Used to redirect all the unsecure connections to the secure ones if necessary-->
<add name="Security" type="{YourNamespace}.Handlers.SecurityModule, {YourAssembly}" />
...
</httpModules>
</system.web>
【讨论】:
system.webServer 下的集成模式配置,并将validation 标签的validateIntegratedModeConfiguration 属性设置为false(有关详细信息,请参阅this answer) .另外,如果你想使用 IIS Express 或 IIS 6 你应该注意this other answer
有点硬编码但直截了当!
if (!HttpContext.Current.Request.IsSecureConnection)
{
Response.Redirect("https://www.foo.com/foo/");
}
【讨论】:
您必须将其从 VB.NET 转换为 C#,但这是我在我的网站中使用的:
Imports System.Web.HttpContext
Public Shared Sub SetSSL(Optional ByVal bEnable As Boolean = False)
If bEnable Then
If Not Current.Request.IsSecureConnection Then
Dim strHTTPS As String = "https://www.mysite.com"
Current.Response.Clear()
Current.Response.Status = "301 Moved Permanently"
Current.Response.AddHeader("Location", strHTTPS & Current.Request.RawUrl)
Current.Response.End()
End If
Else
If Current.Request.IsSecureConnection Then
Dim strHTTP As String = "http://www.mysite.com"
Current.Response.Clear()
Current.Response.Status = "301 Moved Permanently"
Current.Response.AddHeader("Location", strHTTP & Current.Request.RawUrl)
Current.Response.End()
End If
End If
End Sub
它比其他一些技术需要更多的代码,但这是有原因的。此方法只会在它不在它应该处于的模式下时重定向。当它进行重定向时,它会执行 301(永久)重定向。这样做的好处是搜索引擎将遵循 301 重定向,这将防止它们将同一页面索引两次(在 http 和 https 模式下)的任何可能性。您可以将此与 Response.Redirect(302 临时重定向)的默认行为进行比较,例如,Google 不会以相同的方式处理。他们不会根据临时重定向更改索引。
因此,如果您在想要进行 SSL 加密的页面上,请这样称呼它:
设置SSL(真)
否则:
设置SSL(假)
如果您真的需要全局应用它,我会在 global.asax 的 Application_BeginRequest 中调用 SetSSL(True)。请注意,SSL 会减慢速度。出于这个原因,我在 http 和 https 之间切换时通常非常有选择性。事实上,在我开发的几十个站点中,只有两个在整个站点中使用 SSL。
【讨论】:
本文介绍了将请求移入和移出 SSL。有时您不希望用户在 SSL 中查看页面,因为它会为不需要保护的页面消耗 proc 周期。
http://weblogs.asp.net/kwarren/archive/2005/07/08/418541.aspx
【讨论】:
IIR 您可以检查域的请求 (HttpContext.Current.Request),然后您可以检查正在使用的协议(http、https、ftp 等)
【讨论】:
您还可以在 web.config 中的 system.webServer 标记下设置重写规则。例如:
<rewrite>
<rules>
<rule name="Redirect to HTTPS" stopProcessing="true">
<match url="(.*)" />
<conditions>
<add input="{HTTP_HOST}" matchType="Pattern" pattern="^localhost(:\d+)?$" negate="true" ignoreCase="true" />
<add input="{HTTP_HOST}" matchType="Pattern" pattern="^127\.0\.0\.1(:\d+)?$" negate="true" />
<add input="{HTTPS}" pattern="off" />
</conditions>
<action type="Redirect" url="https://{HTTP_HOST}/{R:1}" />
</rule>
</rules>
</rewrite>
【讨论】: