Maintain git repo inside another git repo
GitVersion ControlGithubGit Problem Overview
Here's what I'd like:
REPO-A
/.git
/otherFiles
/REPO-B
/.git
/moreFiles
I want to be able to push all of REPO-A's contents to REMOTE-A and only REPO-B to REMOTE-B.
Possible?
Git Solutions
Solution 1 - Git
It sounds like you want to use Git submodules.
> Git addresses this issue using submodules. Submodules allow you to keep a Git repository as a subdirectory of another Git repository. This lets you clone another repository into your project and keep your commits separate.
Solution 2 - Git
I have always used symlinks to maintain two separate and distinct repos.
Solution 3 - Git
Yes, you can do exactly what you're asking with the file hierarchy you drew. Repo-B will be independant and have no knowledge of Repo-A. Repo-A will track all changes in it's own files and Repo-B's files.
However, I would not recommend doing this. Every time you change files and commit in Repo-B you'll have to commit in Repo-A. Branching in Repo-B will mess with Repo-A and branching in Repo-A will be wonky (trouble removing folders, etc.). Submodules are definitely the way to go.
Solution 4 - Git
You can use a .gitignore
file in the parent A
repository (ignoring B
), but firstly making sure that the B
repository is not currently being tracked: commit the parent .gitignore
before adding the second B
repository.
Solution 5 - Git
You can achieve what you want (that REPO-A repo contains all the files, including those in folder REPO-B instead of only a reference) by using "git-subrepo":
https://github.com/ingydotnet/git-subrepo
It still works if some of your contributors don't have the subrepo command installed; they will see the complete folder structure but won't be able to commit changes to the subrepos.
Solution 6 - Git
Lots of choices, the best one depends on your purpose:
-
if want to keep the parent as a container of different apps, and some of them could eventually become repos, just use bare Git to treat them as different repos (no submodules no subrepos). No need to learn more git features.
-
if you want to keep the parent as a "project" of different repos and feeling safe on managing access for different collaborators, the solution of using symbolic links for different repo folders is a good option. Again, no need to learn more git features.
Explanation:
If one of the app becomes a repo, just git init
there, add the remote repo and forget git tutorials and spend that time for the apps. It just work, and in the parent repo the commits can still be atomic for the rest of apps, and sometimes there will be extra commits,yes, but you do not need to commit parentA for each commit of repoB. You can apply different permisions on both repos (although parent can have repoB code unless you use .gitignore to ignore the repoB) .
Solution 7 - Git
In my case, I didn't want to merge repo A with repo B so the repo inside the repo works perfectly fine. Just carefully update the .gitignore
for both repos
.
And make sure to stay inside the respective dir while using git commands.
Some quick notes:
- Both
repos
will act independently and thus can not be merged. - Parent repo will contain all the changes inside subfolders and files
unless added to its
.gitignore
- Child repo will contain all the
changes inside its subfolders and files unless added to its
.gitignore
. - Parent and Child's
.gitignore
files will act independently of each other. So, for example, if you want to ignore a file in the child repo but want to push it in the parent repo, just add the file in the child repo's.gitignore
- In case both
repos
need to be merged, the above guide will be considered invalid. So, the overall case should be studied properly to use the repo inside the repo strategy.
Thank you for all the helpful answers above. Feel free to update my answer if needed.
Solution 8 - Git
There is one more way this could be handled. You can place the repos(that are submodules) as each separate independent repository. And can create softlinks to the submodule repos inside the master repo.
$ ls
$ main-repo submodule1 submodule2
$ ln -s submodule1 main-repo/submodule1
$ ln -s submodule2 main-repo/submodule2
Once files inside main-repo are listed, the submodules SoftLinks are listed
$ ls main-repo/
$ other-files submodule1 submodule2