Solução Detalhada
Veja a nota no final desta resposta (último parágrafo) para uma alternativa rápida aos submódulos git usando npm;)
Na seguinte resposta, você saberá como extrair uma pasta de um repositório e fazer um repositório git a partir dela e então incluí-la como um submódulo em vez de uma pasta.
Inspirado no artigo de Gerg Bayer Movendo Arquivos de um Repositório Git para Outro, Preservando a História
No início, temos algo assim:
<git repository A>
someFolders
someFiles
someLib <-- we want this to be a new repo and a git submodule!
some files
Nas etapas abaixo, irei me referir a isso someLib
como <directory 1>
.
No final, teremos algo assim:
<git repository A>
someFolders
someFiles
@submodule --> <git repository B>
<git repository B>
someFolders
someFiles
Crie um novo repositório git de uma pasta em outro repositório
Passo 1
Obtenha uma nova cópia do repositório para dividir.
git clone <git repository A url>
cd <git repository A directory>
Passo 2
A pasta atual será o novo repositório, portanto, remova o remoto atual.
git remote rm origin
etapa 3
Extraia o histórico da pasta desejada e submeta-o
git filter-branch --subdirectory-filter <directory 1> -- --all
Agora você deve ter um repositório git com os arquivos directory 1
da raiz do seu repo com todo o histórico de commits relacionado.
Passo 4
Crie seu repositório online e envie seu novo repositório!
git remote add origin <git repository B url>
git push
Você pode precisar definir o upstream
branch para seu primeiro envio
git push --set-upstream origin master
Limpo <git repository A>
(opcional, ver comentários)
Queremos eliminar traços (arquivos e comprometer história) de <git repository B>
partir <git repository A>
de modo história para esta pasta está lá apenas uma vez.
Isso se baseia na remoção de dados confidenciais do github.
Vá para uma nova pasta e
git clone <git repository A url>
cd <git repository A directory>
git filter-branch --force --index-filter 'git rm --cached --ignore-unmatch <directory 1> -r' --prune-empty --tag-name-filter cat -- --all
Substitua <directory 1>
pela pasta que você deseja remover. -r
fará isso recursivamente dentro do diretório especificado :). Agora empurre para origin/master
com--force
git push origin master --force
Boss Stage (veja a nota abaixo)
Crie um submódulo de <git repository B>
em<git repository A>
git submodule add <git repository B url>
git submodule update
git commit
Verifique se tudo funcionou conforme o esperado e push
git push origin master
Nota
Depois de fazer tudo isso, percebi no meu caso que era mais apropriado usar o npm para gerenciar minhas próprias dependências. Podemos especificar urls e versões do git , ver os urls do git package.json como dependências .
Se você fazê-lo desta forma, o repositório que você deseja usar como um requisito deve ser um módulo npm para que ele deve conter um package.json
arquivo ou você obterá este erro: Error: ENOENT, open 'tmp.tgz-unpack/package.json'
.
tldr (solução alternativa)
Você pode achar mais fácil usar o npm e gerenciar dependências com urls git :
- Mova a pasta para um novo repositório
- executar
npm init
dentro de ambos os repositórios
- execute
npm install --save git://github.com/user/project.git#commit-ish
onde você deseja que suas dependências sejam instaladas