'

Outils pour utilisateurs

Outils du site


doc:apache2

apache2

Quelques infos sur la mise en place d'un serveur apache2 sur une DEBIAN « Squeeze ».

Si cette page vous a été utile :

installation

aptitude installera apache en quelques secondes et vous aurez ainsi un serveur web qui répondra en HTTP sur le port 80.

$ sudo aptitude install apache2
Lecture des listes de paquets... Fait
Construction de l'arbre des dépendances       
Lecture des informations d'état... Fait
Lecture de l'information d'état étendu      
Initialisation de l'état des paquets... Fait
Lecture des descriptions de tâches... Fait  
Les NOUVEAUX paquets suivants vont être installés : 
  apache2 apache2-mpm-worker{a} apache2-utils{a} apache2.2-common{a} 
0 paquets mis à jour, 4 nouvellement installés, 0 à enlever et 0 non mis à jour.
Il est nécessaire de télécharger 241ko/1211ko d'archives. Après dépaquetage, 4452ko seront utilisés.
Voulez-vous continuer ? [Y/n/?] 

Pour vérifier qu'apache2 fonctionne, lancer votre navigateur et dans la barre d'adresse, entrez votre adresse IP. Normalement, vous devriez voir une page web qui indique quelque chose comme « It works ! »

Par défaut, apache2 fournit par DEBIAN sert les pages du répertoire /var/www qui contient le fichier index.html.

$ cat /var/www/index.html 
<html><body><h1>It works!</h1></body></html>

Les fichiers de configuration sont stockés dans le répertoire /etc/apache2.

configuration sécurité

Depuis Lenny DEBIAN fournit un fichier de configuration pour améliorer la sécurité du serveur. Voilà le contenu de ce fichier expurgé de quelques commentaires et quelques lignes vides.

$ egrep -B 1 -v '^#|^$' /etc/apache2/conf.d/security 
#ServerTokens Minimal
ServerTokens Full
--
#ServerSignature Off
ServerSignature On
--
#TraceEnable Off
TraceEnable On

Par défaut, le fichier n'apporte rien. Il faudrait au minimum inverser les lignes commentées et celles décommentées. Plus de détails ci-après.

ServerTokens

La directive ServerTokens contrôle la chaîne de caractères retournée dans le champs Server de l'entête HTTP. En spécifiant Full, apache donne son nom, sa version et également le système d'exploitation sur lequel il est installé et les modules ajoutés.

Il est possible de voir ce que retourne un serveur avec wget.

$ wget -S http://localhost                   
--2009-05-31 22:54:04--  http://localhost/
Résolution de localhost... 127.0.0.1, ::1
Connexion vers localhost|127.0.0.1|:80...connecté.
requête HTTP transmise, en attente de la réponse...
  HTTP/1.1 200 OK
  Date: Sun, 31 May 2009 20:54:04 GMT
  Server: Apache/2.2.9 (Debian)
  Last-Modified: Sun, 31 May 2009 20:12:05 GMT
  ETag: "120e2e-2d-46b3aec646f28"
  Accept-Ranges: bytes
  Content-Length: 45
  Vary: Accept-Encoding
  Keep-Alive: timeout=15, max=100
  Connection: Keep-Alive
  Content-Type: text/html
Longueur: 45 [text/html]

Voilà ce qu'on obtient avec un serveur apache2 installé dans sa configuration par défaut sur DEBIAN « Lenny ». Si on installe des modules complémentaires, apache les indique. Exemple en activant plusieurs modules :

Server: Apache/2.2.9 (Debian) PHP/5.2.6-1+lenny2 with Suhosin-Patch mod_python/3.3.1 Python/2.5.2 mod_ruby/1.2.6 Ruby/1.8.7(2008-08-11) mod_ssl/2.2.9 OpenSSL/0.9.8g mod_perl/2.0.4 Perl/v5.10.0

Si un jour le serveur est sujet à une faille de sécurité, le vilain pirate aura de nombreuses informations sur la version de chacun des modules. Pour rendre le serveur moins éloquant, on pourrait choisir la valeur Minimal mais ce n'est pas la moins verbeuse, apache indiquera encore sa version complète. Pour obtenir le minimum, il faudra choisir la valeur Prod.

Avec cette valeur, le champ Server contiendra maintenant :

Server: Apache

On serait tenter de donner de fausses informations en remplaçant Apache par tout autre chose mais ce n'est pas possible par configuration, il faudra recompiler le serveur ou installer mod_security.

Le but ici est de donner le moins d'information possible à un attaquant éventuel. Le jour où une faille dite « 0 day » touche apache, il est préférable de ne pas être identifié trop vite comme une cible de choix. Ça laisse un peu de temps pour appliquer les mises à jour de sécurité.

ServerSignature

La directive ServerSignature. Si la valeur est on les pages d'erreur affichées par apache contiendront la signature définie dans le paragraphe précédent. En positonnant ServerTokens Prod, seule la ligne suivante sera affichée en bas de chaque page d'erreur.

Apache Server at localhost Port 80

Pour supprimer complétement cette ligne : ServerSignature Off.

TRACE et TRACK

TRACE et TRACK sont deux types de requête HTTP comme POST ou GET. Le principe est d'envoyer au serveur des données et celui-ci les renvoie. Ces requêtes sont inutiles sur un serveur opérationnel.

La directive TraceEnable permet d'activer ou désactiver la fonctionnalité TRACE qui devrait être réservée au déverminage.

TraceEnable Off

Par contre, TRACK, qui est une implémentation de TRACE, reste utilisable. Pour désactiver ce type de requête, il faudra utiliser un « rewrite ».

RewriteEngine on
RewriteCond %{REQUEST_METHOD} ^(TRACE|TRACK)
RewriteRule .* - [F]

Ces 3 lignes active le moteur de ré-écriture de apache. La deuxième ligne précise que la règle ne s'applique aux requêtes TRACE ou TRACK. Ce type de requête par à la poubelle.

bilan de la configuration apache

Le fichier /etc/apache2/conf.d/security final ressemble à

$ cat /etc/apache2/conf.d/security
ServerTokens Prod
ServerSignature Off
TraceEnable Off
RewriteEngine on
RewriteCond %{REQUEST_METHOD} ^(TRACE|TRACK)
RewriteRule .* - [F]

php

Pour rendre PHP moins bavard, il faut positionner la directive expose_php = Off dans le fichier /etc/php5/apache2/php.ini. Par défaut sous DEBIAN, la valeur est à On.

Avant la modification, voici la réponse à un wget -S :

  HTTP/1.1 200 OK
  Date: Thu, 09 Jul 2009 20:45:54 GMT
  Server: Apache
  X-Powered-By: PHP/5.2.6-1+lenny3

Après la modification :

  HTTP/1.1 200 OK
  Date: Thu, 09 Jul 2009 20:51:26 GMT
  Server: Apache

Le champ X-Powered-By, l'entête HTTP ne donne donc plus d'information sur PHP ni même sur sa présence.

configuration SSL

Pour utiliser HTTPS, il faut d'abord charger le module ssl via la commande a2enmod.

$ sudo a2enmod ssl
$ sudo apache2ctl restart

Lors de l'installation, DEBIAN génère un certificat auto-signé. Il permettra d'authentifier le serveur et de chiffrer la connexion mais le navigateur alertera l'utilisateur car il ne connaît pas l'autorité qui a signé le certificat.

clé et certificat serveur

Pour utiliser la clé et le certificat générés, par exemple, avec la doc xca, il est nécessaire de modifier deux lignes de configuration dans le fichier /etc/apache2/site-available/default-ssl. Dans les lignes :

SSLCertificateFile /etc/ssl/certs/moncertificat.pem
SSLCertificateKeyFile /etc/ssl/private/macle.key

Ces deux lignes désigne l'emplacement du certificat et de la clef privée du serveur, tous deux au format PEM.

authentification client

La configuration ci-dessous a été extraite du SSL howto apache (en français et sous licence Apache License Version 2.0).

Le but est d'authentifier les clients qui disposent d'un certificat SSL par ce mécanisme. Les autres seront authentifiés via une authentification basique simple (:!: en HTTP (sans « s »), le mot de passe de l'authentification basique passe en clair sur le réseau).

autorité de certification

Pour que le serveur puisse vérifier les certificats présentés par les clients, il doit pouvoir accéder au certificat de l'autoritié de certification. Pour cela, ajouter la directive SSLCACertificateFile au fichier /etc/apache2/site-available/default-ssl. Apache ne reconnait que les certificats au format PEM.

SSLCACertificateFile  /etc/ssl/certs/MaCa.pem

La directive est présente mais commentée dans le fichier fournit par DEBIAN. Il est possible de charger plusieurs certificats de diverses autorités de certification en utilisant la directive SSLCACertificatePath qui pointera vers un répertoire qui contiendra les certificats (par défaut, /etc/ssl/certs/ contient plus de 200 fichiers, il est préférable de choisir un autre répertoire pour ne les charger tous).

définition de l'authentification

Dans cet exemple, l'accès au répertoire /usr/lib/cgi-bin est protégé par une authentification.

  $ cat /etc/apache2/conf.d/cgi 
  <Directory /usr/lib/cgi-bin/>

  # source http://httpd.apache.org/docs/2.3/fr/ssl/ssl_howto.html
  #   Si HTTPS est utilisé, on s'assure que le niveau de chiffrement est fort.
  #   Autorise en plus les certificats clients comme une alternative à
  #   l'authentification basique.

  SSLVerifyClient      optional
  SSLVerifyDepth       1
  SSLOptions           +FakeBasicAuth +StrictRequire

  AuthType Basic
  AuthName "Zone privée"
  AuthBasicProvider   file
  AuthUserFile 				/etc/apache2/htpasswd
  Require 					  valid-user
  </Directory>
  • SSLVerifyClient : optional pour permettre au client sans certificat de s'authentifier.
  • SSLVerifyDepth : 1 si vous utiliser votre propre et unique autorité de certification
  • SSLOptions : +FakeBasicAuth permet de simuler une authentification basique, le DN du certificat devra être déclaré dans le fichier htpasswd avec ou sans mot de passe chiffré (il ne sert à rien). +StrictRequire : si le module SSL échoue dans l'authentification, elle s'arrête sans passer à la suite.

Le reste correspond à une configuration d'authentification basique très classique.

Le fichier /etc/apache2/htpasswd contiendra les utilisateurs authentifier sans SSL et le DN des utilisateurs qui s'authentifie par certificat.

$ cat /etc/apache2/htpasswd
martin:n88yx.lhyNwK2
/C=FR/ST=Labas/L=Chezlui/O=Famille Martin/CN=David/emailAddress=David@famillemartin.net

La première ligne contient le compte de Martin et son mot de passe (vous pouvez essayer de le craquer, c'est bidon ;-) ).

La seconde ligne contient le DN (Distinguished Name) du certificat. Le mot de passe n'est pas utilisé par apache, il n'est pas obligatoire. Si vous ne connaissez pas le DN, charger une page authentifiée avec le navigateur et son certificat, le DN apparaît dans les logs apache ( tail -f /var/log/apache2/ssl_access.log, par exemple).

optimiser la bande passante

Il existe de nombreux mécanismes pour diminuer les besoins en bande passante d'un site. Au moins deux sont implémentables sur un serveur apache.

compression des données

La plupart des navigateurs modernes et des serveurs supportent la compression de données. Pour cela, on utilisera une compression dite gzip qui utilise l'algorithme de compression deflate. Certes la compression utilisera plus de ressources côté serveur et client mais ce sera relativement faible à côté des gains en temps de transfert, surtout avec les machines que nous (sous-)utilisons actuellement.

Il faut commencer par activer le module de compression :

# a2enmod deflate

Ensuite, il faut configurer le niveau de compression et surtout le type de fichier compressé. En efet, il est inutile de perdre du temps à compresser des fichiers qui le sont déjà (par exemple des images au format jpeg).

$ cat /etc/apache2/mods-enabled/deflate.conf 
<IfModule mod_deflate.c>
        AddOutputFilterByType DEFLATE text/html text/plain text/xml text/css image/svg+xml application/xhtml+xml application/xml application/rss+xml application/atom_xml application/x-javascript application/x-httpd-php application/x-httpd-fastphp
        SetEnvIfNoCase Request_URI \.(?:gif|jpe?g|png)$ no-gzip dont-vary
        SetEnvIfNoCase Request_URI \.(?:exe|t?gz|zip|bz2|sit|rar)$ no-gzip dont-vary
        SetEnvIfNoCase Request_URI \.pdf$ no-gzip dont-vary
        SetEnvIfNoCase Request_URI \.avi$ no-gzip dont-vary
        SetEnvIfNoCase Request_URI \.mov$ no-gzip dont-vary
        SetEnvIfNoCase Request_URI \.mp3$ no-gzip dont-vary
        SetEnvIfNoCase Request_URI \.mp4$ no-gzip dont-vary
        SetEnvIfNoCase Request_URI \.rm$ no-gzip dont-vary

</IfModule>

Pour résumer, apache compressera le contenu de type text mais pas les binaires.

google conseille de ne pas compresser les fichiers de moins de 150 octets car cela augmente leur taille mai je n'ai pas trouvé comment faire.

utilisation du cache du navigateur

Les navigateurs savent utiliser un cache qui leur permet de ne pas télécharger un contenu qui est déjà présente dans le cache. Pour que le cache fonctionne, encore faut-il que le serveur le demande gentillement.

Pour cela, il faut activer le module apache expires.

# a2enmod expires

Comme pour la compression, il est possible de préciser ce qui peut être mis dans le cache et surtout pendant combien de temps.

$ cat /etc/apache2/conf.d/expires.conf
ExpiresActive On
ExpiresByType image/gif "access plus 45 days"
ExpiresByType image/jpg "access plus 45 days"
ExpiresByType image/jpeg "access plus 45 days"
ExpiresByType image/png "access plus 45 days"
ExpiresByType image/x-icon "access plus 45 days"
ExpiresByType text/css "access plus 45 days"
ExpiresByType application/x-javascript "access plus 45 days"
ExpiresByType application/javascript "access plus 45 days"

Les images, les feuilles de style et le javascript seront gardés pendant 45 jours depuis le premier accès dans le cache du navigateur avant de télécharger de nouveau le contenu. C'est autant d'octets qui ne seront pas transférés et donc du temps de gagner au chargement des pages.

extension webdav

webdav est une extension de HTTP qui permet notamment de publier des fichiers sur un serveur web. Apache2 dispose de cette extension.

Commençons par activer les modules apache nécessaire :

$ sudo a2enmod dav dav_fs

Il est également nécessaire d'ajouter quelques directives dans la configuration apache. J'ai choisi de créer un fichier webdav dans le répertoire /etc/apache2/conf.d.

$ sudoedit /etc/apache2/conf.d/webdav 
alias /webdav /repertoire/webdav

<Location /webdav>
RewriteEngine On
RewriteCond %{HTTPS} off 
RewriteRule (.*) https://%{HTTP_HOST}%{REQUEST_URI}

DAV On

AuthType Basic
AuthName "Zone privée"
AuthBasicProvider   file
AuthUserFile        /etc/apache2/fichierdemotdepasses

<Limit GET PUT DELETE PROPPATCH MKCOL COPY MOVE LOCK UNLOCK>
  Require valid-user
</Limit>
</Location>

L'alias indique à apache que l'url /webdav pointe vers le répertoire /repertoire/webdav. Ce répertoire contiendra les fichiers transférer en webdav. Ce répertoire n'est pas situé dans le répertoire racine du serveur web, les fichiers ne seront donc par accessible par la partie web « classique » (mon explication n'est pas bien claire …)

Les 3 premières lignes redirige les utilisateurs qui arrivent en HTTP vers HTTPS (pour ce qu'on fait, je préfère).

La directive DAV On active webdav dans ce répertoire (cette « location » pour être précis).

Les 4 directives suivantes permettent de mettre en place une authentification. La liste des utilisateurs est contenue dans le fichier /etc/apache2/fichierdemotdepasses.

Pour finir, on indique à apache qu'un utilisateur dûment authentifié (valid-user) est nécessaire pour utiliser les commandes HTTP : GET PUT DELETE PROPPATCH MKCOL COPY MOVE LOCK UNLOCK, ce sont les commandes utilisées par webdav.

plusieurs domaines sur un même serveur

Il est assez pratique de mutualiser un serveur pour héberger plusieurs sites sur plusieurs domaines différents. Apache propose évidemment ce genre de fonctionnalité connue sous le nom de « virtual host » ou « vhost ».

HTTP

HTTP, comment ça marche ? Quand le navigateur se connecte au port 80 du serveur, il peut demander la page d'un hôte particulier. Voilà ce que donne une capture. L'outil netcat permet d'ouvrir une connexion TCP sur le port 80 et d'envoyer des commandes comme le ferait un navigateur.

Comment ça marche ?

$ 
GET / HTTP/1.1
Host: collilieux.net

C'est la commande Host: collilieux.net qui permet au serveur d'« orienter » vers le bon hôte virtuel.

Configuration Apache

Configurer un hôte virtuel ne nécessite que quelques lignes de configuration :

$ cat /etc/apache2/conf.d/site-available/monsite.net
<VirtualHost *:80>
        ServerAdmin "Gentil At Admin Point Net"
        ServerName monsite.net
        
        DocumentRoot /srv/data/www/monsite.net/
        
        LogLevel warn
        ErrorLog /var/log/apache2/monsite.net_error.log
        CustomLog /var/log/apache2/monsite.net_access.log combined
</VirtualHost>
$ cat /etc/apache2/conf.d/site-available/tonsite.net
<VirtualHost *:80>
        ServerAdmin "Gentil At Admin Point Net"
        ServerName tonsite.net
        
        DocumentRoot /srv/data/www/tonsite.net/
        
        LogLevel warn
        ErrorLog /var/log/apache2/tonsite.net_error.log
        CustomLog /var/log/apache2/tonsite.net_access.log combined
</VirtualHost>

Pour activer ces sites :

$ sudo a2ensite monsite.net
$ sudo a2ensite tonsite.net
$ sudo service apache2 reload

HTTPS

Avec SSL, la méthode précédente ne permet pas de déterminer le vhost car la connexion TCP doit être chiffrée, il faut donc un certificat et partager un certificat entre plusieurs sites n'est pas très propre.

On peut alors utiliser une fonctionnalité récente de 'openssl'' intégrée dans le serveur Apache de Squeeze : « Server Name Indication » (SNI). Lors de l'établissement du canal chiffré, le navigateur indique alors l'hôte (et autres paramètre comme les protocoles de chiffrement supportés).

À terminer… ;-)

Le 17/01/2012 – Sylvain Collilieux – Ce texte est sous licence Creative Commons Attribution

doc/apache2.txt · Dernière modification: Le 07/01/2015 à 23:52 (modification externe)