在ASP.NET MVC中使用SSL操作筛选器重定向循环

时间:2010-02-24 03:45:19

标签: asp.net-mvc ssl https action-filter

我正在使用ActionFilter(见下文)来检测当前控制器/操作是否需要SSL和2.当前正在使用SSL,并相应地重定向。

这在本地工作正常(在IIS 7中使用虚拟证书)但是一旦我在服务器上启动它,我会收到一个指示无限重定向循环的错误。

有什么想法吗?

 public class SslFilter : ActionFilterAttribute
{
    public SslFilter(bool sslRequired)
    {
        SslRequired = sslRequired;
    }

    public bool SslRequired { get; set; }


    public override void OnActionExecuting(ActionExecutingContext filterContext)
    {
        HttpRequestBase req = filterContext.HttpContext.Request;
        HttpResponseBase res = filterContext.HttpContext.Response;

        var builder = new UriBuilder(req.Url);

        if (SslRequired && !req.IsSecureConnection)
        {
            builder.Scheme = Uri.UriSchemeHttps;
            builder.Port = 443;
            res.Redirect(builder.Uri.ToString());

        }
        else if (!SslRequired && req.IsSecureConnection)
        {
            builder.Scheme = Uri.UriSchemeHttp;
            builder.Port = 80;
            res.Redirect(builder.Uri.ToString());
        }

        base.OnActionExecuting(filterContext);
    }
}

Firefox错误:

  

页面未正确重定向

     

Firefox已检测到该服务器   正在重定向此请求   以永远不会的方式解决   完整。

     

有时可能会导致此问题   通过禁用或拒绝接受   饼干。

3 个答案:

答案 0 :(得分:2)

尝试以更MVCish的方式重定向:

var builder = new UriBuilder(req.Url);

if (SslRequired && !req.IsSecureConnection)
{
    builder.Scheme = Uri.UriSchemeHttps;
    builder.Port = 443;
    filterContext.Result = new RedirectResult(builder.Uri.ToString());
    filterContext.Cancel = true;
}
else if (!SslRequired && req.IsSecureConnection)
{
    builder.Scheme = Uri.UriSchemeHttp;
    builder.Port = 80;
    filterContext.Result = new RedirectResult(builder.Uri.ToString());
    filterContext.Cancel = true;
}
else 
{
    base.OnActionExecuting(filterContext);
}

答案 1 :(得分:1)

我在我正在构建的网站上遇到同样的问题,并发现由于某种原因,它与网址中的端口号有关。所以,builder.Uri.ToString()正在输出http://domain.com:80/https://domain.com:443/,据我所知应该没问题,但我们切换到使用builder.Uri.AbsoluteUri并解决了这个问题。以下是我们代码的示例...

UriBuilder __urlBuilder = new UriBuilder(__context.Request.Url);
if (!HttpContext.Current.Request.Url.Scheme.Contains("https")) {
  if (this.Required == RequiredStates.Required) {
    __urlBuilder.Scheme = "https";
    __urlBuilder.Port = 443;
    HttpContext.Current.Response.Redirect(__urlBuilder.Uri.AbsoluteUri, true);
  }
}
else {
  if (this.Required == RequiredStates.NotRequired) {
    __urlBuilder.Scheme = "http";
    __urlBuilder.Port = 80;
    HttpContext.Current.Response.Redirect(__urlBuilder.Uri.AbsoluteUri, true);
  }
}

答案 2 :(得分:0)

请检查服务器上安装的证书。使用MS中的SSL配置工具来检测问题。很可能私人遗失了。