Apache2 VirtualHost IfPort?

Apache2 VirtualHost IfPort?

Eu gostaria de fazer um host virtual como este:

<VirtualHost *:80 *:443>
    <IfPort 443>
        SSLEngine On
        ...
    </IfPort>

    ...
</VirtualHost>

Portanto, se o host foi acessado pela porta 443, quero adicionar algumas funcionalidades adicionais. Posso conseguir isso de alguma forma ou preciso separar isso em dois hosts virtuais?

Responder1

Eu uso mod_macropara resolver esse problema em um servidor que hospeda vários domínios diferentes... Instale o módulo (difere de acordo com o sistema operacional/distro) e configure algo assim:

LoadModule macro_module         libexec/apache22/mod_macro.so

<Macro VHost $host>
        <VirtualHost *:80>
                DocumentRoot /usr/local/www/$host/data
                ServerName $host
                ServerAlias *.$host

                ScriptAlias /cgi-bin/ "/usr/local/www/$host/cgi-bin/"
                IncludeOptional etc/apache22/vhosts/$host
        </VirtualHost> 
</Macro>

<Macro VHostSSL $host>
        <VirtualHost *:80>
                DocumentRoot /usr/local/www/$host/data
                ServerName $host
                ServerAlias *.$host

                ScriptAlias /cgi-bin/ "/usr/local/www/$host/cgi-bin/"
                IncludeOptional etc/apache22/vhosts/$host
        </VirtualHost>
        <VirtualHost *:443>
                DocumentRoot /usr/local/www/$host/data
                ServerName $host
                ServerAlias *.$host

                SSLEngine on
                SSLCertificateFile /usr/local/www/$host/ssl/$host.crt
                SSLCertificateKeyFile /usr/local/www/$host/ssl/$host.key

                ScriptAlias /cgi-bin/ "/usr/local/www/$host/cgi-bin/"
                IncludeOptional etc/apache22/vhosts/$host
        </VirtualHost> 
</Macro>

Use VHostSSL example.com 
Use VHost    example.net

Super fácil adicionar um novo domínio; quaisquer configurações específicas do domínio são lançadas no arquivo de inclusão.

Responder2

usando a solução de John eu entendo isso

Apache 2 is starting ...
AH00526: Syntax error on line 53 of .../httpd-vhosts.conf:
SSLEngine not allowed here

como John disse, a melhor maneira é ter 2 hosts virtuais; mas meu código de host virtual tinha mais de 150 linhas (muitos proxies reversos), pois eu não queria ter 2 de cada código (e um arquivo de configuração muito longo) acabei fazendo isso que funciona:

1.Crie um host virtual para host virtual não SSL.

2.Crie outro host virtual e proxy reverso para o primeiro host virtual

<VirtualHost *:443>
    SSLEngine on
    SSLCipherSuite ALL:!ADH:!EXPORT56:RC4+RSA:+HIGH:+MEDIUM:+LOW:+SSLv2:+EXP:+eNULL
    SSLCertificateFile "...cert.crt"
    SSLCertificateKeyFile "...server.ssl.key"
    ... (any ssl specific config)

    ProxyPreserveHost On
    ProxyPass / http://localhost:80/
    ProxyPassReverse http://localhost:80/ http://yourdomain.com/
</VirtualHost>

esta não é uma solução boa ou de baixo desempenho, mas se a razão por trás de não querer 2 hosts virtuais é evitar ter 2 versões de todas as configurações de host virtual (o que significa alterar 2 linhas cada vez que você quiser alterar alguma coisa), isso funciona.

Responder3

Outra opção para evitar duplicação seria manter a configuração do virtualhost em um arquivo específico e inseri-la com um include:

/etc/path/to/config/example.com.conf:

ServerName example.com.conf
DocumentRoot /var/www/something
# Any other config you want to apply to both vhosts

E seu arquivo de hosts virtuais:

<VirtualHost *:443>
    SSLEngine on
    # Other SSL directives
    Include /etc/path/to/config/example.com.conf
</VirtualHost>
<VirtualHost *:80>
    Include /etc/path/to/config/example.com.conf
</VirtualHost>

Responder4

Dê uma olhada na Ifestrutura do Apache e manipule a solicitação. Vera documentação principal para Ifsea lista de expressões disponíveis para usar nele. Você poderia fazer algo como:

<If "%{SERVER_PORT} == '443'">
    # Do stuff
</If>

Em relação à sua VirtualHosttag, não vejo tal solução na documentação do Apache2. Verhttp://httpd.apache.org/docs/2.2/en/vhosts/examples.html#porte tente sua opção: Apache2 usa um semelhante para IPs diferentes em vez de portas diferentes (http://httpd.apache.org/docs/2.2/en/vhosts/examples.html#intraextra).

Eu ainda recomendaria o uso de 2 hosts virtuais distintos, muito mais claros. Você precisará de dois NameVirtualHoste Listenem seu apache2.confarquivo, de qualquer maneira.

Editar

Não percebi que essa solução realmente gerava um erro, mas vamos voltar ao conceito em si... Ouvir em 80 ou 443 não tem problema, na verdade. O Apache2 teria prazer em fornecer uma solução elegante para isso, se não fosse pela... criptografia. O Apache2 foi desenvolvido em C e, além de threads e forks, utiliza soquetes. Em C, o uso de SSL requer a inicialização de componentes OpenSSL e algumas soluções alternativas para o soquete básico para implementar todo o SSL. Você está procurando uma solução fácil, mas todo o mecanismo por trás é complicado... É por isso que você não pode habilitar SSL em um host virtual básico: HTTP e HTTPs são componentes diferentes e, no modo Apache2, temo que haja nenhum conceito de herança entre o primeiro e o segundo.

informação relacionada