Czy możesz naciskać na wszystkie piloty git za pomocą jednego polecenia?

195

Zamiast robić:

git push origin --all && git push nodester --all && git push duostack --all

Czy można to zrobić za pomocą tylko jednego polecenia?

Dzięki :)

balupton
źródło
1
Zobacz także: stackoverflow.com/q/5620525/223092
Mark Longair,
Aby utworzyć allpilota do obsługi wszystkich pilotów, patrz: stackoverflow.com/a/18637593/802365
Édouard Lopez

Odpowiedzi:

253

Aby przekazać wszystkie gałęzie do wszystkich pilotów:

git remote | xargs -L1 git push --all

Lub jeśli chcesz przekazać określoną gałąź do wszystkich pilotów:

Zastąp mastergałąź, którą chcesz wypchnąć.

git remote | xargs -L1 -I R git push R master

(Bonus) Aby utworzyć alias git dla polecenia:

git config --global alias.pushall '!git remote | xargs -L1 git push --all'

Uruchomienie git pushallspowoduje teraz przekazanie wszystkich gałęzi do wszystkich pilotów.

słaby
źródło
1
Bardzo dobre i proste rozwiązanie. BTW, możesz użyć xargs -l zamiast -L 1, opcja -l jest taka sama jak -L 1. Ponadto czasami dodam --all do git push. git zdalny | xargs -l git push --all
Tony
2
Mam xargs: illegal option -- lOSX. git remote | xargs -L1 git push
Zrozumiałeś
4
Git umożliwia wykonanie tego połączenia w niestandardowym poleceniu. Wystarczy umieścić go w pliku, który 1) znajduje się na twojej ścieżce, 2) masz uprawnienia do wykonywania, oraz 3) o nazwie „git- [nazwa niestandardowa]” (np. Git-foo, git-push-all), a będziesz móc po prostu wpisać „git [nazwa niestandardowa]” (np. git foo, git push-all).
Andrew Martin,
2
@ Tony Na Ubuntu man xargsmówi , że opcja -ljest przestarzała, ponieważ nie ma jej w specyfikacji POISX.
wjandrea
2
@kyb W składni aliasu git !oznacza, że ​​poniższe polecenie nie jest wewnętrznym poleceniem git, ale zewnętrznym poleceniem powłoki.
słaby
285

Utwórz allzdalny z kilkoma adresami URL repo do jego nazwy:

git remote add all origin-host:path/proj.git
git remote set-url --add all nodester-host:path/proj.git
git remote set-url --add all duostack-host:path/proj.git

Więc po prostu git push all --all.


Tak to wygląda w .git/config:

  [remote "all"]
  url = origin-host:path/proj.git
  url = nodester-host:path/proj.git
  url = duostack-host:path/proj.git
Arystoteles Pagaltzis
źródło
5
Super fajna sztuczka! Jedyną wadą jest to, że nie porusza zdalnymi głowami. Musisz biec git fetch --allzaraz po wykonaniu takiego pushu.
madhead
8
Pan Torvalds (twórca Git) wspomina, że ​​stosuje tę metodę, ale twierdzi, że jest ona jedynie dla wygody i nie oferuje żadnej technicznej korzyści marc.info/?l=git&m=116231242118202&w=2 „A na koniec nawet„ git push all ", który wypycha do wielu repozytoriów, w rzeczywistości połączy się raz dla każdego repozytorium, więc jest to naprawdę tylko skrót do robienia wielu operacji" git push ". Nie ma żadnej rzeczywistej przewagi technicznej, tylko wygoda."
Matt
14
Jednym z problemów związanych z tym podejściem jest to, że musisz dodawać nowe adresy URL do allzdalnego, gdy git remote | xargs -L1 git push --allbędą one dostępne, podczas gdy automatycznie będą zbierać nowe piloty.
Raffi Khatchadourian
2
Wskazówka: Aby nie trzeba pisać przy allwysyłaniu zatwierdzenia, po prostu użyj „origin” zamiast „all”:git remote set-url --add origin nodester-host:path/proj.git
Macabeus
zapomniałem ustawić adresy URL push, w przeciwnym razie git pushnie zaktualizuje wszystkich adresów URL. odpowiedź odpowiednio zaktualizowana
user3338098
88

Jeśli chcesz zawsze wypychać repo1, repo2 i repo3, ale zawsze wyciągaj tylko z repo1, ustaw zdalne „pochodzenie” jako

[remote "origin"]
    url = https://[email protected]/path/to/repo1
    pushurl = https://[email protected]/path/to/repo1
    pushurl = https://[email protected]/path/to/repo2
    pushurl = https://[email protected]/path/to/repo3
    fetch = +refs/heads/*:refs/remotes/origin/*

Skonfiguruj w wierszu polecenia:

$ git remote add origin https://[email protected]/path/to/repo1
$ git remote set-url --push --add origin https://[email protected]/path/to/repo1
$ git remote set-url --push --add origin https://[email protected]/path/to/repo2
$ git remote set-url --push --add origin https://[email protected]/path/to/repo3

Jeśli tylko chcesz ciągnąć od repo1, ale push to repo1i repo2 dla konkretnej branżyspecialBranch :

[remote "origin"]
    url = ssh://[email protected]:7999/yyy/repo1.git
    fetch = +refs/heads/*:refs/remotes/origin/*
    ...
[remote "specialRemote"]
    url = ssh://[email protected]:7999/yyy/repo1.git
    pushurl = ssh://[email protected]:7999/yyy/repo1.git
    pushurl = ssh://[email protected]:7999/yyy/repo2.git
    fetch = +refs/heads/*:refs/remotes/origin/*
    ...
[branch "specialBranch"]
    remote = origin
    pushRemote = specialRemote
    ...

Zobacz https://git-scm.com/docs/git-config#git-config-branchltnamegtremote .

Meng Lu
źródło
4
Nie jestem pewien, dlaczego nie ma więcej głosów. Jest to naprawdę bardzo wygodne, ponieważ pozwala to zrobić git pushbez żadnych argumentów.
Husky
1
Głosuj na mnie, proszę!
Meng Lu
1
Wydaje mi się, że jest to bardziej odpowiedni sposób, aby to zrobić. Powinien mieć najwyższe głosy.
Ahmad
Jest to bardzo przydatne. Czy można ograniczyć pushurl tylko do gałęzi master?
fbucek
17

Jako alternatywa interfejsu CLI do edycji pliku .git / config, możesz użyć następujących poleceń:

# git remote add all origin-host:path/proj.git
# git remote set-url --add all nodester-host:path/proj.git
# git remote set-url --add all duostack-host:path/proj.git

To samo git push all --alldziała tutaj.

Osiągnąłeś to samo co odpowiedź nr 1. Właśnie to zrobiłeś za pomocą wiersza poleceń zamiast surowej edycji pliku konfiguracyjnego.

Kurt Vanderwater
źródło
2

Napisałem funkcję krótkiego uderzenia, aby wcisnąć wiele pilotów za jednym razem. Możesz określić jednego pilota jako parametr, wiele pilotów oddzielonych spacjami lub nie podawać żadnego, który będzie przekazywał wszystkie piloty.

Można to dodać do pliku .bashrc lub .bash_profile.

function GitPush {
  REMOTES=$@

  # If no remotes were passed in, push to all remotes.
  if [[ -z "$REMOTES" ]]; then
    REM=`git remote`

    # Break the remotes into an array
    REMOTES=$(echo $REM | tr " " "\n")
  fi

  # Iterate through the array, pushing to each remote
  for R in $REMOTES; do
    echo "Pushing to $R..."
    git push $R
  done
}

Przykład: załóżmy, że twoje repo ma 3 piloty: rem1, rem2 i rem3.

# Pushes to rem1
GitPush rem1

# Pushes to rem1 and rem2
GitPush rem1 rem2

# Pushes to rem1, rem2 and rem3
GitPush
KeyboardCowboy
źródło
0

Możesz używać haczyków git - szczególnie pre-push: dodawaj pchnięcia nie pochodzące od .git/hooks/pre-push.

Witalij Zdanevich
źródło