====== SVN - Subversion ====== Un concurrent de CVS Lien: http://artis.imag.fr/~Xavier.Decoret/resources/svn/index.html Liens: [[http://ericreboisson.developpez.com/tutoriels/install-subversion/|subversion pour windows et aide]]\\ [[http://svnbook.red-bean.com/nightly/en/svn.intro.quickstart.html|Quick Start(en)]]\\ [[http://www.linux-gull.ch/gull/cours/archives/svn/svn-course.pdf|Cours svn (trés complet)]]\\ [[http://svnbook.red-bean.com/en/1.1/ch05s03.html|Chapter 5. Repository Administration]]\\ # apt-get update # apt-get install subversion $ svn --version svn, version 1.3.2 (r19776) compilé Aug 15 2006, 08:51:49 Copyright (C) 2000-2006 CollabNet. Subversion is open source software, see http://subversion.tigris.org/ This product includes software developed by CollabNet (http://www.Collab.Net/). Les modules d'accès à un dépôt (RA) suivants sont disponibles : * ra_dav : Module for accessing a repository via WebDAV (DeltaV) protocol. - handles 'http' scheme - handles 'https' scheme * ra_svn : Module pour accéder à un dépôt avec le protocole réseau propre de svn - handles 'svn' scheme * ra_local : Module for accessing a repository on local disk. - handles 'file' scheme ===== Quick start ===== ==== Repertoire des "repository" ==== Creer le répertoire de stockage, en attribuant le groupe ''src''. # mkdir /var/lib/svn Creer un lien a la racine, pour clarifier la suite. # ln -s /var/lib/svn /svn Par exemple, creer un sous-repertoire ''dev''. # mkdir /svn/dev Créer le user ''svn'' # adduser svn --system --disabled-login --no-create-home --group On l'utilisera par la suite, car il sera le seul autorisé a manipuler directement les repository ==== Installer le daemon "svnserve" ==== (C'est beaucoup plus cool avec ''inetd''... voir plus loin)\\ D'abord preparer un repertoire pour recevoir le PID (generer par le user ''svn''). # mkdir /var/run/svn # chown :svn /var/run/svn # chmod g+ws /var/run/svn Installer un scripte comme ça là: ''/etc/init.d/svnserve-daemon'' #!/bin/sh NAME="svnserve-daemon" DESC="subversion" SVNDAEMON="/usr/bin/svnserve" [ -x $SVNDAEMON ] || exit 0 PIDFILE="/var/run/svn/svnserve.pid" LISTENPORT="3690" SVNPATH="/svn" SVNUSER="svn:svn" start() { echo -n "Starting $DESC: $NAME" start-stop-daemon --start --quiet --exec "$SVNDAEMON" \ -c "$SVNUSER" -- -d --listen-port "$LISTENPORT" -r "$SVNPATH" --pid-file "$PIDFILE" echo "." } stop() { echo -n "Stopping $DESC: $NAME" start-stop-daemon --stop --quiet --pidfile "$PIDFILE" # effacer le fichier PID (je prefere) [ ! -e "$PIDFILE" ] || rm "$PIDFILE" echo "." } case "$1" in start) start ;; stop) stop ;; restart) stop sleep 1 start ;; *) echo "Usage ... {start|restart|stop} " >&2 exit 64 ;; esac exit 0 Noter que ce daemon "voit" tout les "repository" dans ''/svn''. \\ Faire en sorte que ça fonctionne au reboot. # update-rc.d svnserve-daemon defaults ==== Creer un "repository" ==== === create === == methode 1 == $ su # su -s /bin/bash -c "svnadmin create /svn/dev/myproject" svn == methode 2 == $ su # svnadmin create /svn/dev/myproject Cela doit appartenir au user ''svn''. # chown -R svn:svn /svn/dev/myproject === password === A ce stade, si le daemon tourne, la terre entière qui passe par le port TCP (3690) peut modifier le projet!\\ Mettre des restrictions: # cd /svn/dev/myproject/conf # vi passwd ... [users] thierry = mot_de_passe ... Editer aussi ... # vi svnserve.conf ... [general] anon-access = none auth-access = write ... password-db = passwd Et voila un repository protégé... mais je crois que les mots de passe voyagent en clair (à vérifier) ==== Importe un "project" existant... ==== (Ou simplement créer un "project" vide)\\ D'abord, créer un répertoire provisoire, par exemple dans ''**~/tmp/myproject**'' : $ cd ~/tmp $ mkdir myproject $ cd myproject Créeons dans ce répertoire, une arborescence comme suit: $ mkdir trunk $ mkdir branches $ mkdir tags Laisser **tags** et **branches** vide. (y parait que c'est bien...). Copier les fichiers du projet dans **trunk**: $ cp -Rp ~/quelque/part/* ./trunk/ Et enfin, on importe tout cela dans **subversion** : $ cd ~/tmp $ la myproject total 20 drwxr-xr-x 5 thierry thierry 4096 2006-09-11 01:02 . drwxr-xr-x 3 thierry thierry 4096 2006-09-11 01:04 .. drwxr-xr-x 2 thierry thierry 4096 2006-09-11 01:02 branches drwxr-xr-x 2 thierry thierry 4096 2006-09-11 01:02 tags drwxr-xr-x 4 thierry thierry 4096 2006-04-26 23:19 trunk On est bien là où il faut... le répertoire parent de mon projet... Importons donc: $ svn import myproject svn://localhost/dev/myproject -m "initial import" Domaine d'authentification : ffffffff-DDDD-4444-8888-77777777 Mot de passe pour 'thierry' : Ajout myproject/trunk ... Révision 1 propagée. Rappel: on passe par le daemon qui tourne en 'localhost', sinon, on aurait pu faire (si on avait les droits d'écrire dans ''/svn/dev/bourse'') $ svn import myproject file:///svn/dev/myproject -m "initial import for test" Ajout myproject/trunk ... Révision 1 propagée. ==== Où sont les mots de passe... ==== Par la suite, les mots de passe ne seront plus demandé ! Ils sont stockés dans: ~/.subversion/auth/svn.simple ==== Recuperer des fichiers tout neuf du repository: ==== Ce mettre dans le répertoire **parent** du projet: Via le daemon: $ svn checkout svn://localhost/dev/myproject/trunk myproject ou plus généralement: $ svn checkout svn://Adresse_IP/dev/myproject/trunk myproject Sans le daemon: $ svn checkout file:///svn/dev/myproject/trunk myproject Un repertoire **myproject** est créé avec tous les fichiers associés (de **trunk**). Modifions des choses... $ vi ... etc... \\ $ svn update $ svn commit -m "j'ai fait des p'tains de modifs!" Envoi monprojet.c Transmission des données . Révision 3 propagée. $ svn add newfile.c $ svn update $ svn commit -m "un nouveau fichier" Ajout newfile.c Transmission des données . Tiens, des infos: $ svn info file:///svn/dev/myproject Chemin : myproject URL : file:///svn/dev/myproject Racine du dépôt : file:///svn/dev/test1 UUID du dépôt : xxxx Révision : 4 Type de noeud : répertoire Auteur de la dernière modification : thierry Révision de la dernière modification : 4 Date de la dernière modification: 2006-09-11 01:39:56 +0200 (lun, 11 sep 2006) Ou bien aussi: $ svn info svn://10.20.1.111/dev/myproject ... Pour recuperer la revision 3 (par exemple), et dans le repertoire **r3**: $ svn checkout file:///svn/dev/test1/myproject r3 -r 3 Utiliser **svn status** pour voir ce qu'on modifié localement. (alors que **svn update** fait une verification avec le **repository**) $ svn log C'est bien aussi. ===== svnlook ===== Regarder l'arbre: $ svnlook tree /svn/dev Imprimer un fichier de l'arbre $ svnlook cat /svn/dev labo/book/trunk/ex2.c Mais si on est dans un répertoire 'checkouted' on peut aussi faire: $ svn info ou $ svn ls -v ou $ svn cat lefichier Annuler toutes les modifications locales: $ svn revert PATH Et on revient a l'etat du dernier 'update' ou 'checkout' Ce qui a été modifié: $ svn log [PATH] -v En cas de deplacement d'un repository: $ svn switch --relocate FROM_URL TO_URL ===== Installer en serveur avec SSH ===== ==== droits ==== Il faut préalablement s'assurer que l'utilisateur aura les droits de lire et/ou modifier le repository. Pour repartir des exemples ci-dessus: # chmod -R g+ws /svn/dev/myproject Et # adduser thierry svn ==== Cas simple ==== C'est fort simple, il n'y a rien (?) a faire sur le serveur, l'authentification par SSH est suffisante. Donc sur le client, faire un truc du genre: $ svn checkout svn+ssh://thierry@k7/svn/dev/app/trunk app Et aprés la demande du mot de passe 3 fois (et oui!) on a enfin recupéré les fichiers qui sont dans le répertoire **app**. Ensuite, on peut modifier les fichiers etc... et faire les commandes habituelles: $ cd app $ svn update $ svn commit -m "j'ai fait des trucs" Et a chaque fois que necessaire, un passe est demandé. ==== SSH sur un autre port ==== Sur le client, editer le fichier **~/.subversion/config** et ajouter cela dans la section [tunnels] : k7 = ssh -p 5322 Alors a l'invocation de **svn+k7**, **ssh** sera appellé avec le paramètre **-p 5322** qui est le port ouvert pour SSH... Waouh... $ svn checkout svn+k7://thierry@k7/svn/dev/app/trunk app Et c'est relativement long, et ca demande 3 fois le mot de passe... ===== svnserve et inetd ===== C'est finalement mieux et plus simple qu'un daemon.\\ Editer le fichier ''/etc/inetd.conf'' et inserer: svn stream tcp nowait svn /usr/bin/svnserve svnserve -i -r /svn Puis forcer le rechargement du fichier de conf en faisant: # ps aux | grep inetd root 3209 0.0 0.0 1748 576 ? Ss May21 0:00 /usr/sbin/inetd Et enfin: # kill -HUP 3209 (ou ''invoke-rc.d openbsd-inetd reload'') :!: Si vous ne trouvez pas "inetd", c'est peut-être simplement parce que ce daemon ne s'est pas donné la peine de resté chargé (car la conf ne le necessitait pas); donc: # /etc/init.d/openbsd-inetd restart Restarting internet superserver: inetd Et voila. ===== Sauver et restaurer ===== Utiliser le jeu de commande **dump** et **load** avec **svnadmin**. Extraire un dump dans un fichier: $ svnadmin dump /svn/dev/app >app-dump.svn Ensuite, pour l'exemple, on cree un nouveau **repository**: $ svnadmin create /svn/dev/new-app Et puis on charge dedans: $ cat app-dump.svn | svnadmin load /svn/dev/new-app ===== Deplacer ===== Aprés un crash, la bouillie du répertoire **''/svn''** a été deporté sur un serveur distant... Mais voila que mes trunks, ne sont plus a jour et un **''svn checkout''** est exclus. Et puis de toutes les maniéres: $ svn update svn: Impossible d'ouvrir une session ra_local pour l'URL svn: Le dépôt 'file:///svn/dev/labo/sudo2/trunk' n'a pu être ouvert Tu m'etonnes: le repository est par là maintenant: svn://debcave/dev/labo/sudo2/trunk Alors je fais:\\ (sous réserve:) $ svn cleanup et enfin: $ svn switch --relocate file:///svn/dev/labo/sudo2/trunk svn://debcave/dev/labo/sudo2/trunk Et voila !