모든 HTTP 요청을 ELB의 https 요청으로 리디렉션하고 싶습니다 . 두 개의 EC2 인스턴스가 있습니다. 서버에 nginx를 사용하고 있습니다. 나는 성공하지 않고 nginx conf 파일을 다시 작성하려고 시도했습니다. 나는 그것에 대한 몇 가지 조언을 원합니다.
모든 HTTP 요청을 ELB의 https 요청으로 리디렉션하고 싶습니다 . 두 개의 EC2 인스턴스가 있습니다. 서버에 nginx를 사용하고 있습니다. 나는 성공하지 않고 nginx conf 파일을 다시 작성하려고 시도했습니다. 나는 그것에 대한 몇 가지 조언을 원합니다.
답변:
AWS Application Load Balancer는 이제 네이티브 HTTP에서 HTTPS 로의 리디렉션을 지원합니다.
콘솔에서이를 활성화하려면 다음을 수행하십시오.
여기에 설명 된대로 CLI를 사용하여 동일한 작업을 수행 할 수 있습니다 .
다음과 같이 Listener 개체를 설정해야하는 Cloudformation에서도이 작업을 수행 할 수 있습니다.
HttpListener:
Type: AWS::ElasticLoadBalancingV2::Listener
Properties:
LoadBalancerArn: !Ref LoadBalancer
Port: 80
Protocol: HTTP
DefaultActions:
- Type: redirect
RedirectConfig:
Protocol: HTTPS
StatusCode: HTTP_301
Port: 443
여전히 Classic Load Balancer를 사용하는 경우 다른 구성에서 설명한 NGINX 구성 중 하나로 이동하십시오.
instances
탭 이 없기 때문에 )
ELB는 X-Forwarded-Proto
헤더를 설정 합니다.이를 사용하여 원래 요청이 HTTP에 대한 것인지 감지하고 HTTPS로 리디렉션 할 수 있습니다.
server
conf 에서 이것을 시도 할 수 있습니다 .
if ($http_x_forwarded_proto = 'http') {
return 301 https://yourdomain.com$request_uri;
}
ELB 문서를 살펴보십시오 .
nginx
구성 용 이지만 원칙은 모든 웹 서버에 적용됩니다.
내 상황에서 HTTPS는 ELB가 전적으로 처리했으며 소스 도메인을 미리 몰랐기 때문에 동일한 문제가 발생하여 다음과 같은 작업을 수행했습니다.
server {
listen 81;
return 301 https://$host$request_uri;
}
server {
listen 80;
# regular server rules ...
}
그리고 물론 ELB 'https'는 인스턴스 포트 80을 가리키고 'http'경로는 인스턴스 포트 81을 가리 킵니다.
Amazon Elastic Load Balancer (ELB)는 X-FORWARDED-PROTO라는 HTTP 헤더를 지원합니다. ELB를 통과하는 모든 HTTPS 요청은 "HTTPS"와 같은 X-FORWARDED-PROTO 값을 갖습니다. HTTP 요청의 경우 다음과 같은 간단한 재 작성 규칙을 추가하여 HTTPS를 강제 실행할 수 있습니다. 나를 위해 그것은 잘 작동합니다!
Apache
.htaccess 파일에 다음 줄을 추가 할 수 있습니다.
RewriteEngine On
RewriteCond %{HTTP:X-Forwarded-Proto} !https
RewriteRule ^.*$ https://%{SERVER_NAME}%{REQUEST_URI}
또는 동일한 EC2 웹 서버에서 여러 도메인을 관리하기 위해 vhost.conf를 사용하는 경우 vhost.conf에 다음을 추가 할 수 있습니다 (https를 사용하려는 도메인에 추가).
<VirtualHost *:80>
...
RewriteEngine On
RewriteCond %{HTTP:X-Forwarded-Proto} !https
RewriteRule ^.*$ https://%{SERVER_NAME}%{REQUEST_URI}
...
</VirtualHost>
IIS
구성 GUI를 사용하여 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>
RewriteCond %{HTTP:X-Forwarded-Proto} !(https|^$)
위의 htaccess 솔루션으로 인해 ELB 상태 확인이 실패했습니다. 나는 누군가가 내가 가진 것과 같은 문제를 가지고있는 온라인 기사를 발견 할 때까지 해결책을 찾는 데 어려움을 겪었다. 그의 해결책은 대신 이것을 htaccess 파일의 시작 부분에 추가하는 것이 었습니다.
RewriteEngine on
RewriteCond %{HTTP:X-Forwarded-Proto} ^http$
RewriteRule .* https://%{HTTP_HOST}%{REQUEST_URI} [R=301,L]
ELB를 통해 외부 요청을 HTTPS로 리디렉션하는 동안 HTTP를 통한이 요청과 기타 로컬 요청을 허용하려면 https에서 부정적으로 일치하는 대신 http에서 일치하도록 다시 쓰기 조건을 조정합니다.
찾고있는 솔루션이 아닐 수도 있지만 다른 옵션은 ELB 외에 AWS CloudFront를 사용하는 것입니다. CloudFront는 들어오는 모든 HTTP 트래픽을 HTTPS로 리디렉션하는 옵션을 제공합니다.
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;
}
이것은 우리가 실제 클라이언트 프로토콜이 무엇인지 알 수 있음을 의미합니다. 보시다시피 $switch
var에 있습니다. 그리고 현재 필요한 모든 위치에서 이것을 사용합니다.
location ~ /softwareapi/index.php {
fastcgi_param HTTPS $switch;
.. other settings here ..
}
HTTPS 설정을 사용하면 PHP 응용 프로그램이 올바른 프로토콜을 자동으로 감지하고 혼합 콘텐츠 문제를 방지하기 위해 신중하게 상대 경로를 구축합니다.
친애하는.
@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"
}
}
}
.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 환경 변수를 설정해야합니다.