Repositório Git em um repository git

Eu tenho um repository git incluindo um repository git.

repo1/ .git/ files repo2/ .git/ files files 

É possível trabalhar com essa arquitetura?

Você pode ter repositorys git nesteds:
O repository pai será simplesmente ignorar o repo nested .

jleedev comenta e ilustra com este script que o repository pai rastrearia o estado do repo nested através de um gitlink .
(gitlink = SHA-1 do object referente a um commit em outro repository. Os links do Git só podem ser especificados pelo SHA ou através de uma marca de confirmação.
Um gitlink tem um modo especial ‘ 160000 ‘, usado para submódulos, mas também presente para repos nesteds simples).

No entanto, comandos comuns não confirmariam o repository nested: add ou commit se aplicaria apenas em um repository, não no outro.

O submódulo git permitiria fazer referência ao repository nested do repository pai e manter uma referência exata do repository filho.

Outra alternativa poderia envolver:

  • dois repos separados do Git (não nesteds)
  • um link simbólico de um para uma parte específica do outro (tanto o Unix, mas também o Windows Vista + tem links simbólicos)

O que você está tentando realizar é chamado de “submódulo”, confira este link: http://git-scm.com/book/en/v2/Git-Tools-Submodules para descobrir como ele está funcionando.

Eu usei essa estrutura por um bom tempo, com os diretórios sub-repo especificados em .gitignore no repo externo.

Ele confunde a ferramenta git no meu editor (PhpStorm), que sempre quer se comprometer com o repository externo, mas funciona bem. Eu carrego todo o repository externo (que inclui todos os repositorys internos) como um único projeto no editor. Isso permite que eu pesquise e analise facilmente o código no repository externo enquanto estiver trabalhando em um interno.

Eu faço todas as operações do Git do Git bash em qualquer repository em que estou trabalhando.

Submódulos podem ser uma abordagem melhor. Eu não tive tempo para investigar se eles funcionariam melhor com o PhpStorm.

Sim, você pode usar esse padrão. Eu usei isso no passado para trazer as externas do SVN para um clone do git-svn. Submódulos podem lidar melhor com isso agora, mas não atendem às minhas necessidades no momento.

Você vai querer adicionar o seguinte ao repo1 / .git / info / exclude para garantir que as mudanças no repo2 não se misturem com o repo1:

 repo2 

Eu também concordo com Ronald Williams acima. O objective principal do git-submodules é atualizar o código retirado do mundo externo sem necessidade de confirmar mudanças se o código for modificado pela atualização. O mesmo faz o sistema de gerenciamento de pacotes do compositor. Na verdade, eles também não recomendam a consolidação dessas alterações e ignoram a pasta do fornecedor em .gitignore na raiz do projeto. É um pesadelo se você tentar cometer esta pasta porque alguns dos fornecedores / some_repo podem ser da versão dev, conseqüentemente eles têm a pasta .git que resulta em todos os pacotes se tornarem submódulos mesmo se você não os adicionar com git submodule add . Você pode ver algo assim se modificar some_file em um repository .git nested:

 ~/project_root $ git status # On branch master # Changes not staged for commit: # (use "git add ..." to update what will be committed) # (use "git checkout -- ..." to discard changes in working directory) # (commit or discard the untracked or modified content in submodules) # # modified: vendor/nested_repo (modified content) 

Observe o conteúdo modificado na input de submódulos e você não verá o nome some_arquivo na saída. Em vez disso, você vê o aviso (conteúdo modificado) porque o root_project .git vê o fornecedor / nested_repo como um submódulo e não rastreia arquivos individuais nessa pasta.

Se você executar git add -all, você não obterá nenhum resultado até que você confirme as alterações no fornecedor / nested_repo e somente depois disso você poderá confirmar as alterações no repository raiz.

Não faça isso. Em vez disso, se você quiser manter seu projeto como um repository inteiro .git (qualquer repository construído, não apenas do compositor), o que é muito conveniente às vezes, adicione essa input à raiz .gitignore ANTES do commit inicial:

 .git !/.git 

Infelizmente, para que toda a receita funcione, você precisa executar o comando git add para cada uma das reposições aninhadas que você deseja modificar mais tarde. Observe que a barra final nos caminhos de repos é uma obrigação .

 ~/project_root $ git add vendor/some_repo/ vendor/another_repo/ 

Em seguida, modifique some_file no vendor / some_repo e veja a diferença:

 ~/project_root $ git status # On branch master # Changes not staged for commit: # (use "git add ..." to update what will be committed) # (use "git checkout -- ..." to discard changes in working directory) # # modified: vendor/some_repo/some_file 

Dessa forma você pode executar git add --all e depois git commit "Changes ..." no project_root como de costume.

Estou surpreso que ninguém neste segmento mencionou as soluções de gerenciamento de pacotes.

É verdade que os submódulos git permitem desenvolver com a arquitetura que você descreveu, subtrees git fornecem uma solução similar que muitas pessoas preferem.

Na minha opinião, o software de gerenciamento de pacotes é parte integrante de qualquer projeto complexo. Eu gosto de compositor por causa dos streams de trabalho intuitivos que ele suporta: https://getcomposer.org/

Infelizmente os submódulos git não são suportados pelo PHPstorm: http://youtrack.jetbrains.com/issue/IDEA-64024