Histoire des systèmes de contrôle de version



Dans cet article, nous comparons d'un point de vue technique les systèmes de contrôle de version les plus célèbres (à l'avenir, nous prévoyons d'élargir la liste):

  1. Première génération
  2. Deuxième génération
  3. Troisième génération

Les systèmes de contrôle de version (VCS) de première génération ont suivi les changements dans les fichiers individuels, et l'édition n'était prise en charge que localement et par un utilisateur à la fois. Les systèmes ont été construits sur l'hypothèse que tous les utilisateurs se connecteront à leurs comptes sur le même nœud Unix commun.

Le VCS de deuxième génération a introduit le support réseau, ce qui a conduit à des référentiels centralisés avec des versions «officielles» des projets. Ce fut un progrès significatif, car plusieurs utilisateurs pouvaient travailler avec le code en même temps, s'engageant dans le même référentiel central. Cependant, valide l'accès requis au réseau.

La troisième génération est constituée de VCS distribués, où toutes les copies du référentiel sont considérées comme égales, il n'y a pas de référentiel central. Cela ouvre la voie aux validations, aux branches et aux fusions qui sont créées localement sans accès au réseau et déplacées vers d'autres référentiels selon les besoins.

Chronologie de sortie de VCS


Pour le contexte, voici un graphique montrant les dates d'apparition de ces outils:



SCCS (Source Code Control System): première génération


SCCS est considéré comme l'un des premiers systèmes de contrôle de version à succès. Il a été développé en 1972 par Mark Rochkind des Bell Labs. Le système est écrit en C et conçu pour suivre les versions des fichiers source. De plus, cela a grandement facilité la recherche de sources d'erreurs dans le programme. L'architecture et la syntaxe de base de SCCS permettent de comprendre les racines des outils VCS modernes.

L'architecture


Comme la plupart des systèmes modernes, SCCS dispose d'un ensemble de commandes pour travailler avec des versions de fichiers:

  1. Fichiers d'archivage pour le suivi de l'historique dans SCCS.
  2. Extraire des versions spécifiques de fichiers pour révision ou compilation.
  3. Extraire des versions spécifiques pour l'édition.
  4. Présentation de nouvelles versions de fichiers ainsi que des commentaires expliquant les modifications.
  5. Ignorez les modifications apportées au fichier extrait.
  6. Changements importants de branchement et de fusion.
  7. Journal des modifications de fichiers.

Lors de l'ajout d'un fichier de suivi au SCCS, un type spécial de fichier est créé, appelé s- ou . Il est appelé fichier source, uniquement avec le préfixe s. et est stocké dans le sous-répertoire SCCS . Ainsi, pour le fichier test.txt , un fichier historique test.txt sera créé dans le répertoire ./SCCS/ . Au moment de la création, le fichier historique contient le contenu initial du fichier source, ainsi que certaines métadonnées qui permettent de suivre les versions. Les sommes de contrôle sont stockées ici pour garantir que le contenu n'a pas été modifié. Le contenu du fichier historique n'est ni compressé ni encodé (comme dans le VCS de prochaine génération).

Le contenu du fichier source étant désormais stocké dans le fichier historique, il peut être extrait dans le répertoire de travail pour être visualisé, compilé ou modifié. Vous pouvez apporter des modifications au fichier d'historique, telles que l'ajout de lignes, la modification et la suppression, ce qui augmente son numéro de version.

Les ajouts de fichiers ultérieurs ne stockent que les ou les modifications, et pas tout son contenu. Cela réduit la taille du fichier d'historique. Chaque delta est stocké dans un fichier historique dans une structure appelée - . Comme mentionné précédemment, le contenu réel d'un fichier est plus ou moins copié textuellement, avec des séquences d'échappement spéciales pour marquer le début et la fin des sections de contenu ajouté et supprimé. Étant donné que les fichiers d'historique SCCS n'utilisent pas la compression, ils sont généralement plus volumineux que le fichier réel dans lequel les modifications sont suivies. SCCS utilise une méthode appelée , qui garantit un temps de récupération constant quel que soit l'âge de la version récupérée, c'est-à-dire que les anciennes versions sont récupérées à la même vitesse que les nouvelles.

Il est important de noter que tous les fichiers sont suivis et enregistrés séparément. Il n'est pas possible de vérifier les changements dans plusieurs fichiers comme un seul bloc atomique, comme les commits dans Git. Chaque fichier suivi a son propre fichier d'historique, dans lequel son historique des modifications est stocké. Dans le cas général, cela signifie que les numéros de version des différents fichiers d'un projet ne correspondent généralement pas. Cependant, ces versions peuvent être acceptées en modifiant simultanément tous les fichiers du projet (sans même y apporter de réelles modifications) et en ajoutant tous les fichiers en même temps. Cela augmentera simultanément le numéro de version pour tous les fichiers, en les maintenant cohérents, mais notez que ce n'est pas la même chose que d'inclure plusieurs fichiers dans un seul commit, comme dans Git. Dans SCCS, un historique individuel est ajouté à chaque fichier, contrairement à un gros commit qui inclut toutes les modifications à la fois.

Lorsqu'un fichier est extrait pour modification dans SCCS, un verrou est placé dessus, afin que personne d'autre ne puisse le modifier. Cela empêche le remplacement des modifications par d'autres utilisateurs, mais limite également le développement, car à tout moment, un seul utilisateur peut travailler avec ce fichier.

SCCS prend en charge les branches qui stockent les séquences de modifications dans un fichier spécifique. Vous pouvez fusionner une branche avec la version d'origine ou avec une autre branche.

Équipes principales


Voici une liste des commandes SCCS les plus courantes.

  • sccs create <filename.ext> : ajoutez un nouveau fichier à SCCS et créez un nouveau fichier d'historique pour lui (par défaut dans le répertoire ./SCCS/ ).
  • sccs get <filename.ext> : extraire le fichier du fichier historique correspondant et le placer dans le répertoire de travail en mode lecture seule.
  • sccs edit <filename.ext> : extraire le fichier du fichier d'historique correspondant pour le modifier. Verrouillez le fichier historique afin que les autres utilisateurs ne puissent pas le modifier.
  • sccs delta <filename.ext> : ajoutez des modifications au fichier spécifié. Le système demandera un commentaire, enregistrera les modifications dans le fichier historique et libérera le verrou.
  • sccs prt <filename.ext> : affiche le journal des modifications du fichier surveillé.
  • sccs diffs <filename.ext> : affiche les différences entre la copie de travail actuelle du fichier et l'état du fichier lors de son extraction.

Pour plus d'informations sur les composants internes du SCCS, consultez le Guide d' Eric Allman et le Guide de l'utilitaire de programmation d'Oracle .

Exemple de fichier d'historique SCCS


 ^Ah20562 ^As 00001/00001/00002 ^Ad D 1.3 19/11/26 14:37:08 jack 3 2 ^Ac Here is a comment. ^Ae ^As 00002/00000/00001 ^Ad D 1.2 19/11/26 14:36:00 jack 2 1 ^Ac No. ^Ae ^As 00001/00000/00000 ^Ad D 1.1 19/11/26 14:35:27 jack 1 0 ^Ac date and time created 19/11/26 14:35:27 by jack ^Ae ^Au ^AU ^Af e 0 ^At ^AT ^AI 1 Hi there ^AE 1 ^AI 2 ^AD 3 This is a test of SCCS ^AE 2 ^AE 3 ^AI 3 A test of SCCS ^AE 3 

RCS (Revision Control System): première génération


RCS a été écrit en 1982 par Walter Tihey en C comme une alternative au système SCCS, qui à l'époque n'était pas open source.

L'architecture


RCS a beaucoup de points communs avec son prédécesseur, notamment:

  • Gestion des versions séparément pour chaque fichier.
  • Les modifications apportées à plusieurs fichiers ne peuvent pas être regroupées en un seul commit.
  • Les fichiers suivis ne peuvent pas être modifiés par plusieurs utilisateurs en même temps.
  • Aucun support réseau.
  • Les versions de chaque fichier suivi sont stockées dans le fichier historique correspondant.
  • Versions de branchement et de fusion pour les fichiers individuels uniquement.

Lorsqu'un fichier est ajouté pour la première fois au RCS, un fichier d'historique correspondant est créé pour lui dans le stockage local dans le répertoire local ./RCS/ . Une extension ,v , est ajoutée à ce fichier, c'est-à-dire qu'un fichier appelé test.txt sera suivi par un fichier appelé test.txt,v .

RCS utilise un schéma de delta inverse pour stocker les modifications. Lorsque vous ajoutez un fichier, un instantané complet de son contenu est enregistré dans le fichier historique. Lorsque le fichier est modifié et renvoyé à nouveau, un delta est calculé en fonction du contenu existant du fichier historique. L'ancienne image est supprimée et la nouvelle est enregistrée avec le delta pour revenir à l'ancien état. C'est ce qu'on appelle un , car pour récupérer une version plus ancienne, RCS prend la dernière version et applique séquentiellement des deltas jusqu'à ce qu'il atteigne la version souhaitée. Cette méthode vous permet de récupérer les versions actuelles très rapidement, car un instantané complet de la révision actuelle est toujours disponible. Cependant, plus la version est ancienne, plus la vérification prend du temps, car vous devez vérifier de plus en plus de deltas.

Dans SCCS, c'est différent: il faut le même temps pour extraire n'importe quelle version. De plus, la somme de contrôle n'est pas stockée dans les fichiers d'historique RCS, de sorte que l'intégrité des fichiers ne peut pas être garantie.

Équipes principales


Voici une liste des commandes RCS les plus courantes:

  • <filename.ext> : ajoutez un nouveau fichier au RCS et créez un nouveau fichier d'historique pour lui (par défaut dans le répertoire ./RCS/ ).
  • co <filename.ext> : extraire le fichier du fichier historique correspondant et le placer dans le répertoire de travail en mode lecture seule.
  • co -l <filename.ext> : extraire le fichier du fichier d'historique correspondant pour le modifier. Verrouillez le fichier historique afin que les autres utilisateurs ne puissent pas le modifier.
  • ci <filename.ext> : ajoutez des modifications de fichier et créez une nouvelle révision pour celui-ci dans le fichier d'historique correspondant.
  • merge <file-to-merge-into.ext> <parent.ext> <file-to-merge-from.ext> : fusionner les modifications de deux enfants modifiés du même fichier parent.
  • rcsdiff <filename.ext> : affiche les différences entre la copie de travail actuelle du fichier et l'état du fichier lors de son extraction.
  • rcsclean : supprime les fichiers de travail qui ne sont pas verrouillés.

Pour plus d'informations sur les composants RCS internes, consultez le manuel GNU RCS .

Exemple de fichier d'historique RCS


 head 1.2; access; symbols; locks; strict; comment @# @; 1.2 date 2019.11.25.05.51.55; author jstopak; state Exp; branches; next 1.1; 1.1 date 2019.11.25.05.49.02; author jstopak; state Exp; branches; next ; desc @This is a test. @ 1.2 log @Edited the file. @ text @hi there, you are my bud. You are so cool! The end. @ 1.1 log @Initial revision @ text @d1 5 a5 1 hi there @ 

CVS (Concurrent Versions System): deuxième génération


CVS a été créé par Dick Grun en 1986 pour ajouter la prise en charge réseau au contrôle de version. Il est également écrit en C et marque la naissance de la deuxième génération d'outils VCS, grâce à laquelle des équipes de développement dispersées géographiquement ont l'opportunité de travailler ensemble sur des projets.

L'architecture


CVS est une interface pour RCS, il a un nouvel ensemble de commandes pour interagir avec les fichiers d'un projet, mais sous le capot, le même format de fichier d'historique RCS et les commandes RCS sont utilisés. Pour la première fois, CVS a permis à plusieurs développeurs de travailler simultanément avec les mêmes fichiers. Ceci est implémenté à l'aide d'un modèle de référentiel centralisé. La première étape consiste à configurer un référentiel centralisé à l'aide de CVS sur le serveur distant. Les projets peuvent ensuite être importés dans le référentiel. Lorsqu'un projet est importé dans CVS, chaque fichier est converti en un fichier historique ,v et stocké dans un répertoire central: . Le référentiel est généralement situé sur un serveur distant, dont l'accès se fait via un réseau local ou Internet.

Le développeur reçoit une copie du module, qui est copiée dans le répertoire de travail de son ordinateur local. Dans ce processus, aucun fichier n'est bloqué, il n'y a donc pas de limite au nombre de développeurs qui peuvent travailler simultanément avec le module. Les développeurs peuvent modifier leurs fichiers et valider les modifications si nécessaire (validation). Si un développeur valide une modification, les autres développeurs doivent mettre à jour leurs copies de travail en utilisant le processus de fusion (généralement) automatisé avant de valider leurs modifications. Parfois, vous devez résoudre manuellement les conflits de fusion avant de valider. CVS offre également la possibilité de créer et de fusionner des branches.

Équipes principales


  • export CVSROOT=<path/to/repository> : définissez le répertoire racine du référentiel CVS, vous n'avez donc pas besoin de le spécifier dans chaque commande.
  • cvs import -m 'Import module' <module-name> <vendor-tag> <release-tag> : importez des répertoires avec des fichiers dans le module CVS. Avant de démarrer ce processus, accédez au répertoire racine du projet.
  • cvs checkout <module-name> : copiez le module dans le répertoire de travail.
  • cvs commit <filename.ext> : validez le fichier modifié dans le module du référentiel central.
  • cvs add <filename.txt> : ajoutez un nouveau fichier pour suivre les modifications.
  • cvs update : mettez à jour la copie de travail en fusionnant les modifications validées qui existent dans le référentiel central mais pas dans la copie de travail.
  • cvs status : affiche des informations générales sur la copie de travail extraite du module.
  • cvs tag <tag-name> <files> : ajoutez une balise à un fichier ou à un ensemble de fichiers.
  • cvs tag -b <new-branch-name> : créez une nouvelle branche dans le référentiel (vous devez l'extraire avant le travail local).
  • cvs checkout -r <branch-name> : extraire une branche existante vers le répertoire de travail.
  • cvs update -j <branch-to-merge> : fusionne une branche existante avec une copie de travail locale.

Pour plus d'informations sur les composants internes de CVS, consultez le manuel GNU CVS et l'article de Dick Grohn .

Exemple de fichier d'historique CVS


 head 1.1; branch 1.1.1; access ; symbols start:1.1.1.1 jack:1.1.1; locks ; strict; comment @# @; 1.1 date 2019.11.26.18.45.07; author jstopak; state Exp; branches 1.1.1.1; next ; commitid zsEBhVyPc4lonoMB; 1.1.1.1 date 2019.11.26.18.45.07; author jstopak; state Exp; branches ; next ; commitid zsEBhVyPc4lonoMB; desc @@ 1.1 log @Initial revision @ text @hi there @ 1.1.1.1 log @Imported sources @ text @@ 

SVN (Subversion): deuxième génération


Subversion a été créé en 2000 par Collabnet Inc. et est actuellement pris en charge par la Apache Software Foundation. Le système est écrit en C et conçu comme une solution centralisée plus fiable que CVS.

L'architecture


Comme CVS, Subversion utilise un modèle de référentiel centralisé. Les utilisateurs distants nécessitent une connexion réseau pour valider le référentiel central.

Subversion a introduit la fonctionnalité des validations atomiques avec la garantie que la validation est complètement réussie ou complètement annulée en cas de problème. Dans CVS, en cas de dysfonctionnement au milieu d'une validation (par exemple, en raison d'une défaillance du réseau), le référentiel peut rester dans un état endommagé et incohérent. De plus, une validation ou une version dans Subversion peut inclure plusieurs fichiers et répertoires. Ceci est important car il vous permet de suivre des ensembles de modifications connexes ensemble sous la forme d'un bloc groupé, et non séparément pour chaque fichier, comme dans les systèmes du passé.

Subversion utilise actuellement le système de fichiers FSFS (File System au sommet du File System). Ici, une base de données est créée avec la structure des fichiers et des répertoires qui correspondent au système de fichiers hôte. Une caractéristique unique de FSFS est qu'il est conçu pour suivre non seulement les fichiers et les répertoires, mais aussi leurs versions. Il s'agit d'un système de fichiers sensible au facteur temps. Les répertoires sont également des objets complets dans Subversion. Vous pouvez valider des répertoires vides sur le système, tandis que les autres (même Git) ne les remarquent pas.

Lorsque vous créez un référentiel Subversion, une base de données (presque) vide de fichiers et de dossiers est créée dans sa composition. Le répertoire db/revs est créé, qui stocke toutes les informations de suivi de version pour les fichiers ajoutés (validés). Chaque commit (qui peut inclure des modifications dans plusieurs fichiers) est stocké dans un nouveau fichier dans le répertoire revs , et il est donné un nom avec un identifiant numérique séquentiel commençant par 1. Le premier commit enregistre le contenu complet du fichier. Les futures validations du même fichier n'enregistreront que les modifications, également appelées ou deltas, pour économiser de l'espace. De plus, les deltas sont compressés à l'aide d'algorithmes de compression lz4 ou zlib pour réduire la taille.

Un tel système ne fonctionne que jusqu'à un certain point. Bien que les deltas économisent de l'espace, mais s'il y en a beaucoup, il faut beaucoup de temps pour l'opération, car tous les deltas doivent être traités pour recréer l'état actuel du fichier. Pour cette raison, par défaut, Subversion enregistre jusqu'à 1023 deltas par fichier, puis crée une nouvelle copie complète du fichier. Cela offre un bon équilibre de stockage et de vitesse.

SVN n'utilise pas le système de branchement et d'étiquetage habituel. Le modèle de référentiel Subversion standard contient trois dossiers à la racine:

  • trunk/
  • branches/
  • tags/

Le répertoire trunk/ est utilisé pour la version de production du projet. Le répertoire branches/ - pour stocker les sous-dossiers correspondant aux branches individuelles. Le répertoire tags/ sert à stocker des balises représentant des versions spécifiques (généralement importantes) d'un projet.

Équipes principales


  • svn create <path-to-repository> : crée un nouveau shell de référentiel vide dans le répertoire spécifié.
  • svn import <path-to-project> <svn-url> : importez le répertoire des fichiers dans le référentiel Subversion spécifié.
  • svn checkout <svn-path> <path-to-checkout> : copiez le référentiel dans le répertoire de travail.
  • svn commit -m 'Commit message' : valide un ensemble de fichiers et dossiers modifiés avec le message.
  • svn add <filename.txt> : ajoutez un nouveau fichier pour suivre les modifications.
  • svn update : mettez à jour la copie de travail en fusionnant les modifications validées qui existent dans le référentiel central mais pas dans la copie de travail.
  • svn status : affiche une liste des fichiers surveillés qui ont changé dans le répertoire de travail (le cas échéant).
  • svn info : informations générales sur la copie extraite.
  • svn copy <branch-to-copy> <new-branch-path-and-name> : créez une nouvelle branche en copiant une branche existante.
  • svn switch <existing-branch> : basculez le répertoire de travail vers une branche existante. Cela vous permettra de prendre des fichiers à partir de là.
  • svn merge <existing-branch> : fusionne la branche spécifiée avec la branche courante copiée dans le répertoire de travail. Veuillez noter que vous devrez vous engager ultérieurement.
  • svn log : affiche l'historique des validations et les messages correspondants pour la branche active.

Pour plus d'informations sur les composants internes de SVN, consultez Subversion Versioning .

Exemple de fichier d'historique SVN


 DELTA SVN^B^@^@ ^B ^A<89> hi there ENDREP id: 2-1.0.r1/4 type: file count: 0 text: 1 3 21 9 12f6bb1941df66b8f138a446d4e8670c 279d9035886d4c0427549863c4c2101e4a63e041 0-0/_4 cpath: /trunk/hi.txt copyroot: 0 / DELTA SVN^B^@^@$^B%^A¤$K 6 hi.txt V 15 file 2-1.0.r1/4 END ENDREP id: 0-1.0.r1/6 type: dir count: 0 text: 1 5 48 36 d84cb1c29105ee7739f3e834178e6345 - - cpath: /trunk copyroot: 0 / DELTA SVN^B^@^@'^B#^A¢'K 5 trunk V 14 dir 0-1.0.r1/6 END ENDREP id: 0.0.r1/2 type: dir pred: 0.0.r0/2 count: 1 text: 1 7 46 34 1d30e888ec9e633100992b752c2ff4c2 - - cpath: / copyroot: 0 / _0.0.t0-0 add-dir false false false /trunk _2.0.t0-0 add-file true false false /trunk/hi.txt L2P-INDEX ^A<80>@^A^A^A^M^H^@ä^H÷^Aé^FDÎ^Bzè^AP2L-INDEX ^A<91>^E<80><80>@^A?^@'2^@<8d>»Ý<90>^C§^A^X^@õ ½½^N= ^@ü<8d>Ôã^Ft^V^@<92><9a><89>Ã^E; ^@<8a>åw|I^@<88><83>Î<93>^L`^M^@ù<92>À^Eïú?^[^@^@657 6aad60ec758d121d5181ea4b81a9f5f4 688 75f59082c8b5ab687ae87708432ca406I 

Git: troisième génération


Le système Git a été développé en 2005 par Linus Torvalds (créateur de Linux). Il est écrit principalement en C en combinaison avec certains scripts de ligne de commande. Diffère de VCS par ses fonctions, sa flexibilité et sa vitesse. Torvalds a initialement écrit le système pour la base de code Linux, mais au fil du temps, sa portée s'est élargie et c'est aujourd'hui le système de contrôle de version le plus populaire au monde.

L'architecture


Git est un système distribué. Il n'y a pas de référentiel central: toutes les copies sont créées égales, ce qui est très différent du VCS de deuxième génération, où le travail est basé sur l'ajout et l'extraction de fichiers du référentiel central. Cela signifie que les développeurs peuvent échanger des modifications entre eux immédiatement avant de fusionner leurs modifications dans une branche officielle.

De plus, les développeurs peuvent apporter leurs modifications à la copie locale du référentiel à l'insu des autres référentiels. Cela permet des validations sans être connecté à un réseau ou à Internet. Les développeurs peuvent travailler localement hors ligne, jusqu'à ce qu'ils soient prêts à partager leur travail avec d'autres. À ce stade, les modifications sont envoyées à d'autres référentiels pour vérification, test ou déploiement.

Lorsqu'un fichier est ajouté pour le suivi dans Git, il est compressé à l'aide de l'algorithme de compression zlib . Le résultat est haché à l'aide de la fonction de hachage SHA-1. Cela donne un hachage unique qui correspond spécifiquement au contenu de ce fichier. Git le stocke dans la , qui se trouve dans un dossier caché .git/objects . Le nom de fichier est le hachage généré et le fichier contient du contenu compressé. Ces fichiers sont appelés et sont créés chaque fois qu'un nouveau fichier (ou une version modifiée d'un fichier existant) est ajouté au référentiel.

Git implémente un index intermédiaire, qui agit comme une zone intermédiaire pour les modifications en cours de préparation pour la validation. À mesure que de nouvelles modifications sont préparées, leur contenu compressé est référencé dans un fichier d'index spécial, qui prend la forme d'un objet .Une arborescence est un objet Git qui associe des objets blob à leurs vrais noms de fichier, autorisations de fichier et liens vers d'autres arborescences et représente ainsi l'état d'un ensemble spécifique de fichiers et de répertoires. Lorsque toutes les modifications pertinentes sont préparées pour la validation, l'arborescence d'index peut être validée dans le référentiel qui crée l'objet dans la base de données des objets Git. Le commit fait référence à l'arborescence d'en-tête pour une version spécifique, ainsi qu'à l'auteur du commit, l'adresse e-mail, la date et le message du commit. Chaque commit stocke également un lien vers son ou ses commit (s) parent.Ainsi, au fil du temps, un historique du développement du projet est créé.

Comme déjà mentionné, tous les objets Git - blobs, arbres et commits - sont compressés, hachés et stockés dans la base de données d'objets en fonction de leurs hachages. Ils s'appellent (objets lâches). Aucune différence n'est utilisée ici pour économiser de l'espace, ce qui rend Git très rapide, car le contenu complet de chaque version du fichier est disponible en tant qu'objet gratuit. Cependant, certaines opérations, telles que l'envoi de validations dans un référentiel distant, le stockage d'un très grand nombre d'objets ou l'exécution manuelle de la commande de récupération de place Git, entraînent le reconditionnement des objets . Dans le processus de compression, des différences inverses sont calculées, qui sont compressées pour éliminer la redondance et réduire la taille. En conséquence, des fichiers .packavec le contenu de l'objet sont créés et pour chacun d'eux un fichier .idx(ou index) est créé avec un lien vers les objets emballés et leur emplacement dans le fichier de commandes.

Lorsque des branches sont déplacées vers ou récupérées à partir de référentiels distants, ces fichiers de commandes sont transférés sur le réseau. Lors de l'étirement ou de l'extraction de branches, les fichiers de package sont décompressés pour créer des objets libres dans le référentiel d'objets.

Équipes principales


  • git init: initialise le répertoire courant en tant que référentiel Git (un dossier caché .gitet son contenu sont créés).
  • git clone <git-url> : Téléchargez une copie du référentiel Git à l'URL spécifiée.
  • git add <filename.ext> : ajouter un fichier non suivi ou modifié à la zone de transit (crée les enregistrements correspondants dans la base de données d'objets).
  • git commit -m 'Commit message' : valider un ensemble de fichiers et dossiers modifiés avec un message de validation.
  • git status : affiche l'état du répertoire de travail, de la branche actuelle, des fichiers non suivis, des fichiers modifiés, etc.
  • git branch <new-branch> : crée une nouvelle branche basée sur la branche extraite actuelle.
  • git checkout <branch> : extraire la branche spécifiée dans le répertoire de travail.
  • git merge <branch> : fusionne la branche spécifiée avec la branche actuelle, qui est extraite dans le répertoire de travail.
  • git pull : Mettez à jour la copie de travail en combinant les modifications validées qui existent dans le référentiel distant, mais pas dans la copie de travail.
  • git push : empaqueter des objets gratuits pour les validations locales de la branche active dans des fichiers de package et les transférer vers un référentiel distant.
  • git log : affiche l'historique des validations et les messages correspondants pour la branche active.
  • git stash : enregistre toutes les modifications non validées du répertoire de travail dans le cache pour une récupération ultérieure.

Si vous voulez savoir comment fonctionne le code Git, consultez le Guide de démarrage Git . Pour plus d'informations sur les composants internes, consultez le chapitre correspondant dans le livre Pro Git .

Exemple de blob, d'arborescence et de commit git


Blob avec un hachage 37d4e6c5c48ba0d245164c4e10d5f41140cab980:

 hi there 

Objet d'arbre avec un hachage b769f35b07fbe0076dcfc36fd80c121d747ccc04:

 100644 blob 37d4e6c5c48ba0d245164c4e10d5f41140cab980hi.txt 

Hash commit dc512627287a61f6111705151f4e53f204fbda9b:

 tree b769f35b07fbe0076dcfc36fd80c121d747ccc04 author Jacob Stopak 1574915303 -0800 committer Jacob Stopak 1574915303 -0800 Initial commit 

Mercurial: troisième génération


Mercurial a été créé en 2005 par Matt McCall et écrit en Python. Il est également conçu pour héberger la base de code Linux, mais Git a finalement été choisi pour cette tâche. Il s'agit du deuxième système de contrôle de version le plus populaire, bien qu'il soit utilisé beaucoup moins fréquemment.

L'architecture


Mercurial est également un système distribué qui permet à n'importe quel nombre de développeurs de travailler avec leur copie du projet indépendamment des autres. Mercurial utilise bon nombre des mêmes technologies que Git, y compris la compression et le hachage SHA-1, mais il le fait différemment.

Lorsqu'un nouveau fichier est validé pour le suivi dans Mercurial, un fichier correspondant est créé pour lui revlogdans un répertoire caché .hg/store/data/. Vous pouvez considérer le fichier revlog(journal des modifications) comme une version mise à niveau dans les anciens VCS comme CVS, RCS et SCCS. Contrairement à Git, qui crée un nouveau blob pour chaque version de chaque fichier préparé, Mercurial crée simplement une nouvelle entrée de revlog pour ce fichier. Pour économiser de l'espace, chaque nouvel enregistrement contient uniquement le delta de la version précédente. Lorsque le nombre seuil de deltas est atteint, l'instantané complet du fichier est à nouveau enregistré. Cela réduit le temps de recherche lors du traitement d'un grand nombre de deltas pour restaurer une version spécifique d'un fichier.

Chaque revlog est nommé en fonction du fichier qu'il suit, mais avec l'extension .iou .d. Les fichiers .dcontiennent un delta compressé. Les fichiers .isont utilisés comme index pour suivre rapidement différentes versions dans les fichiers.d. Pour les petits fichiers avec peu de modifications, les index et le contenu sont stockés dans des fichiers .i. Les entrées Revlog sont compressées pour les performances et hachées pour l'identification. Ces valeurs de hachage sont nommées nodeid.

À chaque commit, Mercurial garde une trace de toutes les versions des fichiers de ce commit dans ce qu'on appelle un . Le manifeste est également un fichier revlog - il stocke les entrées correspondant à certains états du référentiel. Au lieu d'avoir un contenu de fichier séparé, comme revlog, le manifeste stocke une liste de noms de fichiers et de noeuds qui déterminent quelles versions du fichier existent dans la version du projet. Ces entrées de manifeste sont également compressées et hachées. Les valeurs de hachage sont également appelées nodeid.

Enfin, Mercurial utilise un autre type de revlog appelé changelog, c'est-à-dire un journal des modifications. Il s'agit d'une liste d'entrées qui associent chaque commit aux informations suivantes:

  • manifeste nodeid: un ensemble complet de versions de fichiers qui existent à un moment donné.
  • un ou deux nodeid pour les commit parents: cela permet à Mercurial de construire une chronologie ou une branche de l'historique du projet. Un ou deux ID parents sont stockés en fonction du type de validation (normal ou fusion).
  • Commit Author
  • Date de validation
  • Message de validation

Chaque entrée du journal des modifications génère également un hachage appelé son nodeid.

Équipes principales


  • hg init: initialise le répertoire courant en tant que référentiel Mercurial (crée un dossier caché .hget son contenu).
  • hg clone <hg-url> : Téléchargez une copie du référentiel Mercurial à l'URL spécifiée.
  • hg add <filename.ext> : Ajoutez un nouveau fichier pour suivre les modifications.
  • hg commit -m 'Commit message' : validez l'ensemble des fichiers et dossiers modifiés avec le message de validation.
  • hg status : affiche les informations relatives à l'état du répertoire de travail, les fichiers non suivis, les fichiers modifiés, etc.
  • hg update <revision> : extraire la branche spécifiée dans le répertoire de travail.
  • hg merge <branch> : fusionne la branche spécifiée avec la branche courante extraite dans le répertoire de travail.
  • hg pull : Téléchargez les nouvelles versions à partir d'un référentiel distant, mais ne les fusionnez pas dans un répertoire de travail.
  • hg push : Transférez les nouvelles versions vers le référentiel distant.
  • hg log : Afficher l'historique des validations et des messages associés pour la branche active.

Exemples de fichiers Mercurial


Manifeste:

 hey.txt208b6e0998e8099b16ad0e43f036ec745d58ec04 hi.txt74568dc1a5b9047c8041edd99dd6f566e78d3a42 

Journal des modifications (journal des modifications):

 b8ee947ce6f25b84c22fbefecab99ea918fc0969 Jacob Stopak 1575082451 28800 hey.txt Add hey.txt 

Informations supplémentaires sur l'appareil Mercurial:

Source: https://habr.com/ru/post/fr478752/


All Articles