【问题标题】:Enforce https on one controller and http on the other在一个控制器上强制执行 https,在另一个控制器上强制执行 http
【发布时间】:2018-08-19 10:38:33
【问题描述】:

我正在使用 ASP.NET 核心 2.1, 我正在寻找一种在一个控制器上强制执行 https 并在另一个控制器上强制执行 http 的方法。

以下文档显示了如何为整个 ASP.NET 核心强制实施 HTTPS,而不是对单个控制器强制实施 HTTPS。

https://docs.microsoft.com/en-us/aspnet/core/security/enforcing-ssl?view=aspnetcore-2.1&tabs=visual-studio

【问题讨论】:

    标签: asp.net-core asp.net-core-webapi


    【解决方案1】:

    一种方法是使用两种操作过滤器:一种用于强制执行 HTTPS 重定向,另一种用于允许 HTTP 请求。第一个将在全球范围内注册,第二个仅用于您希望允许 HTTP 流量的控制器/操作。举个例子:

    [AllowHttp]
    public class HomeController : Controller
    

    其中AllowHttp定义为:

    [AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, AllowMultiple = false)]
    // Inheriting from ActionFilterAttribute allows this to show
    // up in the ActionExecutingContext.Filters collection.
    // See the global filter's implementation.
    public class AllowHttpAttribute : ActionFilterAttribute
    {
    }
    

    接下来,全局过滤器:

    // Needed for the GetEncodedUrl() extension method.
    using Microsoft.AspNetCore.Http.Extensions;
    
    public class RedirectToHttpsActionFilter : ActionFilterAttribute
    {
        public override void OnActionExecuting(ActionExecutingContext context)
        {
            if (context.Filters.Any(x => x is AllowHttpAttribute))
            {
                return;
            }
    
            if (!context.HttpContext.Request.IsHttps)
            {
                var insecureUri = context.HttpContext.Request.GetEncodedUrl();
                var secureUri = insecureUri.Replace("http://", "https://");
    
                // As you're likely trying this out locally, you'll need to specify
                // the port to redirect to as well. You won't need this on production.
                // Change the first port to your HTTP port and the second to your HTTPS port.
                secureUri = secureUri.Replace(":49834", ":44329");
    
                context.Result = new RedirectResult(secureUri);
            }
        }
    }
    

    最后,您必须在 Startup.cs 中全局注册过滤器:

    services.AddMvc(options =>
    {
        options.Filters.Add(new RedirectToHttpsActionFilter());
    });
    

    我相信您可以通过 URL 重写来实现相同的效果,但是在您可能更改控制器路由的情况下,这将继续工作而无需干预。

    【讨论】:

    • 谢谢,我还以为asp.net core内置了更直接的方法。关于“全局过滤器”,它是我需要在项目中制作的常规课程吗?
    • @Dror 不客气,没错。为它创建一个新类。 ActionFilterAttribute 位于 Microsoft.AspNetCore.Mvc.Filters 命名空间中。
    • Gotcha,不能真正在本地测试它,因为在 IIS express 上它在任何情况下都使用 HTTP。我可以在本地忽略此过滤器吗?另一方面,在生产中它似乎确实有效!
    • @Dror 实际上是个好问题,但也许最好的方法是为 IIS Express 启用 SSL。这样,您就可以在更接近生产的环境中工作。如果您转到 Web 项目的属性 -> 调试 -> Web 服务器设置 -> 启用 SSL,那应该会为您完成。不过,您需要在本地包含端口重定向。
    • @Dror 其实我刚刚发现可以通过ConfigureServices方法获取环境,在开发环境中避免注册过滤器。见:stackoverflow.com/a/46551596/729541
    猜你喜欢
    • 1970-01-01
    • 2015-03-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-10-12
    • 2018-11-20
    • 1970-01-01
    相关资源
    最近更新 更多