This text is a work in progress—highly subject to change—and may not accurately describe any released version of the Apache™ Subversion® software. Bookmarking or otherwise referring others to this page is probably not such a smart idea. Please visit http://www.svnbook.com/ for stable versions of this book.
Nous avons déjà indiqué que Subversion est un logiciel de gestion de versions moderne et en réseau. Comme décrit dans la section intitulée « Notions générales de la gestion de versions », un dépôt sert de cœur de stockage pour les données suivies en versions et c'est par l'intermédiaire de copies de travail que les utilisateurs et les logiciels qu'ils manipulent interagissent avec les données. Dans cette section, nous allons commencer par introduire les différentes manières dont Subversion implémente la gestion de versions.
Subversion implémente le concept de dépôt comme tout autre logiciel de gestion de versions moderne. Contrairement à une copie de travail, un dépôt Subversion est une entité abstraite qui ne peut être manipulée pratiquement que par les bibliothèques et les propres outils de Subversion. Comme la plupart des interactions d'un utilisateur de Subversion se font par l'intermédiaire du client Subversion et qu'elles ont lieu dans le contexte de la copie de travail, ce livre traite en une grande partie de la copie de travail et des actions que l'on peut y appliquer. Pour les détails du dépôt, vous pouvez cependant vous référer au Chapitre 5, Administration d'un dépôt.
Avertissement | |
---|---|
Dans Subversion, l'entité que possède chaque utilisateur du logiciel — le répertoire des fichiers suivis en versions ainsi que les métadonnées qui permettent au système de tracer les données et de communiquer avec le serveur — s'appelle la copie de travail. Bien que d'autres logiciels de gestion de versions utilisent le terme de « dépôt » pour l'entité côté client, c'est à la fois incorrect et une source fréquente de confusion d'utiliser ce terme dans ce sens là dans le contexte de Subversion. Les copies de travail sont abordées plus loin, dans la section intitulée « Copies de travail ». |
Une opération svn commit propage (c'est-à-dire communique au serveur) les modifications d'un nombre quelconque de fichiers et de répertoires en une seule opération atomique. Par opération atomique, nous entendons que, soit toutes les modifications sont prises en compte par le dépôt, soit rien n'est pris en compte. Subversion essai d'être robuste dans ce concept d'atomicité, même en cas de plantage du programme, du système, de problèmes réseau ou d'actions de la part des autres utilisateurs.
Chaque fois que le dépôt accepte une propagation (c'est-à-dire une opération svn commit), il crée un nouvel état de l'arborescence du système de fichiers que l'on appelle révision. À Chaque révision est associé un entier naturel unique, immédiatement supérieur à l'entier associé à la révision précédente. La révision initiale d'un dépôt nouvellement créé à pour numéro 0 et n'est constituée que d'un répertoire racine vide.
La Figure 1.6, « L'évolution de l'arborescence au cours du temps » illustre une manière intéressante de se représenter le dépôt. Imaginez un tableau de numéros de révisions, commençant à zéro et s'étirant de la gauche vers la droite. À Chaque numéro de révision est suspendue une arborescence du système de fichiers, qui est une photo, un « instantané » (snapshot en anglais) du dépôt prise après une propagation.
les logiciels côté client de Subversion utilisent des URL pour identifier les fichiers et répertoires suivis en versions dans les dépôts Subversion. Pour leur grande partie, ces URL utilisent la syntaxe standard, permettant de spécifier le nom du serveur et le numéro de port directement dans l'URL.
Les URL de dépôts Subversion ne se limitent pas au domaine
http://
. Comme Subversion permet à ses
clients de dialoguer de différentes manières avec les dépôts,
les URL utilisées pour se connecter diffèrent subtilement en
fonction du protocole employé. La
Tableau 1.1, « Les différents motifs d'URL pour l'accès aux dépôts » décrit la
correspondance entre les différents motifs d'URL et les méthodes
d'accès aux dépôts. Pour plus de détails sur les options du
serveur Subversion, reportez-vous au
Chapitre 6, Configuration du serveur.
Tableau 1.1. Les différents motifs d'URL pour l'accès aux dépôts
Schéma | Méthode d'accès |
---|---|
file:///
|
Accès direct au dépôt (sur disque local) |
http://
|
Accès par protocole WebDAV sur un serveur Apache disposant d'un connecteur Subversion |
https://
|
Comme http:// , avec une
encapsulation SSL |
svn://
|
Accès via un protocole personnalisé à un
serveur svnserve |
svn+ssh://
|
Comme svn:// , avec une
encapsulation dans un tunnel SSH |
La gestion des URL par Subversion possède quelques particularités
qu'il convient de noter. Par exemple, les URL contenant la méthode
d'accès file://
(utilisée pour les dépôts locaux)
doivent spécifier, par convention, soit le nom de serveur
localhost
, soit pas de nom de
serveur :
D'autre part, les utilisateurs du procédé
file://
sur les plateformes Windows doivent
se servir d'une syntaxe qui est un « standard »
officieux pour accéder à leurs dépôts se trouvant sur la même
machine mais sur un disque différent du disque de travail
habituel du client. Les deux syntaxes de chemin d'URL suivantes
fonctionnent, X
étant le disque sur lequel
le dépôt se trouve :
Remarquez qu'une URL utilise des barres obliques
(/
) alors que la forme native (non-URL) d'un
chemin sous Windows utilise des barres obliques inversées
(\
).
Notez aussi que, dans la seconde syntaxe, vous devez entourer
l'URL de guillemets pour éviter que la barre verticale ne soit
interprétée comme un symbole de redirection (un
« pipe »).
Note | |
---|---|
Les URL Subversion |
Il faut noter que le client Subversion encode
automatiquement les URL en cas de besoin, exactement
comme le fait un navigateur web. Par exemple, l'URL
http://host/path with space/project/españa
— qui contient à la fois des espaces et des caractères
non ASCII— est automatiquement interprétée par Subversion
comme si vous aviez fourni
http://host/path%20with%20space/project/espa%C3%B1a
.
Si l'URL contient des espaces, prenez bien soin de les placer
entre guillemets dans la ligne de commande afin que le shell
traite le tout comme un unique argument du programme.
Il existe aussi une exception à la gestion des URL par
Subversion qui s'applique à la gestion des chemins locaux dans
beaucoup de contextes. Si le dernier élément de l'URL
ou du chemin contient le signe arobase (@
),
vous devez utiliser une syntaxe particulière, décrite dans
la section intitulée « Révisions pivots et révisions opérationnelles », afin que Subversion
prenne proprement en compte l'adresse de cette ressource.
Dans Subversion 1.6, une nouvelle notation, dite
syntaxe avec chapeau (^
) a été
introduite comme raccourci pour « l'URL du répertoire
racine du dépôt ». Par exemple, vous pouvez utiliser
^tags/gros-sandwich
pour désigner l'URL du
répertoire /tags/gros-sandwich
à la racine
du dépôt. Une telle URL est appelée URL
relative au dépôt. Remarquez que cette syntaxe d'URL
ne fonctionne que si votre répertoire de travail est une copie
de travail, le client texte interactif récupérant l'URL
de la racine du dépôt dans les métadonnées de la copie de
travail. Notez aussi que lorsque vous voulez faire référence
précisément au répertoire racine du dépôt, vous devez utiliser
^/
(avec la barre oblique terminale) et non
simplement ^
. Les utilisateurs sous Windows
ne doivent pas oublier que le caret est un caractère
d'échappement pour ce système. En conséquence, vous devez
utiliser un double caret ^^
si votre client
Subversion tourne sur une machine Windows.
Une copie de travail Subversion est une arborescence classique de répertoires de votre système local, contenant un ensemble de fichiers. Vous pouvez éditer ces fichiers comme vous le voulez et, s'il s'agit de code source, vous pouvez compiler votre programme à partir de ceux-ci de la façon habituelle. Votre copie de travail est votre espace de travail personnel privé : Subversion n'y incorpore jamais les changements d'autres personnes ni ne rend jamais disponibles vos propres changements à d'autres personnes tant que vous ne lui demanderez pas explicitement de le faire. Vous pouvez même avoir plusieurs copies de travail d'un même projet.
Après que vous ayez apporté quelques modifications aux fichiers de votre copie de travail et vérifié qu'elles fonctionnent correctement, Subversion vous fournit des commandes pour « publier » vos changements vers les autres personnes qui travaillent avec vous sur votre projet (en les transmettant au dépôt). Si d'autres personnes publient leurs propres modifications, Subversion vous fournit des commandes pour fusionner ces changements dans votre copie de travail (en les obtenant du dépôt). Remarquez que le dépôt central joue le rôle d'intermédiaire pour les changements de tout le monde dans Subversion ; les modifications ne passent pas directement d'une copie de travail à une autre copie de travail dans le processus classique.
Une copie de travail contient également quelques
fichiers supplémentaires, créés et gérés par Subversion, pour
l'aider à effectuer ces opérations. En particulier, chaque
copie de travail contient un sous-répertoire nommé
.svn
, aussi connu sous l'appellation de
répertoire administratif de votre copie
de travail. Les fichiers de ce répertoire administratif
permettent à Subversion d'identifier quels fichiers contiennent
des modifications non-publiées et quels fichiers sont périmés
vis-à-vis du travail des autres personnes.
Note | |
---|---|
Avant la version 1.7, Subversion plaçait un répertoire
|
Pour chaque fichier d'un répertoire de travail, Subversion
enregistre deux informations essentielles dans la zone
administrative .svn/
:
la révision sur laquelle votre fichier de travail est basé (qui est appelée la révision de travail du fichier) et
la date et l'heure de la dernière mise à jour de la copie locale depuis le dépôt
À partir de ces informations, en dialoguant avec le dépôt, Subversion est capable de déterminer dans lequel des quatre états suivants se trouve un fichier de travail
Le fichier est inchangé dans le répertoire de travail et aucune modification de ce fichier n'a été propagée vers le dépôt depuis sa révision de travail. Un appel à svn commit sur le fichier ne fait rien, un appel à svn update sur le fichier ne fait rien non plus.
Le fichier a été modifié dans le répertoire de travail et aucune modification du fichier n'a été propagée dans le dépôt depuis la dernière mise à jour. Il existe des modifications locales qui n'ont pas été propagées vers le dépôt, donc un appel à svn commit sur le fichier permet de publier vos modifications et un appel à svn update ne fait rien.
Le fichier n'a pas été modifié dans le répertoire de travail mais a changé dans le dépôt. Le fichier devra être mis à jour à un moment ou à un autre, pour l'amener au niveau de la dernière révision publique. Un appel à svn commit sur le fichier ne fait rien et un appel à svn update incorpore les dernières modifications dans votre copie de travail.
Le fichier a été modifié à la fois dans le répertoire de travail et dans le dépôt. Un appel à svn commit sur le fichier va échouer, renvoyant comme erreur « Périmé » (out-of-date en anglais). Le fichier doit d'abord être mis à jour ; un appel à svn update va tenter de fusionner les modifications publiques avec les modifications locales. Si Subversion ne parvient pas à réaliser automatiquement cette fusion de manière crédible, il va laisser à l'utilisateur le soin de résoudre le conflit.
Un dépôt Subversion contient bien souvent les fichiers (ou code source) de plusieurs projets ; habituellement, chaque projet est un sous-répertoire de l'arborescence du système de fichiers du dépôt. Dans cette situation, la copie de travail d'un utilisateur correspond à une sous-arborescence particulière du dépôt.
Par exemple, supposons que votre dépôt contienne deux
projets logiciels, paint
et
calc
. Chaque projet réside dans son propre
sous-répertoire racine, comme indiqué dans la Figure 1.7, « Système de fichiers du dépôt ».
Pour obtenir une copie de travail, vous devez
extraire une sous-arborescence du
répertoire (le terme « extraire »,
check out en anglais, peut vous
faire penser que cela a quelque chose à voir avec verrouiller
ou réserver des ressources, mais ce n'est pas le cas ;
cela crée simplement pour vous une copie privée du projet).
Par exemple, si vous extrayez /calc
, vous
obtenez une copie de travail qui ressemble à
ceci :
$ svn checkout http://svn.exemple.com/depot/calc A calc/Makefile A calc/entier.c A calc/bouton.c Révision 56 extraite. $ ls -A calc Makefile bouton.c entier.c .svn/ $
Les lettres A
qui s'affichent dans la
marge de gauche indiquent que Subversion est en train
d'ajouter des éléments dans votre copie de travail. Vous avez
désormais votre copie personnelle du répertoire
/calc
du dépôt, avec une entrée
supplémentaire, .svn
, qui contient des
informations complémentaires nécessaires à Subversion, comme
évoqué précédemment.
Supposons que vous fassiez des modifications à
bouton.c
. Comme le répertoire
.svn
se souvient de la date de
modification et du contenu du fichier original, Subversion
peut en déduire que vous avez modifié le fichier. Néanmoins,
Subversion ne rend pas vos modifications publiques tant que
vous ne lui dites pas de le faire. L'action de publication de
vos modifications est plus communément appelée
propagation (« commit » ou
check in en anglais et,
parfois, archivage ou
livraison en français) des
modifications au sein du dépôt.
Pour rendre publiques vos modifications, vous pouvez utiliser la commande Subversion svn commit :
$ svn commit bouton.c -m "Coquille corrigée dans bouton.c." Ajout bouton.c Transmission des données . Révision 57 propagée. $
À présent, vos modifications de
bouton.c
ont été propagées au sein du
dépôt, avec un commentaire décrivant ces changements
(« vous avez corrigé une coquille »). Si un
autre utilisateur extrait une copie de travail de
/calc/
, il verra vos modifications dans
la dernière version du fichier.
Supposons que vous ayez une collaboratrice, Sally, qui a
extrait une copie de travail de /calc
en
même temps que vous. Lorsque vous propagez votre modification
de bouton.c
, la copie de travail de Sally
reste inchangée ; Subversion ne modifie les copies de
travail qu'à la demande des utilisateurs.
Pour mettre son projet à jour, Sally peut demander à Subversion de mettre à jour (update en anglais) sa copie de travail, en utilisant la commande svn update. Cela va intégrer vos modifications dans sa copie de travail, ainsi que celles qui ont été envoyées par d'autres personnes depuis qu'elle l'avait extraite.
$ pwd /home/sally/calc $ ls -A Makefile bouton.c entier.c .svn/ $ svn update U bouton.c Actualisé à la révision 57. $
En sortie, la commande svn update
indique que Subversion a mis à jour le contenu de
bouton.c
. Remarquez que Sally n'a pas eu
besoin de spécifier quels fichiers devaient être mis à
jour ; Subversion utilise les informations contenues dans
le répertoire .svn
, ainsi que d'autres
informations en provenance du dépôt, pour décider quels
fichiers doivent être mis à jour.
Un principe général de Subversion est d'être aussi flexible que possible. Un type particulier de flexibilité est la capacité d'avoir une copie de travail contenant des fichiers et des répertoires avec un mélange de différents numéros de révision. Les copies de travail ne correspondent pas toujours à une révision unique du dépôt elles peuvent contenir des fichiers qui sont à des révisions différentes. Par exemple, supposons que vous extrayez une copie de travail d'un dépôt dont la révision la plus récente porte le numéro 4 :
calc/
Makefile:4
entier.c:4
bouton.c:4
Tel quel, le répertoire de travail correspond exactement
à la révision 4 du dépôt. Maintenant, supposons que vous
modifiez le fichier bouton.c
et que
vous propagiez cette modification. Si aucune autre propagation
n'a eu lieu entre temps, votre propagation crée la révision
5 du dépôt et votre copie de travail ressemble à :
calc/
Makefile:4
entier.c:4
bouton.c:5
Supposons que, à ce moment ci, Sally propage une
modification à entier.c
, créant ainsi la
révision 6. Si vous faites svn update pour
mettre à jour votre copie de travail, elle ressemble
à :
calc/
Makefile:6
entier.c:6
bouton.c:6
Les modifications apportées par Sally à
entier.c
apparaissent dans votre copie
de travail et vos modifications sont toujours présentes dans
bouton.c
. Dans cet exemple, le texte de
Makefile
est identique dans les révisions
4, 5 et 6 mais Subversion marque votre copie de travail
de Makefile
comme étant à la révision 6
pour indiquer qu'elle est à jour. Ainsi, quand vous effectuez
une mise à jour au niveau de la racine de votre copie de
travail, celle-ci correspond en général à une révision
donnée du dépôt.
Une des règles fondamentales de Subversion est que l'action de « pousser » ne déclenche pas une action de « tirer », ni l'inverse. Le simple fait que vous soyez prêt à soumettre vos nouvelles modifications au dépôt ne veut pas dire que vous êtes prêts à recevoir les modifications d'autres personnes. Et si vous avez de nouvelles modifications encore en cours, alors svn update fusionne élégamment les changements du dépôt avec les vôtres, plutôt que de vous forcer à les publier.
Le principal effet secondaire de cette règle est que la copie de travail a de la comptabilité supplémentaire à effectuer pour suivre les mélanges de révision et également être tolérante vis-à-vis de l'ensemble. Cela est rendu encore plus difficile par le fait que les répertoires eux-mêmes sont suivis en versions.
Par exemple, supposons que vous ayez une copie de
travail qui soit intégralement à la révision 10. Vous éditez
le fichier truc.html
et réalisez
ensuite un svn commit qui crée la
révision 15 dans le dépôt. Après que la propagation ait
réussi, nombreux sont ceux parmi les nouveaux utilisateurs
qui s'attendraient à ce que toute la copie de travail soit à
la révision 15, mais ce n'est pas le cas ! Un certain
nombre de modifications ont pu avoir lieu dans le dépôt
entre les révisions 10 et 15. Le client ne sait rien de ces
changements qui ont été apportés au dépôt, puisque vous
n'avez pas encore exécuté la commande
svn update et la commande
svn commit ne récupère pas les
nouvelles modifications. D'un autre côté, si la commande
svn commit téléchargeait automatiquement
les modifications les plus récentes, alors il serait
possible d'avoir toute la copie de travail à la révision
15 mais, dans ce cas, nous enfreindrions la règle
fondamentale selon laquelle « pousser » et
« tirer » doivent demeurer des actions
distinctes. Ainsi, la seule chose que le client Subversion
peut faire en toute sécurité est de marquer le fichier
truc.html
, et lui seulement, comme
étant à la révision 15. Le reste de la copie de travail
reste à la révision 10. Seule l'exécution de la commande
svn update permet de récupérer les
dernières modifications et de marquer la copie de travail
comme étant à la révision 15.
Le fait est qu'à chaque fois que
vous exécutez la commande svn commit,
votre copie de travail se retrouve composée d'un mélange de
révisions. Les éléments que vous venez juste de propager
sont marqués comme ayant un numéro de révision plus élevé
que tous les autres. Après plusieurs propagations (sans
mise à jour entre-temps), votre copie de travail va contenir
tout un mélange de révisions. Même si vous êtes la seule
personne à utiliser le dépôt, vous constaterez quand même
ce phénomène. Pour étudier votre propre mélange de révisions
de travail, utilisez la commande
svn status avec l'option
--verbose
(voir la section intitulée « Vue d'ensemble des changements effectués » pour plus
d'informations).
Souvent, les nouveaux utilisateurs n'ont pas du tout conscience que leur copie de travail contient des révisions mélangées. Cela peut être déroutant car beaucoup de commandes client sont sensibles à la révision de travail de l'élément qu'elles examinent. Par exemple, la commande svn log est utilisée pour afficher l'historique des modifications d'un fichier ou d'un répertoire (cf. la section intitulée « Historique des modifications »). Lorsque l'utilisateur appelle cette commande sur un objet de la copie de travail, il s'attend à obtenir l'historique complet de celui-ci. Mais si la révision de travail de l'objet est assez ancienne (souvent parce que svn update n'a pas été lancé depuis un certain temps), alors c'est l'historique de l'ancienne version de l'objet qui est affiché.
Si votre projet est suffisamment complexe, vous allez découvrir qu'il est parfois pratique d'effectuer un retour en arrière forcé (c'est-à-dire de faire une mise à jour vers une version plus ancienne que celle que vous avez déjà) sur certaines parties de votre copie de travail vers des révisions plus anciennes ; vous apprendrez comme le faire dans le Chapitre 2, Utilisation de base. Vous avez peut-être envie de tester une version précédente d'un sous-module contenu dans un sous-répertoire ou bien de comprendre comment un bogue est apparu pour la première fois dans un fichier donné. C'est le côté « machine à voyager dans le temps » d'un logiciel de gestion de versions, la fonctionnalité qui vous permet de déplacer n'importe quelle partie de votre copie de travail en avant ou en arrière dans le temps.
Quelle que soit la façon dont vous utilisez les mélanges de révision dans votre copie de travail, il existe des limites à cette flexibilité.
Premièrement, vous ne pouvez pas propager la suppression d'un fichier ou d'un répertoire qui n'est pas complètement à jour. Si une version plus récente de l'élément existe dans le dépôt, votre tentative de suppression est rejetée, afin de vous empêcher de détruire accidentellement des modifications dont vous n'aviez pas encore connaissance.
Deuxièmement, vous ne pouvez propager la modification des métadonnées d'un répertoire que si celui-ci est complètement à jour. Vous apprendrez comment associer des « propriétés » à des éléments dans le Chapitre 3, Sujets avancés. La révision de travail d'un répertoire définit un ensemble précis d'entrées et de propriétés et propager la modification d'une propriété d'un répertoire périmé risquerait de détruire des propriétés dont vous n'aviez pas encore connaissance.
Enfin, à partir de Subversion 1.7, vous ne pouvez pas utiliser par défaut une copie de travail à révisions mélangées comme cible d'une opération de fusion ; cette limitation a été introduite pour prévenir certains problèmes qui apparaissent dans ce cas.