Wie importiere ich ein vorhandenes Git-Repository in ein anderes?

476

Ich habe ein Git-Repository in einem Ordner namens XXX und ich habe ein zweites Git-Repository namens YYY .

Ich möchte das XXX- Repository als Unterverzeichnis mit dem Namen ZZZ in das JJJ- Repository importieren und den gesamten Änderungsverlauf von XXX zu JJJ hinzufügen .

Ordnerstruktur vor:

├── XXX
│   ├── .git
│   └── (project files)
└── YYY
    ├── .git
    └── (project files)

Ordnerstruktur nach:

YYY
├── .git  <-- This now contains the change history from XXX
├──  ZZZ  <-- This was originally XXX
│    └── (project files)
└──  (project files)

Kann das gemacht werden oder muss ich auf Submodule zurückgreifen?

Vijay Patel
quelle
2
Auf Github ist es nun möglich , diese von der Web - Schnittstelle zu tun , wenn Sie einen neuen Repo erstellen
bgcode
Mögliches Duplikat von Wie fügst du zwei Git-Repositorys zusammen?
BuZZ-dEE

Antworten:

430

Der wahrscheinlich einfachste Weg wäre, das XXX- Zeug in einen Zweig in YYY zu ziehen und es dann in master zusammenzuführen:

In JJJ :

git remote add other /path/to/XXX
git fetch other
git checkout -b ZZZ other/master
mkdir ZZZ
git mv stuff ZZZ/stuff                      # repeat as necessary for each file/dir
git commit -m "Moved stuff to ZZZ"
git checkout master                
git merge ZZZ --allow-unrelated-histories   # should add ZZZ/ to master
git commit
git remote rm other
git branch -d ZZZ                           # to get rid of the extra branch before pushing
git push                                    # if you have a remote, that is

Ich habe das gerade mit ein paar meiner Repos versucht und es funktioniert. Im Gegensatz zu Jörgs Antwort können Sie das andere Repo nicht weiter verwenden, aber ich glaube, Sie haben das sowieso nicht angegeben.

Hinweis: Da dies ursprünglich im Jahr 2009 geschrieben wurde, hat git die in der Antwort unten erwähnte Zusammenführung von Teilbäumen hinzugefügt. Ich würde diese Methode wahrscheinlich heute verwenden, obwohl diese Methode natürlich immer noch funktioniert.

ebneter
quelle
1
Vielen Dank. Ich habe eine leicht modifizierte Version Ihrer Technik verwendet: Ich habe auf XXX einen 'Staging'-Zweig erstellt, in dem ich den ZZZ-Ordner erstellt und das' Zeug 'in ihn verschoben habe. Dann habe ich XXX in YYY zusammengeführt.
Vijay Patel
1
Das hat bei mir super funktioniert. Die einzigen Änderungen, die ich vorgenommen habe, waren: 1) "git branch -d ZZZ" vor dem Push, weil ich nicht wollte, dass dieser temporäre Zweig herumhängt. 2) "git push" gab mir den Fehler: "Keine Refs gemeinsam und keine angegeben; nichts tun. Vielleicht sollten Sie einen Zweig wie 'master' angeben." (Der Ursprung, auf den ich drängte, war ein leeres, nacktes Repository.) Aber "git push --all" funktionierte wie ein Champion.
CrazyPyro
1
Ich wollte nur den ZZZ-Ordner plus Verlauf im JJJ-Repo haben: Ich wollte das ursprüngliche XXX-Repo und den ZZZ-Zweig im JJJ-Repo löschen. Ich habe festgestellt, dass der ZZZ-Zweig gelöscht wurde, da @CrazyPyro vorgeschlagen hat, den Verlauf zu entfernen. Um ihn beizubehalten, habe ich den ZZZ-Zweig vor dem Löschen mit dem Master zusammengeführt.
Oli Studholme
4
@SebastianBlask Ich habe gerade mit zwei meiner Repos damit rumgespielt und festgestellt, dass es einen fehlenden Schritt gibt, den niemand jemals bemerkt hat, obwohl ich seit Jahren positive Stimmen dazu habe. :-) Ich habe erwähnt , dass es in Master zusammengeführt wird, habe es aber nicht gezeigt. Bearbeiten Sie es jetzt ...
ebneter
2
Sie könnten so etwas hinzufügen, wenn Sie Dateien in Ihren Unterordner verschieben: git mv $(ls|grep -v <your foldername>) <your foldername>/ Dies kopiert alle Dateien und Ordner in Ihren neuen Ordner
Serup
367

Wenn Sie den genauen Festschreibungsverlauf des zweiten Repositorys beibehalten und daher auch in Zukunft problemlos Upstream-Änderungen zusammenführen möchten, finden Sie hier die gewünschte Methode. Dies führt dazu, dass der unveränderte Verlauf des Teilbaums in Ihr Repo importiert wird, plus ein Zusammenführungs-Commit, um das zusammengeführte Repository in das Unterverzeichnis zu verschieben.

git remote add XXX_remote <path-or-url-to-XXX-repo>
git fetch XXX_remote
git merge -s ours --no-commit --allow-unrelated-histories XXX_remote/master
git read-tree --prefix=ZZZ/ -u XXX_remote/master
git commit -m "Imported XXX as a subtree."

Sie können Upstream-Änderungen folgendermaßen verfolgen:

git pull -s subtree XXX_remote master

Git findet selbst heraus, wo sich die Wurzeln befinden, bevor die Zusammenführung durchgeführt wird, sodass Sie das Präfix bei nachfolgenden Zusammenführungen nicht angeben müssen.

Der Nachteil ist, dass im zusammengeführten Verlauf die Dateien nicht fixiert sind (nicht in einem Unterverzeichnis). Als Ergebnis git log ZZZ/awerden Ihnen alle Änderungen (falls vorhanden) mit Ausnahme derjenigen im zusammengeführten Verlauf angezeigt. Du kannst tun:

git log --follow -- a

Dadurch werden jedoch keine anderen Änderungen als in der zusammengeführten Historie angezeigt.

Mit anderen Worten, wenn Sie die ZZZDateien im Repository nicht ändern , XXXmüssen Sie --followeinen nicht festgelegten Pfad angeben . Wenn Sie sie in beiden Repositorys ändern, haben Sie zwei Befehle, von denen keiner alle Änderungen anzeigt.

Git-Versionen vor 2.9 : Sie müssen die --allow-unrelated-historiesOption nicht an übergeben git merge.

Die Methode in der anderen Antwort, die read-treeden merge -s oursSchritt verwendet und überspringt, unterscheidet sich effektiv nicht vom Kopieren der Dateien mit cp und Festschreiben des Ergebnisses.

Die ursprüngliche Quelle war der Hilfeartikel "Subtree Merge" von github . Und noch ein nützlicher Link .

ColinM
quelle
9
Dies scheint die Geschichte nicht erhalten zu haben. Wenn ich eine der git logvon mir eingezogenen Dateien durchführe, sehe ich nur das Commit für die einzelne Zusammenführung und nichts von seinem vorherigen Leben im anderen Repo? Git 1.8.0
Anentropic
8
Aha! Wenn ich den alten Pfad der importierten Datei verwende, dh das Unterverzeichnis weglasse, in das sie importiert wurde, gibt mir das Git-Protokoll den Commit-Verlauf, z. B. git log -- myfileanstelle vongit log -- rack/myfile
Anentropic
2
@FrancescoFrassinelli, ist das nicht wünschenswert? Das Einbringen der Historie ist ein Merkmal dieser Methode.
Patrickvacek
4
@FrancescoFrassinelli, wenn Sie keine Geschichte wollen, warum nicht einfach eine reguläre Kopie machen? Ich versuche herauszufinden, was Sie zu dieser Methode ziehen würde, wenn nicht die Geschichte - das ist der einzige Grund, warum ich diese Methode verwendet habe!
Patrickvacek
7
Seit Git 2.9 benötigen Sie die Option, --allow-unrelated-historieswenn Sie die Zusammenführung durchführen.
stuXnet
112

git-subtreeist ein Skript, das genau für diesen Anwendungsfall entwickelt wurde, bei dem mehrere Repositorys zu einem zusammengeführt werden, während der Verlauf beibehalten wird (und / oder der Verlauf von Teilbäumen aufgeteilt wird, obwohl dies für diese Frage irrelevant zu sein scheint). Es wird seit Release 1.7.11 als Teil des Git-Baums verteilt .

Verwenden Sie Folgendes, um ein Repository <repo>bei der Revision <rev>als Unterverzeichnis zusammenzuführen :<prefix>git subtree add

git subtree add -P <prefix> <repo> <rev>

git-subtree implementiert die Strategie zum Zusammenführen von Teilbäumen benutzerfreundlicher.

Für Ihren Fall würden Sie im Repository JJJ Folgendes ausführen:

git subtree add -P ZZZ /path/to/XXX.git master

Der Nachteil ist, dass im zusammengeführten Verlauf die Dateien nicht fixiert sind (nicht in einem Unterverzeichnis). Als Ergebnis git log ZZZ/awerden Ihnen alle Änderungen (falls vorhanden) mit Ausnahme derjenigen im zusammengeführten Verlauf angezeigt. Du kannst tun:

git log --follow -- a

Dadurch werden jedoch keine anderen Änderungen als in der zusammengeführten Historie angezeigt.

Mit anderen Worten, wenn Sie die ZZZDateien im Repository nicht ändern , XXXmüssen Sie --followeinen nicht festgelegten Pfad angeben . Wenn Sie sie in beiden Repositorys ändern, haben Sie zwei Befehle, von denen keiner alle Änderungen anzeigt.

Mehr dazu hier .

kynan
quelle
4
Wenn Sie ein Verzeichnis zum Zusammenführen anstelle eines nackten Repositorys oder einer Remote- git subtree add -P name-of-desired-prefix ~/location/of/git/repo-without-.git branch-name
Datei haben
2
Noob-Erfahrung: git (Version 2.9.0.windows.1) antwortet "fatal: mehrdeutiges Argument 'HEAD': unbekannte Revision oder Pfad nicht im Arbeitsbaum", als ich dies in einem frisch initialisierten, lokalen, nicht nackten Repository versuchte. Aber es hat gut funktioniert, nachdem ich das neue Repository wirklich in Betrieb genommen hatte, dh nachdem ich eine einfache Datei hinzugefügt und den normalen Weg festgeschrieben hatte.
Stein
Hat wunderbar für mein Szenario funktioniert.
Johnny Utahh
Oh das ist fantastisch.
Dwjohnston
Ich habe @Tatsh Vorschlag verwendet und es hat bei mir funktioniert
Carmine Tambascia
49

Es gibt eine bekannte Instanz davon im Git-Repository selbst, die in der Git-Community zusammenfassend als " die coolste Zusammenführung aller Zeiten " bezeichnet wird (nach der Betreffzeile, die Linus Torvalds in der E-Mail an die Git-Mailingliste verwendet hat, die dies beschreibt verschmelzen). In diesem Fall war die gitkGit-GUI, die jetzt Teil von Git ist, eigentlich ein separates Projekt. Linus hat es geschafft, dieses Repository auf diese Weise mit dem Git-Repository zusammenzuführen

  • Es erscheint im Git-Repository so, als ob es immer als Teil von Git entwickelt worden wäre.
  • Die ganze Geschichte wird intakt gehalten und
  • Es kann weiterhin unabhängig in seinem alten Repository entwickelt werden, wobei Änderungen einfach git pullbearbeitet werden.

Die E-Mail die Schritte enthält zum Reproduzieren benötigt, aber es ist nicht für schwache Nerven: Erstens, Linus schrieb Git, so dass er wahrscheinlich ein bisschen mehr darüber weiß als du oder ich, und zweitens, das fast 5 Jahren war vor und Git hat sich seitdem erheblich verbessert , vielleicht ist es jetzt viel einfacher.

Insbesondere denke ich, dass man heutzutage in diesem speziellen Fall ein Gitk-Submodul verwenden würde.

Jörg W Mittag
quelle
3
Übrigens. Die Strategie, die für nachfolgende Zusammenführungen verwendet wird (falls vorhanden), wird als Teilbaumzusammenführung bezeichnet , und es gibt ein git-subtreeTool von Drittanbietern , das Ihnen dabei helfen kann: github.com/apenwarr/git-subtree
Jakub Narębski
Danke, das habe ich vergessen. Die subtreeZusammenführungsstrategie, insbesondere in Verbindung mit dem git-subtreeTool, ist eine nette, vielleicht sogar überlegene Alternative zu Submodulen.
Jörg W Mittag
12

Der einfache Weg, dies zu tun, ist die Verwendung des Git-Format-Patches.

Angenommen, wir haben 2 Git-Repositories foo und bar .

foo enthält:

  • foo.txt
  • .git

Bar enthält:

  • bar.txt
  • .git

und wir wollen mit foo enden, das die Bar enthält und diese Dateien enthält:

  • foo.txt
  • .git
  • foobar / bar.txt

Also, um das zu tun:

 1. create a temporary directory eg PATH_YOU_WANT/patch-bar
 2. go in bar directory
 3. git format-patch --root HEAD --no-stat -o PATH_YOU_WANT/patch-bar --src-prefix=a/foobar/ --dst-prefix=b/foobar/
 4. go in foo directory
 5. git am PATH_YOU_WANT/patch-bar/*

Und wenn wir alle Nachrichten-Commits von bar neu schreiben möchten, können wir dies tun, z. B. unter Linux:

git filter-branch --msg-filter 'sed "1s/^/\[bar\] /"' COMMIT_SHA1_OF_THE_PARENT_OF_THE_FIRST_BAR_COMMIT..HEAD

Dadurch wird am Anfang jeder Festschreibungsnachricht "[bar]" hinzugefügt.

Damien R.
quelle
Wenn das ursprüngliche Repository Verzweigungen und Zusammenführungen enthielt, git amschlägt dies wahrscheinlich fehl.
Adam Monsen
1
Minor gotcha: git am entfernt alles [ ]aus der Commit-Nachricht. Sie sollten also einen anderen Marker verwenden als[bar]
HRJ
Hat bei mir nicht funktioniert. Erhalten "Fehler: foobar / mySubDir / test_host1: existiert nicht im Index. Die Kopie des fehlgeschlagenen Patches befindet sich in: /home/myuser/src/proj/.git/rebase-apply/patch Wenn Sie dieses Problem behoben haben Führen Sie "git am --continue" aus. Dies geschah nach dem Anwenden von 11 Patches (von 60).
Oligofren
1
Dieser Blog hat eine ähnliche Antwort auf eine etwas andere Frage (nur ausgewählte Dateien verschieben).
Jesse Glick
Ich sehe einen Nachteil: Alle Commits werden dem HEAD des Ziel-Repositorys hinzugefügt.
CSchulz
8

Diese Funktion klont das Remote-Repo in das lokale Repo-Verzeichnis. Nach dem Zusammenführen werden alle Commits gespeichert und git logdie ursprünglichen Commits und die richtigen Pfade angezeigt:

function git-add-repo
{
    repo="$1"
    dir="$(echo "$2" | sed 's/\/$//')"
    path="$(pwd)"

    tmp="$(mktemp -d)"
    remote="$(echo "$tmp" | sed 's/\///g'| sed 's/\./_/g')"

    git clone "$repo" "$tmp"
    cd "$tmp"

    git filter-branch --index-filter '
        git ls-files -s |
        sed "s,\t,&'"$dir"'/," |
        GIT_INDEX_FILE="$GIT_INDEX_FILE.new" git update-index --index-info &&
        mv "$GIT_INDEX_FILE.new" "$GIT_INDEX_FILE"
    ' HEAD

    cd "$path"
    git remote add -f "$remote" "file://$tmp/.git"
    git pull "$remote/master"
    git merge --allow-unrelated-histories -m "Merge repo $repo into master" --edit "$remote/master"
    git remote remove "$remote"
    rm -rf "$tmp"
}

Wie benutzt man:

cd current/package
git-add-repo https://github.com/example/example dir/to/save

Wenn Sie ein wenig Änderungen vornehmen, können Sie sogar Dateien / Verzeichnisse von zusammengeführtem Repo in verschiedene Pfade verschieben, zum Beispiel:

repo="https://github.com/example/example"
path="$(pwd)"

tmp="$(mktemp -d)"
remote="$(echo "$tmp" | sed 's/\///g' | sed 's/\./_/g')"

git clone "$repo" "$tmp"
cd "$tmp"

GIT_ADD_STORED=""

function git-mv-store
{
    from="$(echo "$1" | sed 's/\./\\./')"
    to="$(echo "$2" | sed 's/\./\\./')"

    GIT_ADD_STORED+='s,\t'"$from"',\t'"$to"',;'
}

# NOTICE! This paths used for example! Use yours instead!
git-mv-store 'public/index.php' 'public/admin.php'
git-mv-store 'public/data' 'public/x/_data'
git-mv-store 'public/.htaccess' '.htaccess'
git-mv-store 'core/config' 'config/config'
git-mv-store 'core/defines.php' 'defines/defines.php'
git-mv-store 'README.md' 'doc/README.md'
git-mv-store '.gitignore' 'unneeded/.gitignore'

git filter-branch --index-filter '
    git ls-files -s |
    sed "'"$GIT_ADD_STORED"'" |
    GIT_INDEX_FILE="$GIT_INDEX_FILE.new" git update-index --index-info &&
    mv "$GIT_INDEX_FILE.new" "$GIT_INDEX_FILE"
' HEAD

GIT_ADD_STORED=""

cd "$path"
git remote add -f "$remote" "file://$tmp/.git"
git pull "$remote/master"
git merge --allow-unrelated-histories -m "Merge repo $repo into master" --edit "$remote/master"
git remote remove "$remote"
rm -rf "$tmp"

Hinweise
Pfade werden über ersetzt. sedStellen Sie daher sicher, dass sie nach dem Zusammenführen in den richtigen Pfaden verschoben wurden.
Der --allow-unrelated-historiesParameter existiert nur seit git> = 2.9.

Andrey Izman
quelle
2
Installieren Sie für OS X-Benutzer, gnu-seddamit die git-add-repoFunktion funktioniert. Nochmals vielen Dank Andrey!
Ptaylor
7

Basierend auf diesem Artikel hat die Verwendung von Teilbaum für mich funktioniert und nur die zutreffende Historie wurde übertragen. Hier posten, falls jemand die Schritte benötigt (stellen Sie sicher, dass Sie die Platzhalter durch die für Sie zutreffenden Werte ersetzen):

Teilen Sie den Unterordner in Ihrem Quell-Repository in einen neuen Zweig auf

git subtree split --prefix=<source-path-to-merge> -b subtree-split-result

in Ihrem Ziel-Repo im Zweig für geteilte Ergebnisse zusammenführen

git remote add merge-source-repo <path-to-your-source-repository>
git fetch merge-source-repo
git merge -s ours --no-commit merge-source-repo/subtree-split-result
git read-tree --prefix=<destination-path-to-merge-into> -u merge-source-repo/subtree-split-result

Überprüfen Sie Ihre Änderungen und legen Sie fest

git status
git commit

Vergiss es nicht

Bereinigen Sie, indem Sie den subtree-split-resultZweig löschen

git branch -D subtree-split-result

Entfernen Sie die Fernbedienung, die Sie hinzugefügt haben, um die Daten aus dem Quell-Repo abzurufen

git remote rm merge-source-repo

Alex
quelle
3

Eine weitere Antwort hinzufügen, da ich denke, dass dies etwas einfacher ist. Ein Pull von repo_dest wird in repo_to_import ausgeführt und dann ein Push --set-upstream url: repo_dest master wird ausgeführt.

Diese Methode hat bei mir funktioniert, indem ich mehrere kleinere Repos in ein größeres importiert habe.

So importieren Sie: repo1_to_import to repo_dest

# checkout your repo1_to_import if you don't have it already 
git clone url:repo1_to_import repo1_to_import
cd repo1_to_import

# now. pull all of repo_dest
git pull url:repo_dest
ls 
git status # shows Your branch is ahead of 'origin/master' by xx commits.
# now push to repo_dest
git push --set-upstream url:repo_dest master

# repeat for other repositories you want to import

Benennen oder verschieben Sie Dateien und Verzeichnisse an die gewünschte Position im ursprünglichen Repo, bevor Sie den Import durchführen. z.B

cd repo1_to_import
mkdir topDir
git add topDir
git mv this that and the other topDir/
git commit -m"move things into topDir in preparation for exporting into new repo"
# now do the pull and push to import

Die unter dem folgenden Link beschriebene Methode hat diese Antwort inspiriert. Ich mochte es, weil es einfacher schien. Aber Vorsicht! Es gibt Drachen! https://help.github.com/articles/importing-an-external-git-repository verschiebt git push --mirror url:repo_dest Ihren lokalen Repo-Verlauf und -Status auf remote (URL: repo_dest). ABER es löscht die alte Geschichte und den Zustand der Fernbedienung. Spaß folgt! : -E

gaoithe
quelle
1

Ich wollte in meinem Fall nur einige Dateien aus dem anderen Repository (XXX) importieren. Der Teilbaum war zu kompliziert für mich und die anderen Lösungen funktionierten nicht. Das habe ich getan:

ALL_COMMITS=$(git log --reverse --pretty=format:%H -- ZZZ | tr '\n' ' ')

Auf diese Weise erhalten Sie eine durch Leerzeichen getrennte Liste aller Commits, die sich auf die Dateien auswirken, die ich importieren wollte (ZZZ), und zwar in umgekehrter Reihenfolge (möglicherweise müssen Sie --follow hinzufügen, um auch Umbenennungen zu erfassen). Ich ging dann in das Ziel-Repository (JJJ), fügte das andere Repository (XXX) als Remote hinzu, holte es ab und schließlich:

git cherry-pick $ALL_COMMITS

Wenn Sie alle Commits zu Ihrem Zweig hinzufügen, haben Sie alle Dateien mit ihrem Verlauf und können mit ihnen alles tun, was Sie wollen, als wären sie schon immer in diesem Repository.

Sebastian Blask
quelle
1

Siehe Basisbeispiel in diesem Artikel und berücksichtigen Sie eine solche Zuordnung für Repositorys:

  • A<-> YYY,
  • B <-> XXX

Entfernen Sie nach allen in diesem Kapitel beschriebenen Aktivitäten (nach dem Zusammenführen) den Zweig B-master:

$ git branch -d B-master

Drücken Sie dann die Änderungen.

Für mich geht das.

VeLKerr
quelle
0

Ich war in einer Situation, in der ich gesucht habe, -s theirsaber diese Strategie gibt es natürlich nicht. Meine Geschichte war, dass ich ein Projekt auf GitHub gegabelt hatte und jetzt aus irgendeinem Grund mein lokales masternicht mit zusammengeführt werden konnteupstream/master obwohl ich keine lokalen Änderungen an diesem Zweig vorgenommen hatte. (Ich weiß wirklich nicht, was dort passiert ist - ich glaube, Upstream hat hinter den Kulissen vielleicht ein paar schmutzige Stöße gemacht?)

Was ich am Ende tat, war

# as per https://help.github.com/articles/syncing-a-fork/
git fetch upstream
git checkout master
git merge upstream/master
....
# Lots of conflicts, ended up just abandonging this approach
git reset --hard   # Ditch failed merge
git checkout upstream/master
# Now in detached state
git branch -d master # !
git checkout -b master   # create new master from upstream/master

Jetzt ist my masterwieder synchron mit upstream/master(und Sie können das oben Gesagte für jeden anderen Zweig wiederholen, den Sie ebenfalls ähnlich synchronisieren möchten).

Tripleee
quelle
1
Ein git reset --hard upstream/masterMitarbeiter in Ihrer masterZweigstelle würde den Job erledigen. Auf diese Weise verlieren Sie nicht den lokalen Zweigkonflikt - Dinge wie den Standard-Upstream.
Tomékwi
0

Ich kann eine andere Lösung (Alternative zu Git-Submodulen ) für Ihr Problem vorschlagen - das Gil-Tool (Git-Links)

Es ermöglicht die Beschreibung und Verwaltung komplexer Abhängigkeiten von Git-Repositorys.

Außerdem bietet es eine Lösung für das Abhängigkeitsproblem der rekursiven Git-Submodule .

Angenommen, Sie haben die folgenden Projektabhängigkeiten: Beispiel eines Git-Repository-Abhängigkeitsdiagramms

Anschließend können Sie eine .gitlinksDatei mit einer Beschreibung der Repositorys definieren:

# Projects
CppBenchmark CppBenchmark https://github.com/chronoxor/CppBenchmark.git master
CppCommon CppCommon https://github.com/chronoxor/CppCommon.git master
CppLogging CppLogging https://github.com/chronoxor/CppLogging.git master

# Modules
Catch2 modules/Catch2 https://github.com/catchorg/Catch2.git master
cpp-optparse modules/cpp-optparse https://github.com/weisslj/cpp-optparse.git master
fmt modules/fmt https://github.com/fmtlib/fmt.git master
HdrHistogram modules/HdrHistogram https://github.com/HdrHistogram/HdrHistogram_c.git master
zlib modules/zlib https://github.com/madler/zlib.git master

# Scripts
build scripts/build https://github.com/chronoxor/CppBuildScripts.git master
cmake scripts/cmake https://github.com/chronoxor/CppCMakeScripts.git master

Jede Zeile beschreibt Git Link im folgenden Format:

  1. Eindeutiger Name des Repositorys
  2. Relativer Pfad des Repositorys (gestartet vom Pfad der .gitlinks-Datei)
  3. Git-Repository, das im git-Klonbefehl Repository-Zweig zum Auschecken verwendet wird
  4. Leere oder mit # begonnene Zeilen werden nicht analysiert (als Kommentar behandelt).

Schließlich müssen Sie Ihr Root-Beispiel-Repository aktualisieren:

# Clone and link all git links dependencies from .gitlinks file
gil clone
gil link

# The same result with a single command
gil update

Als Ergebnis klonen Sie alle erforderlichen Projekte und verknüpfen sie ordnungsgemäß miteinander.

Wenn Sie alle Änderungen in einem Repository mit allen Änderungen in untergeordneten verknüpften Repositorys festschreiben möchten, können Sie dies mit einem einzigen Befehl tun:

gil commit -a -m "Some big update"

Pull, Push-Befehle funktionieren auf ähnliche Weise:

gil pull
gil push

Das Gil-Tool (Git-Links) unterstützt die folgenden Befehle:

usage: gil command arguments
Supported commands:
    help - show this help
    context - command will show the current git link context of the current directory
    clone - clone all repositories that are missed in the current context
    link - link all repositories that are missed in the current context
    update - clone and link in a single operation
    pull - pull all repositories in the current directory
    push - push all repositories in the current directory
    commit - commit all repositories in the current directory

Weitere Informationen zum Abhängigkeitsproblem von rekursiven Git-Submodulen .

Chronoxor
quelle
0

Lassen Sie mich Namen a(anstelle von XXXund ZZZ) und b(anstelle vonYYY ) verwenden, da dadurch die Beschreibung etwas leichter zu lesen ist.

Sagen Sie bitte Repository zusammenführen möchten ain b(Ich gehe davon aus sie nebeneinander angeordnet sind):

cd a
git filter-repo --to-subdirectory-filter a
cd ..
cd b
git remote add a ../a
git fetch a
git merge --allow-unrelated-histories a/master
git remote remove a

Hierfür müssen Sie git-filter-repoinstalliert haben ( filter-branchwird davon abgeraten ).

Ein Beispiel für das Zusammenführen von zwei großen Repositorys, wobei eines davon in einem Unterverzeichnis abgelegt wird: https://gist.github.com/x-yuri/9890ab1079cf4357d6f269d073fd9731

Mehr dazu hier .

x-yuri
quelle
-1

Ich kenne keinen einfachen Weg, das zu tun. Sie könnten dies tun:

  1. Verwenden Sie git filter-branch, um ein ZZZ-Superverzeichnis zum XXX-Repository hinzuzufügen
  2. Verschieben Sie den neuen Zweig in das JJJ-Repository
  3. Verbinden Sie den geschobenen Zweig mit dem Stamm von YYY.

Ich kann mit Details bearbeiten, wenn das ansprechend klingt.

Walter Mundt
quelle
-2

Ich denke, Sie können dies mit 'git mv' und 'git pull' tun.

Ich bin ein fairer Idiot - seien Sie also vorsichtig mit Ihrem Haupt-Repository -, aber ich habe es nur in einem temporären Verzeichnis versucht und es scheint zu funktionieren.

Benennen Sie zuerst die Struktur von XXX so um, dass sie dem Aussehen entspricht, wenn sie sich in JJJ befindet:

cd XXX
mkdir tmp
git mv ZZZ tmp/ZZZ
git mv tmp ZZZ

Jetzt sieht XXX so aus:

XXX
 |- ZZZ
     |- ZZZ

Verwenden Sie nun 'git pull', um die Änderungen abzurufen:

cd ../YYY
git pull ../XXX

Jetzt sieht JJJ so aus:

YYY
 |- ZZZ
     |- ZZZ
 |- (other folders that already were in YYY)
Aaron
quelle