我已经阅读了很多关于ASP.NET MVC [RequireHttps]
的问题 - 但找不到这个问题的答案:
如果将[RequireHttps]
属性设置为https(如果不是https),如何将public ActionResult DoSomething()
{
return View("AnotherAction");
}
[RequireHttps]
public ActionResult AnotherAction()
{
return View();
}
属性切换为https?
我有这段代码:
[RequireSsl(Redirect = true)]
但是我收到一条错误消息:“所请求的资源只能通过SSL访问。”
MVC期货项目具有类似的属性DoSomething()
。但现在已经过时了... MVC 2中的等价物是什么?
如果有人在网址http://example.com/home/dosomething或网址http://example.com/home/anotheraction中输入内容,我需要将其自动重定向到网址 s :// example@home / anotheraction
编辑这是一系列事件:
从其他网站调用网址http://example.com/home/dosomething。他们将用户重定向到此网址(使用response.redirect或类似网址)。
AnotherAction()
然后尝试返回{{1}},但失败并显示错误消息“只能通过SSL访问所请求的资源。”
答案 0 :(得分:21)
RequiresHttps
属性会自动尝试重定向到https://your-url
。我在使用该属性的网站上验证了此行为,并查看了Reflector中的代码:
protected virtual void HandleNonHttpsRequest(AuthorizationContext filterContext)
{
if (!string.Equals(filterContext.HttpContext.Request.HttpMethod, "GET", StringComparison.OrdinalIgnoreCase))
{
throw new InvalidOperationException(MvcResources.RequireHttpsAttribute_MustUseSsl);
}
string url = "https://" + filterContext.HttpContext.Request.Url.Host + filterContext.HttpContext.Request.RawUrl;
filterContext.Result = new RedirectResult(url);
}
您确定要将您的网站设置为接受安全连接吗?如果您尝试直接浏览https://your-url
会怎样?
答案 1 :(得分:14)
[mvc 4]简答:
protected void Application_BeginRequest(Object source, EventArgs e)
{
if (!Context.Request.IsSecureConnection)
{
Response.Redirect(Request.Url.AbsoluteUri.Replace("http://", "https://"));
}
}
更长的回答:
要从http移动到https,你不能在第一个数据包后发送重定向到https,
因此,您需要使用Application_BeginRequest来捕获数据包,
从Global.asax添加函数,它将覆盖默认值,
代码应该是这样的(类级别的Global.asax):
protected void Application_BeginRequest(Object source, EventArgs e)
{
if (!Context.Request.IsSecureConnection &&
!Request.Url.Host.Contains("localhost") &&
Request.Url.AbsolutePath.Contains("SGAccount/Login"))
{
Response.Redirect(Request.Url.AbsoluteUri.Replace("http://", "https://"));
}
}
我强烈建议设置一个断点并检查Request.Url对象是否有任何与网址相关的需求
或者访问msdn page混淆request.url absoluteuri vs originalalstring?
所以我可以去dotnetperls 举例
此功能使您可以在localhost上进行开发并按原样部署代码
现在,对于要进行https重定向的每个页面,您需要在if条件中指定它
要从https移动到http,您可以使用常规的Response.Redirect,如下所示:
if (Request.Url.Scheme.Contains("https"))
{
Response.Redirect(string.Format("http://{0}", Request.Url.Authority), true);
}
请注意,这也支持在本地主机上进行开发时使用相同的代码,而不会在https添加之前中断原始过程。
我还建议考虑实现一些返回网址约定(如果尚未实现),那么你应该这样做:
if (Request.Url.Scheme.Contains("https"))
{
Response.Redirect(string.Format("http://{0}{1}", Request.Url.Authority, returnUrl), true);
}
这将在登录后重定向到请求的页面。
当然,您应该保护每个显示用户数据,注册,登录等的页面。
答案 2 :(得分:3)
Http HEAD 请求似乎未被重定向。在查看我们的错误日志时,我们看到了很多这样的消息,谷歌在这里搜索,但在仔细查看细节后,他们有一些有趣的“功能”
换句话说,所有失败的尝试都不是面向客户......
(100%赞成来自@ arserbin3的评论让我意识到他们都是 HEAD 请求)
答案 3 :(得分:2)
MVC4现在重定向
但不是你期望的。
http://www.example.com:8080/alpha/bravo/charlie?q=quux 将客户端的浏览器重定向到 https://www.example.com/alpha/bravo/charlie?q=quux
请注意缺少端口号。
http://aspnetwebstack.codeplex.com/SourceControl/latest#test/System.Web.Mvc.Test/Test/RequireHttpsAttributeTest.cs 代码测试 [事实] public void OnAuthorizationRedirectsIfRequestIsNotSecureAndMethodIsGet()
确认这是理想的行为。
如果您想编写包含PORT的自定义属性...您可以将代码基于:
http://aspnetwebstack.codeplex.com/SourceControl/latest#src/System.Web.Mvc/RequireHttpsAttribute.cs
[AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, Inherited = true, AllowMultiple = false)]
public class RequireHttpsAttribute : FilterAttribute, IAuthorizationFilter
{
public RequireHttpsAttribute()
: this(permanent: false)
{
}
/// <summary>
/// Initializes a new instance of the <see cref="RequireHttpsAttribute"/> class.
/// </summary>
/// <param name="permanent">Whether the redirect to HTTPS should be a permanent redirect.</param>
public RequireHttpsAttribute(bool permanent)
{
this.Permanent = permanent;
}
/// <summary>
/// Gets a value indicating whether the redirect to HTTPS should be a permanent redirect.
/// </summary>
public bool Permanent { get; private set; }
public virtual void OnAuthorization(AuthorizationContext filterContext)
{
if (filterContext == null)
{
throw new ArgumentNullException("filterContext");
}
if (!filterContext.HttpContext.Request.IsSecureConnection)
{
HandleNonHttpsRequest(filterContext);
}
}
protected virtual void HandleNonHttpsRequest(AuthorizationContext filterContext)
{
// only redirect for GET requests, otherwise the browser might not propagate the verb and request
// body correctly.
if (!String.Equals(filterContext.HttpContext.Request.HttpMethod, "GET", StringComparison.OrdinalIgnoreCase))
{
throw new InvalidOperationException(MvcResources.RequireHttpsAttribute_MustUseSsl);
}
// redirect to HTTPS version of page
string url = "https://" + filterContext.HttpContext.Request.Url.Host + filterContext.HttpContext.Request.RawUrl;
filterContext.Result = new RedirectResult(url, this.Permanent);
}
}
答案 4 :(得分:0)
为了补充已经给出的答案,这是来自HandleNonHttpsRequest的MVC 5实现的代码
protected virtual void HandleNonHttpsRequest(AuthorizationContext filterContext)
{
// only redirect for GET requests, otherwise the browser might not propagate the verb and request
// body correctly.
...
}