我通常至少有3个远程分支:master、staging和production。我有3个本地分支来跟踪这些远程分支。
更新我所有的本地分支是乏味的:
git fetch --all
git rebase origin/master
git checkout staging
git rebase origin/staging
git checkout production
git rebase origin/production
我很想做一个“git pull -all”,但我还没能让它工作。它似乎做了一个“fetch -all”,然后更新(快进或合并)当前工作的分支,但不包括其他本地分支。
我仍然需要手动切换到每个本地分支并进行更新。
我为我的giitbash写的脚本。完成以下任务:
默认情况下,为跟踪原点而设置的所有分支从原点提取,允许您根据需要指定不同的远程。
如果您的当前分支处于脏状态,那么它将存储您的更改,并在结束时尝试恢复这些更改。
对于每个用于跟踪远程分支的本地分支,将:
Git结帐分支
Git拉源
最后,将您返回到原始分支并恢复状态。
**我使用这个,但没有彻底测试,使用自负风险。在.bash_alias文件中可以看到该脚本的示例。
# Do a pull on all branches that are tracking a remote branches, will from origin by default.
# If current branch is dirty, will stash changes and reply after pull.
# Usage: pullall [remoteName]
alias pullall=pullAll
function pullAll (){
# if -h then show help
if [[ $1 == '-h' ]]
then
echo "Description: Pulls new changes from upstream on all branches that are tracking remotes."
echo
echo "Usage: "
echo "- Default: pullall"
echo "- Specify upstream to pull from: pullall [upstreamName]"
echo "- Help: pull-all -h"
else
# default remote to origin
remote="origin"
if [ $1 != "" ]
then
remote=$1
fi
# list all branches that are tracking remote
# git branch -vv : list branches with their upstreams
# grep origin : keep only items that have upstream of origin
# sed "s/^.."... : remove leading *
# sed "s/^"..... : remove leading white spaces
# cut -d" "..... : cut on spaces, take first item
# cut -d splits on space, -f1 grabs first item
branches=($(git branch -vv | grep $remote | sed "s/^[ *]*//" | sed "s/^[ /t]*//" | cut -d" " -f1))
# get starting branch name
startingBranch=$(git rev-parse --abbrev-ref HEAD)
# get starting stash size
startingStashSize=$(git stash list | wc -l)
echo "Saving starting branch state: $startingBranch"
git stash
# get the new stash size
newStashSize=$(git stash list | wc -l)
# for each branch in the array of remote tracking branches
for branch in ${branches[*]}
do
echo "Switching to $branch"
git checkout $branch
echo "Pulling $remote"
git pull $remote
done
echo "Switching back to $startingBranch"
git checkout $startingBranch
# compare before and after stash size to see if anything was stashed
if [ "$startingStashSize" -lt "$newStashSize" ]
then
echo "Restoring branch state"
git stash pop
fi
fi
}
如果可能,以下一行代码将快速前进所有具有上游分支的分支,否则打印错误:
git branch \
--format "%(if)%(upstream:short)%(then)git push . %(upstream:short):%(refname:short)%(end)" |
sh
它是如何工作的?
它使用git分支命令的自定义格式。对于每个具有上游分支的分支,它打印一行具有以下模式的代码:
git push . <remote-ref>:<branch>
这可以直接通过管道传输到sh(假设分支名称是格式良好的)。忽略| sh,看看它在做什么。
警告
单行程序不会联系你的遥控器。在运行它之前,发出git fetch或git fetch。
当前签出的分支将不会用类似于
! [remote rejected] origin/master -> master (branch is currently checked out)
为此,您可以求助于常规的git pull -ff-only。
别名
将以下内容添加到你的.gitconfig中,以便git fft执行此命令:
[alias]
fft = !sh -c 'git branch --format \"%(if)%(upstream:short)%(then)git push . %(upstream:short):%(refname:short)%(end)\" | sh' -
参见my .gitconfig。别名是“快进跟踪(分支)”的缩写。