Como alterar o repositório remoto para um submódulo git?

724

Eu criei um repositório git com um submódulo nele. Sou capaz de dizer ao próprio submódulo para alterar o caminho do repositório remoto, mas não sei como informar ao repositório pai como alterar o caminho do repositório remoto para o submódulo.

Eu não ficaria surpreso se eu estivesse um pouco sem sorte e tivesse que fazer as coisas manualmente, pois nem mesmo excluir sub-módulos é fácil.

Andrew Grimm
fonte
8
Nota: O Git 2.25 (primeiro trimestre de 2020) vem com um novo comando ":git submodule set-url [--] <path> <newurl>
VonC

Respostas:

1010

Você deve poder editar o .gitmodulesarquivo para atualizar a URL e, em seguida, executar git submodule syncpara refletir essa alteração no superprojeto e na sua cópia de trabalho.

Jim Puls
fonte
22
Isso não parece atualizar .git / config, pelo menos em 1.7.1 ou 1.7.3.
Davidtbernal
6
isso também atualiza a configuração de URL do submódulo para as confirmações anteriores? ex, se eu fizer o checkout de um commit mais antigo, ele apontará para novos URLs do submódulo?
precisa saber é o seguinte
63
Use git submodule foreach -q git config remote.origin.urlpara ver "reais" urls submódulo
Joel Purra
10
Não foi atualizado .git/configpara mim usando o git 2.1.0. Eu tive que atualizar os dois manualmente .gitmodulese .git/configantes de executar um git submodule sync --recursivepara atualizar meu submódulo remoto.
desseim 11/09/2014
7
Parece estar faltando a etapa principal da git submodule update --init --recursive --remotequal realmente muda o repositório para o novo controle remoto
Jason Axelson
155

Esses comandos farão o trabalho no prompt de comando sem alterar nenhum arquivo no repositório local

git config --file=.gitmodules submodule.Submod.url https://github.com/username/ABC.git
git config --file=.gitmodules submodule.Submod.branch Development
git submodule sync
git submodule update --init --recursive --remote

Veja as capturas de tela do blog: Alterando a URL / ramificação dos sub-módulos do GIT para outra URL / ramificação do mesmo repositório

Pavan Sokke Nagaraj
fonte
8
Isso funcionou, mas eu tive que lembrar de enviar as alterações para o controle remoto. git add .gitmodules git commit -m "modified submodule URL" git push origin master
precisa saber é o seguinte
5
Bem, isso criou uma bagunça terrível para mim. Os comandos foram interrompidos silenciosamente, mas o repositório real do sub-módulo ainda acha que seu controle remoto é o antigo (a URL antiga). Talvez esses comandos devam ser acompanhados de outros comandos no repositório do submódulo?
Motti Shneor
5
O último comando é um pouco extremo ... Se você tiver submódulos com submódulos, isso também atualizará remotamente os submódulos, o que é improvável o que você precisa.
Baptiste Wicht
7
Observe que você precisa substituir o Submod pelo nome do seu submódulo!
Shital Shah
133

Em termos simples, você só precisa editar o arquivo .gitmodules, ressincronizar e atualizar:

Edite o arquivo, através de um comando git ou diretamente:

git config --file=.gitmodules -e

ou apenas:

vim .gitmodules

ressincronize e atualize:

git submodule sync
git submodule update --init --recursive --remote
Matthew Wilcoxson
fonte
6
git submodule update --initfuncionou para mim, --remoteparece amarrá-lo à cabeça do repo remoto.
Chaim Eliyah
96

Com o Git 2.25 (primeiro trimestre de 2020), você pode modificá- lo.
Consulte " URL do sub-módulo Git alterado " e o novo comando

git submodule set-url [--] <path> <newurl>

Resposta original (maio de 2009, dez anos atrás)

Na verdade, um patch foi enviado em abril de 2009 para esclarecer a gitmodulefunção.

Portanto, agora a documentação do gitmodule ainda não inclui:

O .gitmodulesarquivo, localizado no diretório de nível superior de uma árvore de trabalho do git, é um arquivo de texto com uma sintaxe que corresponde aos requisitos -de linkgit: git-config 1 .
[NOVO]:
como esse arquivo é gerenciado pelo Git, ele rastreia os registros + dos submódulos de um projeto.
As informações armazenadas neste arquivo são usadas como uma dica para preparar a versão autorizada do registro armazenado no arquivo de configuração do projeto.
Alterações de registro específicas do usuário (por exemplo, para contabilizar diferenças nos URLs do submódulo devido a situações de rede) devem ser feitas no arquivo de configuração, enquanto alterações de registro a serem propagadas (por exemplo, + devido a uma realocação da fonte do submódulo) devem ser feitas nesse arquivo .

Isso praticamente confirma a resposta de Jim .


Se você seguir este tutorial do submódulo git , verá que precisa de um " git submodule init" para adicionar os URLs do repositório do submódulo a .git / config.

" git submodule sync" foi adicionado em agosto de 2008 precisamente para facilitar essa tarefa quando o URL é alterado (especialmente se o número de submódulos for importante).
O script associado a esse comando é direto o suficiente:

module_list "$@" |
while read mode sha1 stage path
do
    name=$(module_name "$path")
    url=$(git config -f .gitmodules --get submodule."$name".url)
    if test -e "$path"/.git
    then
    (
        unset GIT_DIR
        cd "$path"
        remote=$(get_default_remote)
        say "Synchronizing submodule url for '$name'"
        git config remote."$remote".url "$url"
    )
    fi
done

O objetivo permanece: git config remote."$remote".url "$url"

VonC
fonte
Eu queria alterar o URL do submódulo apenas nesta máquina. No projeto pai, eu poderia modificar o registro .git/configfazendo: git config submodule."$submodule_name".url "$new_url" que também é descrito aqui .
joeytwiddle
O que os traços duplos opcionais git submodule set-url [--] <path> <newurl>fazem?
jeverling
1
@jeverling Eles ajudam a separar as opções dos parâmetros: consulte stackoverflow.com/a/1192194/6309
VonC
1
Observe que para usuários do Ubuntu com uma versão mais antiga git, você pode usar este PPA para atualizar: launchpad.net/~git-core/+archive/ubuntu/ppa
starbeamrainbowlabs
69

O que funcionou para mim (no Windows, usando a versão 1.8.3.msysgit.0 do git):

  • Atualize .gitmodules com o caminho para o novo repositório
  • Remova a linha correspondente do arquivo ".git / config"
  • Exclua o diretório correspondente no diretório ".git / modules / external"
  • Exclua o próprio diretório do sub-módulo com check-out (não tenho certeza se isso é necessário)
  • Corra git submodule initegit submodule update
  • Verifique se o submódulo com check-out está no commit correto e confirme, pois é provável que o hash seja diferente

Depois de fazer tudo isso, tudo está no estado que eu esperaria. Eu imagino que outros usuários do repositório terão problemas semelhantes quando atualizarem - seria sensato explicar essas etapas na sua mensagem de confirmação!

Ben Hymers
fonte
2
Muito obrigado por isso. Este é o único que funcionou para mim depois que eu já havia executado um git submodule update. Seguir as outras respostas não mudaria o que estava no ./git/modules/externaldiretório, portanto, tentar atualizar resultaria em ainda puxando o URL incorreto.
NtscCobalt
isso parece ser um pouco perigoso, e não tenho certeza se preserva a história do submódulo anterior. Se, por exemplo, você deseja verificar um commit ou ramo antigo do seu repositório principal (aquele que contém o submódulo), não tenho certeza de que ele saberá puxar o submódulo OLD anexado e relacionado a esse commit antigo do main .
Motti Shneor
Não, quase certamente não saberá - você terá que executar todas as etapas após a primeira novamente. Isso é exatamente o que eu achei que funcionou para controlar o estado atual do submódulo. Eu não sei se o estado de coisas mudou desde que eu escrevi isso, mente :)
Ben Hymers
@MottiShneor que parece realmente perigoso se você precisar manter o histórico do submódulo anterior, embora não tenha certeza. No meu caso é a única solução que funcionou, o que eu queria era basicamente substituir o sub-módulo original com o meu próprio garfo
arainone
1
Siga estas etapas e descobriu que "Excluir o próprio diretório do sub-módulo com check-out (não tem certeza se isso é necessário)" é necessário. Caso contrário, você encontrará "fatal: Não é um repositório git: ..." ao executar a atualização do sub-módulo git
PiersyP
10

Apenas edite seu arquivo .git / config . Por exemplo; se você tem um submódulo "comum", você pode fazer isso no super-módulo:

git config submodule.common.url /data/my_local_common
FelipeC
fonte
Essa é apenas a melhor maneira se você estiver tentando alterar a URL para uso único, não permanentemente no super projeto. Por exemplo, você deseja clonar submódulos de cópias locais no disco.
Andy
4

git config --file=.gitmodules -e abre o editor padrão no qual você pode atualizar o caminho

LuGo
fonte