【熟能生巧】每日一键更新所有GIT项目

问题

我司的项目都是模块化的,一个大项目下面有很多小项目。某一个开发阶段,开发人员可能要同时修改5-6个项目。

所以,每天早上到办公室的第一件事,我会打开SourceTree(一个管理Git代码的软件,提供图形化界面),把每个正在开发的项目更新一下(点一下Pull那个按钮)。
如果有还没来得及 commit 的代码,还要先做备份(这就比较复杂了,需要使用 stash 功能)。

这个过程,一般要花5-10分钟,甚至更久,如果 Git 或者 SourceTree 很慢的话。这一件十分琐碎的工作,需要优化。

解决思路

思路很简单,Git更新项目用到的核心命令是git fetch / git pull。所以,可以结合Shell脚本将这个过程自动化。

最终实现一键更新所有项目。

项目设置

开发使用的是Windows系统,项目路径如下:

C:/codebase/Project_A
C:/codebase/Project_B
C:/codebase/Project_C

存放脚本路径如下:

C:/scripts/git_update.sh

代码

第一部分:读取参数

接受的参数为:项目名 和 branch名

#
# PART 1 - Prep
#
helpFunction()
{
   echo ""
   echo "Usage: $0 -p param_project -b param_branch" 
   echo -e "	-p, param_project"
   echo -e "	-b, param_branch"
   exit 1 # Exit script after printing help
}

while getopts "p:b:" opt
do
   case "$opt" in
      p ) param_project="$OPTARG" ;;
      b ) param_branch="$OPTARG" ;;
      ? ) echo "parameter not right"; helpFunction ;; # Print helpFunction in case parameter is non-existent
   esac
done

## Print helpFunction in case parameters are empty
if [ -z "$param_project" ] || [ -z "$param_branch" ]
then
   echo "Some or all of the parameters are empty";
   helpFunction
fi

# Begin script in case all parameters are correct
echo "[INPUT] param_project: $param_project"
echo "[INPUT] param_branch: $param_branch"

第二部分:处理

处理逻辑是这样的:先将任何change备份到一个文件,然后discard;然后pull;最后再将change重新apply回去。

#
# PART 2 - Process
#

# Parse input
DIR_PATH=/c/codebase/
branch=$param_branch
timestamp=`date "+%Y_%m_%d_%H_%M_%S"`

# git backup changes
gitBackupFunction()
{
	cd $DIR_PATH/$project
	echo "[INFO] current dir is: $PWD"; 

	echo "[GIT] checkout $branch" 
	git checkout $branch
	
	echo "[GIT] save changes to diff_${branch}_${timestamp}" 
	git diff > diff_${branch}_${timestamp}
	
	echo "[GIT] reset branch" 
	git reset --hard
}

# git pull
gitUpdateFunciton()
{
	echo "[GIT] fetch $branch"
	git -c diff.mnemonicprefix=false -c core.quotepath=false fetch origin

	echo "[GIT] pull $branch"
	git -c diff.mnemonicprefix=false -c core.quotepath=false pull --rebase origin $branch
}

# git reapply changes
gitReapplyFunction()
{
	echo "[GIT] reapply changes from diff_${branch}_${timestamp}" 
	git apply diff_${branch}_${timestamp}
	
	echo "[GIT] remove temp changes" 
	rm diff_${branch}_${timestamp}
}

# Loop each project
for project in $param_project
do
	echo -e "
##### START TO PROCESS $project #####"
	gitBackupFunction
	gitUpdateFunciton
	gitReapplyFunction
	echo -e "##### FINISH TO PROCESS $project #####
"
done

有一点需要说明的是,代码备份+还原,这里使用了git diff,而没有使用git stash。原因有二:

  • git diff执行起来更快,git stash经常会卡住一会。
  • git stash删除起来比较麻烦,它需要指定 stash 队列中的元素位置,而不是名称。
git stash push -m stash_name_with_timestamp
git stash apply stash^{/stash_name_with_timestamp}
# note: can't delete with stash name, have to go with sequence number using git stash drop...

执行

在Windows任意目录下,打开Git Bash,输入如下命令:

/c/scripts/git_update.sh -p "Project_A Project_B Project_C" -b dev_branch_20201010

这句话的意思是,更新Project A,B,C这三个项目的dev_branch_20201010分支。

定时执行

在Windows下面可以设置定时执行任务。这里就不赘述了。

实际工作中,因为没有计算机的管理员权限,所以我选择了另一种半自动的方法:将所有需要每天执行的脚本命令都放到一个文件。然后早上到了公司就运行一下这个文件,然后再去接水/泡咖啡啦~~~

原文地址:https://www.cnblogs.com/maxstack/p/13852659.html