1

I have following dir stucture

root
root/framework (Yii)
root/protected/messages

All of this folder must be separate git repos

What I want to do is

  1. root and root/framework must be separate repos. But

    • root/framework must be pull only because I have no push access to this repository. I mean I want to pull yii when I pull parent repo, but don't want to push when I push parent repo.

    • Another problem is, remote dir structure of Yii (root/framework) looks like http://screencast.com/t/mU1TgXuZDv I need only framework folder's contents. How can I pull only this folder's contents into root/framework ?

  2. To make root/protected/messages separate git repo so that, when I push & pull root git repo, to do it for this one too. In other words, to push & pull with parent one to 2 separate remotes.

To solve second problem, I initialized new repo inside root/protected/messages but now they push & pull separatelly. I mean, I want them to push & pull changes to/from 2 remotes at once. Can't figure out how to do it.

Also I have no idea about first problem.

Any suggestions?

heron
  • 3,611
  • 25
  • 80
  • 148

2 Answers2

1
  1. In order to create a separate and independent git repos within a parent git repo, you want to look into Git Submodules (http://git-scm.com/book/en/Git-Tools-Submodules). These basically allow you to create a completely independent git repos inside a directory which by itself is a git repository.

  2. To create the submodule the command is git submodule add git://path/to/gitname.git folder-containing-the-inner-git. Of course you will need to cd into the parent folder before firing this command, which in your case will be root. The git://path/to/gitname.git will be the git url for Yii and folder-containing-the-inner-git will be root/framework.

  3. In order to pull a specific folder of Yii of the entire git repo you might want to try out git checkout as suggested by this question on stackoverflow How to pull specific directory with git. I have never tried this myself.
    Also, as of Git 1.7 you can also do a sparse checkout (https://www.kernel.org/pub/software/scm/git/docs/v1.7.0/git-read-tree.html#_sparse_checkout). Although you will still have to fetch the entire repo.

  4. Once you create a separate git repo using git submodules inside root, you will have to push and pull the git inside root/protected/messages seperately. You can however automate this process by creating a git hook (http://git-scm.com/book/en/Customizing-Git-Git-Hooks) for the repo inside root. A hook is a script that can be executed upon specific git events/operations like committing, merging, etc. For a full list of these events you can refer to this page ... http://www.manpagez.com/man/5/githooks/
    It seems that there is no event for a git push or pull. However there is an event for git merge ... post-merge :

    This hook is invoked by git merge, which happens when a git pull is done on a local repository. The hook takes a single parameter, a status flag specifying whether or not the merge being done was a squash merge. This hook cannot affect the outcome of git merge and is not executed, if the merge failed due to conflicts.

    This hook can be used in conjunction with a corresponding pre-commit hook to save and restore any form of metadata associated with the working tree (eg: permissions/ownership, ACLS, etc). See contrib/hooks/setgitperms.perl for an example of how to do this.

So you can write a simple bash script like :

cd root/protected/messages
git pull origin master

So everytime you pull from the outer repo in root this script will get fired and you will be able to pull the contents of your inner repo as well. However, this will happen on every merge, not just the merges that happen on a pull so you might want to be careful.

Hope this helps.

Community
  • 1
  • 1
vijay
  • 2,646
  • 2
  • 23
  • 37
  • I searched a lot about this subject. If I had any solution I'd do it. So help me with my situation or better delete your answer – heron Mar 03 '13 at 09:00
  • when you say "this subject" ... do you mean git submodules? – vijay Mar 03 '13 at 09:02
  • remote dir structure of Yii (root/framework) looks like screencast.com/t/mU1TgXuZDv I need only framework folder's contents. How can I pull only this folder's contents into root/framework ? – heron Mar 03 '13 at 09:27
  • like i explained in part 3 of my answer you can use `git checkout`. However, i have never tried it myself. Do have a look at `sparse checkout` https://www.kernel.org/pub/software/scm/git/docs/v1.7.0/git-read-tree.html#_sparse_checkout as well. – vijay Mar 03 '13 at 09:34
0

You may try more straightforward way:

  • Init your git repo in root;
  • Add your root/framework to .gitignore in it;
  • Go to root/framework and init new git repository there;

You will have matroshka styled repos. But, to be frankly, they will be harder to support than git-submodules solution, since root repo does not aware about other repos at all, and all pushesh, pulls need to be done separately inn each repo.

shytikov
  • 9,155
  • 8
  • 56
  • 103
  • Another problem is, remote dir structure of Yii (root/framework) looks like http://screencast.com/t/mU1TgXuZDv I need only framework folder's contents. How can I pull only this folder's contents into root/framework ? – heron Mar 03 '13 at 09:07
  • 1
    You can find the way to do it — for example via checking out only folder from local branch (I need to test will it work on the remotes), but this is not the way how Git was designed. It should keep consistency of source code, not tear it down, thus partial pull is not the way how it works. – shytikov Mar 03 '13 at 09:11