web-dev-qa-db-fra.com

Comment rebaser un référentiel Git sur un autre?

J'avais un référentiel Git (A) qui contient le développement d'un projet jusqu'à un certain point. Ensuite, j'ai perdu la clé USB sur laquelle ce dépôt A était activé. Heureusement, j'avais une sauvegarde du dernier commit, donc je pouvais créer un nouveau référentiel (B) plus tard où j'importais l'état du dernier projet et continuer le développement. Maintenant, j'ai récupéré cette clé USB perdue, j'ai donc deux référentiels Git.

Je pense que je dois juste rebaser le repo B sur le repo A d'une manière ou d'une autre, mais je ne sais pas comment faire, peut-être en utilisant fetch/pull et rebase?

57
kroimon

Si A et B ne sont pas le même dépôt (vous avez créé B en utilisant la dernière copie de travail que vous aviez), vous devez utiliser un greffon pour prétendre qu'ils ont un historique commun.

Supposons que vous ayez ajouté A comme télécommande pour B selon réponse de VonC , et le dépôt ressemble à ceci1:

~/B$ git tnylog 
* 6506232 (HEAD, master) Latest work on B
* 799d6ae Imported backup from USB stick
~/B$ git tnylog A/master
* 33b5b16 (A/master) Head of A
* 6092517 Initial commit

Créez une greffe indiquant à la racine de B que son parent est le chef de A:

echo '799d6aeb41095a8469d0a12167de8b45db02459c 33b5b16dde3af6f5592c2ca6a1a51d2e97357060' \
 >> .git/info/grafts

Maintenant, les deux historiques ci-dessus apparaîtront comme un lorsque vous demanderez l'historique de B. Rendre le greffon permanent est un simple git filter-branch sans argument. Après la branche de filtrage, cependant, vous n'êtes sur aucune branche, vous devriez donc git branch -D master; git checkout -b master.


1git tnylog = git log --oneline --graph --decorate

62
Josh Lee

Si A et B sont le même dépôt (les premiers SHA1 sont communs), vous pouvez:

  • déclarer A comme télécommande pour B: git remote add A /path/to/A
  • git fetch A à mettre à jour toutes les branches A distantes sur le référentiel B
  • git checkout dev (sur B, où vous développez)
  • git rebase A/devBranch pour rejouer B (c'est-à-dire ce que vous développez ou re-développez à partir de votre sauvegarde) en plus de A/devBranch (le développement que vous avez perdu). Un peu comme ça SO question .

La dernière étape vous permet de synchroniser votre dev avec celui que vous avez perdu.
Mais en fait, une fois que vous avez récupéré de A, vous avez terminé: B contient maintenant l'historique " all " (celui que vous avez perdu et votre travail actuel)

29
VonC

Tout d'abord, commencez par faire un clone fonctionnel du repo A.

Ensuite, tirez simplement dessus depuis B et fusionnez. Vous préférerez peut-être créer une nouvelle branche, y tirer, puis fusionner les deux branches. Vous pourriez également avoir besoin d'un indicateur de forçage; J'ai fait des choses comme ça dans Mercurial (greffer deux référentiels apparemment indépendants l'un de l'autre) et il a besoin de "-f".

2
crazyscot