NGINX como proxy reverso na frente do Apache não funciona com o SSL ativado

2

Eu li todos os posts, tutoriais e comentários em fóruns que estão por aí e ainda não consegui usar o Nginx Proxy para funcionar corretamente assim que o SSL for ativado no bloco de servidores Nginx.

O Apache está totalmente configurado com o host virtual para acesso regular e SSL. O Apache está escutando na porta 8081 com ports.conf é como segue:

NameVirtualHost *:8081
Listen 8081

<IfModule ssl_module>
        Listen 443
</IfModule>

<IfModule mod_gnutls.c>
        Listen 443
</IfModule>

Meu vache apache SSL é o seguinte:

Com o nginx ativado e as configurações de ssl comentadas como na configuração a seguir (veja abaixo), tudo funciona bem, já que consigo acessar as versões SSL e não SSL do site corretamente.

    server {
        listen 80;
  #      listen 443 ssl;
        server_name foobar.net;

   # ssl on;
   #     ssl_certificate /etc/letsencrypt/live/foobar.net/fullchain.pem;
   #     ssl_certificate_key /etc/letsencrypt/live/foobar.net/privkey.pem;

        location / {
            proxy_pass http://104.236.224.53:8081;
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
            proxy_set_header X-Forwarded-Proto $scheme;
        }
    }

Quando eu modifico o arquivo acima e ligo o SSL por opções de não comentar no bloco do servidor, parece haver um conflito entre o Nginx e o Apache na porta 443?

Blocos de servidores atualizados e não comentados são assim:

    server {
        listen 80;
        listen 443 ssl;
        server_name foobar.net;

    ssl on;
        ssl_certificate /etc/letsencrypt/live/foobar.net/fullchain.pem;
        ssl_certificate_key /etc/letsencrypt/live/foobar.net/privkey.pem;

        location / {
            proxy_pass http://104.236.224.53:8081;
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
            proxy_set_header X-Forwarded-Proto $scheme;
        }
    }

Tentando iniciar o retorno nginx após erro:

 nginx.service - A high performance web server and a reverse proxy server
   Loaded: loaded (/lib/systemd/system/nginx.service; enabled; vendor preset: enabled)
   Active: failed (Result: exit-code) since Mon 2017-02-20 18:35:20 EST; 16s ago
  Process: 14505 ExecStop=/sbin/start-stop-daemon --quiet --stop --retry QUIT/5 --pidfile /run/nginx.pid (code=exited, status=0/SUCCESS
  Process: 14475 ExecReload=/usr/sbin/nginx -g daemon on; master_process on; -s reload (code=exited, status=0/SUCCESS)
  Process: 14671 ExecStart=/usr/sbin/nginx -g daemon on; master_process on; (code=exited, status=1/FAILURE)
  Process: 14652 ExecStartPre=/usr/sbin/nginx -t -q -g daemon on; master_process on; (code=exited, status=0/SUCCESS)
 Main PID: 14328 (code=exited, status=0/SUCCESS)

Feb 20 18:35:18 foo.foobar.net nginx[14671]: nginx: [emerg] listen() to 0.0.0.0:443, backlog 511 failed (98: Address already in use)
Feb 20 18:35:18 foo.foobar.net nginx[14671]: nginx: [emerg] listen() to 0.0.0.0:443, backlog 511 failed (98: Address already in use)
Feb 20 18:35:19 foo.foobar.net nginx[14671]: nginx: [emerg] listen() to 0.0.0.0:443, backlog 511 failed (98: Address already in use)
Feb 20 18:35:19 foo.foobar.net nginx[14671]: nginx: [emerg] listen() to 0.0.0.0:443, backlog 511 failed (98: Address already in use)
Feb 20 18:35:20 foo.foobar.net nginx[14671]: nginx: [emerg] listen() to 0.0.0.0:443, backlog 511 failed (98: Address already in use)
Feb 20 18:35:20 foo.foobar.net nginx[14671]: nginx: [emerg] still could not bind()
Feb 20 18:35:20 foo.foobar.net systemd[1]: nginx.service: Control process exited, code=exited status=1
Feb 20 18:35:20 foo.foobar.net systemd[1]: Failed to start A high performance web server and a reverse proxy server.
Feb 20 18:35:20 foo.foobar.net systemd[1]: nginx.service: Unit entered failed state.
Feb 20 18:35:20 foo.foobar.net systemd[1]: nginx.service: Failed with result 'exit-code'.

O que estou perdendo aqui com a minha implementação para obter SSL para passar corretamente para o Apache do Nginx?

Editar 1: Para abordar o bom ponto do Tim, vou editar minha intenção principal de ter o Nginx lidando com todos os pedidos.

  • Minha intenção original era instalar o Discourse, que está em um contêiner do Docker, na mesma máquina em que o Apache já estava sendo usado como meu servidor principal.
  • Como o Discourse precisa de acesso à porta 80 para funcionar corretamente, recomenda-se configurar o nginx na frente como um proxy reverso para manipular todas as solicitações recebidas para que elas sejam transmitidas de acordo.
  • Eu quero usar o apache na parte de trás para lidar com todo o conteúdo dinâmico e deixar o nginx lidar com bits estáticos. Assim, entendo que, para isso, um hos virtual precisa ser estabelecido no apache para cada instância: solicitações http e https. Talvez eu esteja errado aqui neste ponto?

Eu segui as configurações sugeridas por DigitalOcean: avançar rapidamente para o seu passo opcional 9.

Logicamente, neste ponto, assim como eu tenho o host HTTP no apache ouvindo na porta 8081 para solicitações transmitidas do nginx, presumi que poderia fazer o mesmo e também ter host HTTPS no apache para ouvir a porta 8081 e passar cabeçalhos para o Apache para lidar com o resto. Esta implementação não funcionou totalmente porque eu estava com o erro 400: the plain http request was sent to https port

Eu dei um passo além e imaginei que, novamente, já que o Apache HTTP e HTTPS estão escutando a porta 8081 no verso, se eu atribuísse o HTTP do apache à porta 8081 e HTTPS à porta 1443, tudo funcionaria perfeitamente. Mais uma vez, ele não funciona totalmente como quando eu tento acessar o meu blog worpress via HTTPS com esta implementação eu recebo erro

Your browser sent a request that this server could not understand.
Reason: You're speaking plain HTTP to an SSL-enabled server port.
Instead use the HTTPS scheme to access this URL, please.

A essa altura, estou literalmente sem novas ideias, embora pareça que muitos conseguiram que a implementação do oceano digital sugerisse que funcionasse corretamente. : - /

    
por Robert 21.02.2017 / 00:41

3 respostas

0

Parece que finalmente consegui implementar graças a todos os comentários que recebi de você. Thanx @AlexeyTen e @Tim

  • Primeiro desativei https vhost no apache para o domínio foobar.net sudo a2dissite foobar.net.cong

  • Eu editei o arquivo apache ports.conf para ouvir apenas a porta 8081 e removi a escuta na porta 443:

NameVirtualHost *:8081

Listen 8081
  • Por fim, editei o bloco do servidor nginx para ouvir a porta 443 e fiz questão de comentar ssl on . Não fazê-lo não funcionou.
> server {
>     listen 80;
>     listen 443 ssl;
>     server_name foobar.net;
> 
>   # ssl on;
>     ssl_certificate /etc/letsencrypt/live/foobar.net/fullchain.pem;
>     ssl_certificate_key /etc/letsencrypt/live/foobar.net/privkey.pem;
> 
>     location / {
>         proxy_pass http://104.236.224.53:8081;
>         proxy_set_header Host $host;
>         proxy_set_header X-Real-IP $remote_addr;
>         proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
>         proxy_set_header X-Forwarded-Proto $scheme;
>     } }

Esta implementação parece funcionar bem e manipular o manuseio do PHP para o Apache sem problemas.

    
por 21.02.2017 / 20:02
2

Você disse ao Apache e ao Nginx para escutar na porta 443, eu assumo na mesma máquina. Apenas um aplicativo pode escutar em uma porta.

Talvez você possa editar sua pergunta para nos dizer por que deseja usar tanto o Nginx quanto o Apache - você pode fazer a maioria das coisas com qualquer um deles. Você pode obter mais conselhos úteis dessa maneira.

    
por 21.02.2017 / 05:35
0

@Robert, sua solução funcionou, mas não carregou certificados SSL no navegador.

Minha solução é a seguinte:

Alterar porta padrão do apache de 80 para 8080

Alterar a porta SSL padrão do apache de 443 para 444

Abaixo está minha configuração do ngnix:

servidor {

ouça 80;

server_name servername.com;

localização / {

    proxy_pass http://127.0.0.1:8080;
    proxy_set_header Host $host;
    proxy_set_header X-Real-IP $remote_addr;
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    proxy_set_header X-Forwarded-Proto $scheme;
    expires off;
}

}

servidor {

listen 443 ssl http2;
server_name servername.com;
ssl on;
ssl_certificate /etc/nginx/ssl/keyname.crt;
ssl_certificate_key /etc/nginx/ssl/private/keyname.key;

localização / {

    proxy_pass https://127.0.0.1:444;
    proxy_set_header Host $host;
    proxy_set_header X-Real-IP $remote_addr;
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    proxy_set_header X-Forwarded-Proto $scheme;
    expires off;
}

}

Nota:

  1. proxy_pass precisa ser alterado para https no caso de SSL.
  2. Isso funciona bem quando o nginx está sendo exibido como proxy reverso para o apache.
  3. Requer que o vache apache seja modificado para incluir 444 em vez de 443 para configuração de SSL.
  4. Configure o ports.conf no apache para o 444 para SSL
por 08.09.2017 / 13:33