Перенаправление EC2 Elastic Load Balancer с HTTP на HTTPS

Я хочу перенаправить все HTTP-запрос на https запрос на ELB. У меня есть два экземпляра EC2. Я использую nginx для сервера. Я попытался переписать файлы conf nginx без какого-либо успеха. Я хотел бы несколько советов по этому поводу.

Ответ 1

ELB устанавливает заголовок X-Forwarded-Proto, вы можете использовать его для определения того, был ли исходный запрос HTTP и перенаправлен на HTTPS.

Вы можете попробовать это в своем server conf:

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

Взгляните на документы ELB.

Ответ 2

Балансировщики нагрузки приложений AWS теперь поддерживают перенаправление HTTP на HTTPS.

Чтобы включить это в консоли, выполните следующие действия:

  1. Перейдите в балансировщик нагрузки в EC2 и на вкладку "Слушатели"
  2. Выберите "Просмотреть/отредактировать правила" в своем HTTP-слушателе.
  3. Удалить все правила, кроме правила по умолчанию (внизу)
  4. Изменить правило по умолчанию: выберите "Перенаправить на" в качестве действия, оставьте все по умолчанию и введите "443" в качестве порта.

Native redirect listener rule

То же самое может быть достигнуто с помощью 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, описанных другими.

Ответ 3

У меня была та же проблема, в моей ситуации HTTPS полностью обрабатывался ELB, и я раньше не знал своего исходного домена, поэтому я закончил делать что-то вроде:

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

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

И затем, конечно, указывая ELB "https" на порт экземпляра 80, а затем на "http" маршрут на порт экземпляра 81.

Ответ 4

Балансировщик эластичных нагрузок Amazon (ELB) поддерживает HTTP-заголовок, называемый X-FORWARDED-PROTO. Все запросы HTTPS, проходящие через ELB, будут иметь значение X-FORWARDED-PROTO, равное "HTTPS". Для HTTP-запросов вы можете заставить HTTPS добавить следующее правило перезаписи. Для меня это прекрасно работает!

Apache

Вы можете добавить следующие строки в файл .htaccess:

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

Или, если вы используете vhost.conf для управления несколькими доменами на одном веб-сервере EC2, вы можете добавить следующее в vhost.conf(добавьте его в домен, для которого вы хотите использовать https):

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

IIS

Установите модуль IIS Url-Rewrite, используя графический интерфейс конфигурации, добавьте следующие настройки:

<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>

Подробнее здесь

Ответ 5

Возможно, это не решение, которое вы можете искать, но еще одним вариантом может быть использование AWS CloudFront в дополнение к ELB. CloudFront предоставляет возможность перенаправлять весь входящий HTTP-трафик на HTTPS.

Ответ 6

У меня была странная проблема с конфигурацией nginx и ELB. Моя настройка включала 3 разных сервиса внутри одного nginx за ELB. И у меня была проблема со смешанным контентом: когда ваш запрос на 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;
}

Это означает, что мы будем знать, что такое настоящий клиентский протокол. Как видите, мы будем иметь его в $switch var. И в этот момент вы используете это во всех местах, где вам это нужно:

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

С настройкой HTTPS приложение php автоматически обнаружит правильный протокол и тщательно построит относительный путь для предотвращения проблемы смешанного содержимого.

С уважением.

Ответ 7

Вышеупомянутые решения 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.

Источник: перенаправление HTTP на HTTPS с помощью AWS и ELB

Ответ 8

Основано на ответе @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"
    }
  }
}

Источник

Ответ 9

Создайте файл .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 '[email protected]$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"

Обязательно заранее установите переменную среды APP_URL из консоли управления AWS.