将EC2 Elastic Load Balancer从HTTP重定向到HTTPS


104

我想将所有HTTP请求重定向到ELB上的https请求。我有两个EC2实例。我正在为服务器使用Nginx。我尝试重写nginx conf文件没有任何成功。我希望就此提出一些建议。


1
互联网似乎无法就此问题达成单一,完整且有效的解决方案。希望您能在我的帖子中得到一些帮助。最后,我不得不跳了圈才想到这个。
ADTC '11

1
该ans具有最新的解决方案,而不是公认的分析工具
AsifM,

Answers:


87

AWS Application Load Balancer现在支持本机HTTP到HTTPS重定向。

要在控制台中启用此功能,请执行以下操作:

  1. 转到EC2中的负载均衡器,然后选择“监听器”标签
  2. 在HTTP侦听器上选择“查看/编辑规则”
  3. 删除除默认规则(底部)以外的所有规则
  4. 编辑默认规则:选择“重定向到”作为操作,将所有内容保留为默认值,然后输入“ 443”作为端口。

本机重定向侦听器规则

同样可以通过使用CLI如所描述的来实现这里

也可以在Cloudformation中执行此操作,在该处您需要设置如下的Listener对象:

  HttpListener:
    Type: AWS::ElasticLoadBalancingV2::Listener
    Properties:
      LoadBalancerArn: !Ref LoadBalancer
      Port: 80
      Protocol: HTTP
      DefaultActions:
      - Type: redirect 
        RedirectConfig:
          Protocol: HTTPS
          StatusCode: HTTP_301
          Port: 443

如果仍然使用经典负载均衡器,请使用其他描述的NGINX配置之一。


1
现在知道它更容易非常有用。但这将是一个更好的答案,提供有关配置内容的更多信息,而不仅仅是链接。
约翰·里斯

1
@JohnRees相应地编辑了答案,希望对您有所帮助
Ulli,

真好 我赞成您使您归零。你应得更多。
约翰·里斯

2
@florian您似乎正在使用经典负载均衡器。切换到应用程序负载平衡器以获取该选项
Ulli,

如何将应用程序负载均衡器分配给我的实例?(因为没有instances标签)
Florian

107

ELB设置X-Forwarded-Proto标头,您可以使用它来检测原始请求是否是对HTTP的请求,然后再重定向到HTTPS。

您可以在serverconf中尝试:

if ($http_x_forwarded_proto = 'http') {
    return 301 https://yourdomain.com$request_uri;
}

看一下ELB文档


3
这种配置在哪里进行?
ericpeters0n

2
@ ericpeters0n答案中的代码段用于nginx配置,但是该原理适用于任何Web服务器。
德米特里·穆欣

1
如果您将beanstalk与standalone-standalone一起使用,请单击此链接以获取有关更改nginx配置的方法。qiita.com/tak_nishida/items/cf30a2d373744943b943
YEONHO

3
确保负载平衡器上具有HTTP和HTTPS侦听器。
加文·帕尔默

1
@Ronald,服务器conf在响应中,我的意思是在ELB后面运行的ec2实例上的nginx服务器。
德米特里·穆欣

34

我遇到了同样的问题,在我的情况下,HTTPS完全由ELB处理,并且我不知道自己的源域,所以我最终做了如下操作:

server {
  listen 81;
  return 301 https://$host$request_uri;
}

server {
  listen 80;
  # regular server rules ...
}

然后当然将ELB“ https”指向实例端口80,然后将“ http”路由指向实例端口81。


3
这是天才。
安迪·海登

2
@CodyBugstein,这是nginx配置,如果您有的话
timurso 18-4-19

@timurso,如果您有一个?
CodyBugstein

@CodyBugstein,如果您的应用程序前面有Nginx(例如,我没有-它直接路由到运行ExpressJS的容器)
timurso

Nginx会去哪里?在ELB内部?在EC2内部?这是在Elastic Beanstalk中的某个地方配置的吗?
CodyBugstein

16

Amazon Elastic Load Balancer(ELB)支持称为X-FORWARDED-PROTO的HTTP标头。通过ELB的所有HTTPS请求的X-FORWARDED-PROTO值将等于“ HTTPS”。对于HTTP请求,您可以通过添加以下简单的重写规则来强制执行HTTPS。对我来说,一切正常!

阿帕奇

您可以在.htaccess文件中添加以下行:

RewriteEngine On
RewriteCond %{HTTP:X-Forwarded-Proto} !https
RewriteRule ^.*$ https://%{SERVER_NAME}%{REQUEST_URI}

或者,如果您使用vhost.conf在同一EC2 Web服务器中管理多个域,则可以将以下内容添加到vhost.conf中(将其添加到您要对其使用https的域中):

<VirtualHost *:80>
...
RewriteEngine On
RewriteCond %{HTTP:X-Forwarded-Proto} !https
RewriteRule ^.*$ https://%{SERVER_NAME}%{REQUEST_URI}
...
</VirtualHost>

IIS

安装IIS Url-Rewrite模块,使用配置GUI添加以下设置:

<rewrite xdt:Transform="Insert">
<rules>
<rule name="HTTPS rewrite behind ELB rule" stopProcessing="true">
<match url="^(.*)$" ignoreCase="false" />
<conditions>
<add input="{HTTP_X_FORWARDED_PROTO}" pattern="^http$" ignoreCase="false" />
</conditions>
<action type="Redirect" redirectType="Found" url="https://{SERVER_NAME}{URL}" />
</rule>
</rules>
</rewrite>

在这里阅读更多


我们遇到了使实例重定向正常的HTTP流量的问题,因为甚至不存在标头。我通过制定以下条件来解决它:RewriteCond %{HTTP:X-Forwarded-Proto} !(https|^$)
natronite 2016年

这导致无限重定向。我在Windows服务器上使用IIS。
这是一个陷阱

@ It'satrap:如果IIS无法正常工作,请尝试使用以下URL中的脚本:stephen.genoprime.com/2012/01/01/aws-elb-ssl-with-iis.html
Iman Sedighi

5

上面的htaccess解决方案导致ELB健康检查失败。在找到在线文章中有人遇到与我相同的问题之前,我很难找到解决方案。他的解决方案是将其添加到htaccess文件的开头:

RewriteEngine on 
RewriteCond %{HTTP:X-Forwarded-Proto} ^http$
RewriteRule .* https://%{HTTP_HOST}%{REQUEST_URI} [R=301,L]

要通过HTTP允许此请求和其他本地请求,同时将外部请求通过ELB重定向到HTTPS,请调整重写条件以使其在http上匹配,而在https上不匹配。

来源:使用AWS和ELB将HTTP重定向到HTTPS


“调整重写条件以在http上匹配,而不是在https上匹配否定”,这就是我要解决的部分。谢谢!
Merricat


3

我对nginx和ELB配置有奇怪的问题。我的设置在ELB后面的一个Nginx中包含3种不同的服务。而且我遇到了混合内容问题:当您对ELB的请求是https,但仅在ELB HTTP中,并且服务器使用http创建到静态的相对路径时,浏览器将出现“混合内容”问题。而且我必须为没有重定向的http / https工作创建解决方案。

这是位于nginx/conf.d/文件夹中的配置:

# Required for http/https switching
map $http_x_forwarded_port $switch {
  default   off;
  "80"    off;
  "443"   on;
}

这意味着我们将了解什么是真正的客户端协议。如您所见,我们将在$switchvar中使用它。现在,您可以在需要的所有位置使用它:

location ~ /softwareapi/index.php {
  fastcgi_param HTTPS $switch;
  .. other settings here ..
}

通过HTTPS设置,php应用程序将自动检测正确的协议,并仔细构建相对路径以防止混合内容问题。

最好的祝福。


3

基于@Ulli的答案如果要使用Terraform对其进行配置,请参见以下示例>

resource "aws_alb_listener" "web" {
  load_balancer_arn = "${aws_alb.web.arn}"

  port              = "80"
  protocol          = "HTTP"

  default_action {
    type = "redirect"

    redirect {
      port        = "443"
      protocol    = "HTTPS"
      status_code = "HTTP_301"
    }
  }
}

资源


-2

创建一个.ebextensions/00_forward_http_to_https.config具有以下内容的文件:

files: 
  /tmp/deployment/http_redirect.sh:
    mode: "000755"
    content: |
      APP_URL=`/opt/elasticbeanstalk/bin/get-config environment --output yaml | grep -oP 'APP_URL: \K([^\s)\"](?!ttp:))+'`
      sed -ie 's@$proxy_add_x_forwarded_for;@$proxy_add_x_forwarded_for;\n        if ($http_x_forwarded_proto = 'http') { return 301 https://'"$APP_URL"'$request_uri; }@' /tmp/deployment/config/#etc#nginx#conf.d#00_elastic_beanstalk_proxy.conf

container_commands:
  http_redirect:
    command: "/tmp/deployment/http_redirect.sh"

确保事先从AWS管理控制台设置APP_URL环境变量。


在平衡与ELB的TCP连接时,该怎么做?
繁荣

1
我看不到您的答案适合该问题的地方……您在谈论弹性豆秆,而问题是关于EC2内部的nginx。
jvarandas
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.