Gestion de versions avec Subversion, Apache, OpenSSL

De La Mouche VII


Cette page propose un petit tutoriel sur l'installation d'un serveur de gestion de versions grâce à Subversion, le système de gestion de versions à proprement parler, et Apache, serveur web permettant un accès facile aux dépôts Subversion – avec pour sécuriser le tout l'utilisation de SSL grâce à OpenSSL.

Subversion

Installer Subversion (éventuellement aussi le paquet subversion-tools, qui contient quelques commandes utiles) :

# aptitude install subversion subversion-tools

Créer un répertoire racine pour les dépôts, par exemple /home/svn :

# mkdir /home/svn

La création d'un dépôt se fait grâce à la commande svnadmin. Ne pas oublier de donner un accès en écriture à l'utilisateur qui lance Apache (le compte www-data sous Debian). Par exemple pour créer un dépot toto :

# svnadmin create /home/svn/toto
# chown -R www-data /home/svn/toto

Voir la page Gestion de versions : utilisation de base de Subversion pour les commandes spécifiques à la gestion des dépôts.

Apache

Installation

Installer Apache, ainsi que le module Subversion :

# aptitude install apache2 apache2-utils libapache2-svn

On peut créer un répertoire pour la racine du site web, si on ne veut pas utiliser le répertoire par défaut (/var/www chez Debian), par exemple /home/www :

# mkdir /home/www

Activation des modules nécessaires

Il faut activer les modules dav_svn et ssl :

# a2enmod ssl
# a2enmod dav_svn
# a2enmod authz_svn

Mise en place du SSL

Génération des fichiers nécessaires (en remplaçant « serveur » par ce que l'on veut, par exemple le nom du serveur) :

# mkdir /root/ssl
# cd /root/ssl
# openssl req -config /etc/ssl/openssl.cnf -new -out serveur.csr
# openssl rsa -in privkey.pem -out serveur.key
# openssl x509 -in serveur.csr -out serveur.crt -req -signkey serveur.key -days 3650
# openssl x509 -in serveur.crt -out serveur.der.crt -outform DER

On déplace ensuite les fichiers nécessaires dans l'arborescence de la configuration d'Apache :

# mkdir /etc/apache2/{ssl.key,ssl.crt}
# cp /root/ssl/serveur.key /etc/apache2/ssl.key
# cp /root/ssl/serveur.crt /etc/apache2/ssl.crt

Configuration du site Apache

Nous devons configurer Apache pour qu'il accepte les connexions sur le port 443 (le port HTTPS), en plus du port 80 :

# echo "Listen 443" >>/etc/apache2/ports.conf

ou, plus fin :

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

La configuration du site se fait ensuite dans le fichier /etc/apache2/sites-available/default. Nous allons créer deux serveurs virtuels, l'un écoutant sur le port 80 et l'autre sur le port 443, et n'activer l'accès aux dépôts Subversion que sur le port 443, afin d'empêcher que les mots de passe ne transitent en clair lors des connexions des utilisateurs.

Voici un exemple de fichier de configuration :

NameVirtualHost *:80
NameVirtualHost *:443

<VirtualHost *:80>
   ServerName serveur.example.com
   ServerAdmin root@serveur.example.com
   
   DocumentRoot /home/www/
   <Directory />
      Options FollowSymLinks
      AllowOverride None
   </Directory>
   <Directory /home/www/>
      Options Indexes FollowSymLinks MultiViews
      AllowOverride None
      Order allow,deny
      allow from all
   </Directory>

   ScriptAlias /cgi-bin/ /usr/lib/cgi-bin/
   <Directory "/usr/lib/cgi-bin">
      AllowOverride None
      Options ExecCGI -MultiViews +SymLinksIfOwnerMatch
      Order allow,deny
      Allow from all
   </Directory>

   ErrorLog /var/log/apache2/error.log

   # Possible values include: debug, info, notice, warn, error, crit,
   # alert, emerg.
   LogLevel warn

   CustomLog /var/log/apache2/access.log combined
   ServerSignature On

    Alias /doc/ "/usr/share/doc/"
    <Directory "/usr/share/doc/">
        Options Indexes MultiViews FollowSymLinks
        AllowOverride None
        Order deny,allow
        Deny from all
        Allow from 127.0.0.0/255.0.0.0 ::1/128
    </Directory>
</VirtualHost>

<VirtualHost *:443>
   ServerName serveur.example.com
   ServerAdmin root@serveur.example.com

   # SSL
   SSLEngine on
   SSLCertificateFile /etc/apache2/ssl.crt/serveur.crt
   SSLCertificateKeyFile /etc/apache2/ssl.key/serveur.key

   DocumentRoot /home/www/
   <Directory />
      Options FollowSymLinks
      AllowOverride None
   </Directory>
   <Directory /home/www/>
      Options Indexes FollowSymLinks MultiViews
      AllowOverride None
      Order allow,deny
      allow from all
   </Directory>

   ScriptAlias /cgi-bin/ /usr/lib/cgi-bin/
   <Directory "/usr/lib/cgi-bin">
      AllowOverride None
      Options ExecCGI -MultiViews +SymLinksIfOwnerMatch
      Order allow,deny
      Allow from all
   </Directory>

   # Activation des dépôts Subversion
   <Location /svn>
     DAV svn

     # Répertoire de base des dépôts
     SVNParentPath /home/svn

     AuthType Basic
     AuthName "Subversion Repository"
     AuthUserFile /home/svn/dav_svn.passwd

     AuthzSVNAccessFile /home/svn/dav_svn.authz

     # The following three lines allow anonymous read, but make
     # committers authenticate themselves.
     #<LimitExcept GET PROPFIND OPTIONS REPORT>
       Require valid-user
     #</LimitExcept> 
   </Location>

   ErrorLog /var/log/apache2/error.log

   # Possible values include: debug, info, notice, warn, error, crit,
   # alert, emerg.
   LogLevel warn

   CustomLog /var/log/apache2/access.log combined
   ServerSignature On
</VirtualHost>

Ici, nous avons opté pour une gestion fine des droits, mais si vous n'avez pas besoin d'une telle précision, les paramètres de dav_svn peuvent être simplifiés ; il suffit de commenter la ligne suivante :

     AuthzSVNAccessFile /home/svn/dav_svn.authz

Gestion des accès

Nous devons créer le fichier de mots de passe dav_svn.passwd, et le fichier de description des autorisation dav_svn.authz (si nous avons opté pour la gestion fine des droits).

Comptes et mots de passe

Le fichier de mots de passe se crée grâce à la commande suivante :

# htpasswd -c /home/svn/dav_svn.passwd utilisateur1

Ceci aura pour effet d'ajouter l'utilisateur utilisateur1 (un mot de passe vous sera demandé). Pour ajouter un nouvel utilisateur, utiliser :

# htpasswd /home/svn/dav_svn.passwd utilisateur2

On peut aussi utiliser les comtes système (/etc/passwd et /etc/shadow) pour l'authentification, ce qui est évidemment moins sécurisé, car cela implique de donner accès aux mots de passe des utilisateurs à l'utilisateur qui lance Apache (www-data sous Debian, comme nous l'avons déjà dit). Un petit script perl permet d'automatiser cette tâche :

#!/usr/bin/perl -w
#
# Script : maphtpasswd.pl
#
# Convertit la base d'utilisateurs du système, en un format htpasswd.
# La sortie est faite sur stdout.

use strict ;

my $uid_min = 1000 ; # Premier UID à traiter
my $uid_max = 2000 ; # Dernier UID à traiter

my($login, $pass, $uid) ;

while (($login, $pass, $uid) = getpwent())
{
        if ($uid >= $uid_min && $uid <= $uid_max)
        {
                print "$login:$pass\n" ;
        }
}

Lancé en tant que root, ce script affichera une ligne de la forme « utilisateur:mot de passe » pour chaque utilisateur dont l'UID est compris entre 1000 et 2000. Pour générer notre fichier de mots de passe, il suffit de lancer :

# maphtpasswd.pl >/home/svn/dav_svn.passwd

Et pour le garder à jour, une simple ligne dans la crontab système pour indiquer que le fichier sera regénéré tous les jours à 23h59 :

# echo '59  23    * * *   root    /root/bin/maphtpasswd.pl >/home/svn/dav_svn.passwd' >>/etc/crontab

Ne pas oublier de restreindre l'accès au fichier de mots de passe :

# chown root:www-data /home/svn/dav_svn.passwd
# chmod 640 /home/svn/dav_svn.passwd

Droits d'accès aux dépôts

Nous allons maintenant créer le fichier /home/svn/dav_svn.authz. Voici un exemple de fichier, dont la syntaxe parle d'elle-même :

##############################################################################
# Fichier de configuration des accès aux dépôts SVN
#
# Documentation :
#   http://svnbook.red-bean.com/en/1.4/svn.serverconfig.pathbasedauthz.html
##############################################################################


##############################################################################
# Définition des groupes
[groups]
toto-devs = utilisateur1, utilisateur4, utilisateur3


##############################################################################
# Par défaut, tous les utilisateurs peuvent accéder en lecture à tous les
# dépôts :
[/]
* = r


##############################################################################
# Dépôt « toto » :
[toto:/]
@toto-devs = rw
utilisateur8 = rw
[toto:/doc]
utilisateur10 = rw

Comme indiqué en commentaire, plus de détails sur la syntaxe de ce fichier sont fournis dans la documentation officielle de Subversion.

Note : Une fois le fichier créé, ou après une modification, il n'est pas nécessaire de redémarrer Apache : les changements se propageront au bout de quelques minutes.

Conclusion

Les utilisateurs peuvent maintenant accéder aux dépôts en utilisant l'URI https://serveur.example.com/svn/nom_du_dépôt/. Pour la suite, voir la page Gestion de versions : utilisation de base de Subversion.