bash 在所有子目录上运行 git pull

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/3497123/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-09 19:35:28  来源:igfitidea点击:

Run git pull over all subdirectories

gitbash

提问by Petah

How can I update multiple git repositories from their shared parent's directory without cd'ing into each repo's root directory? I have the following which are all separate git repositories (notsubmodules):

如何在不cd进入每个 repo 的根目录的情况下从其共享父目录更新多个 git 存储库?我有以下都是单独的 git 存储库(不是子模块):

/plugins/cms
/plugins/admin
/plugins/chart

I want to update them all at once or at least simplify my current workflow:

我想一次更新它们或至少简化我当前的工作流程:

cd ~/plugins/admin
git pull origin master
cd ../chart
git pull

etc.

等等。

回答by leo

Run the following from the parent directory, pluginsin this case:

plugins在本例中,从父目录运行以下命令:

find . -type d -depth 1 -exec git --git-dir={}/.git --work-tree=$PWD/{} pull origin master \;

To clarify:

澄清:

  • find .searches the current directory
  • -type dto find directories, not files
  • -depth 1for a maximum depth of one sub-directory
  • -exec {} \;runs a custom command for every find
  • git --git-dir={}/.git --work-tree=$PWD/{} pullgit pulls the individual directories
  • find .搜索当前目录
  • -type d查找目录,而不是文件
  • -depth 1一个子目录的最大深度
  • -exec {} \;为每个查找运行一个自定义命令
  • git --git-dir={}/.git --work-tree=$PWD/{} pullgit 拉取单个目录

To play around with find, I recommend using echoafter -execto preview, e.g.:

要玩弄查找,我建议使用echoafter-exec进行预览,例如:

find . -type d -depth 1 -exec echo git --git-dir={}/.git --work-tree=$PWD/{} status \;

Note: if the -depth 1option is not available, try -mindepth 1 -maxdepth 1.

注意:如果该-depth 1选项不可用,请尝试-mindepth 1 -maxdepth 1

回答by Dmitry Mitskevich

ls | xargs -I{} git -C {} pull

To do it in parallel:

要并行执行:

ls | xargs -P10 -I{} git -C {} pull

回答by Ingo Blechschmidt

A bit more low-tech than leo's solution:

比 leo 的解决方案技术含量低一点:

for i in */.git; do ( echo $i; cd $i/..; git pull; ); done

This will update all Git repositories in your working directory. No need to explicitly list their names ("cms", "admin", "chart"). The "cd" command only affects a subshell (spawned using the parenthesis).

这将更新您工作目录中的所有 Git 存储库。无需明确列出他们的名字(“cms”、“admin”、“chart”)。“cd”命令仅影响子shell(使用括号生成)。

回答by Liudvikas

I use this one:

我用这个:

find . -name ".git" -type d | sed 's/\/.git//' |  xargs -P10 -I{} git -C {} pull

Universal: Updates all git repositories that are below current directory.

通用:更新当前目录下的所有 git 存储库。

回答by Gildas

Actually, if you don't know if the subfolders have a git repo or not, the best would be to let findget the repos for you:

实际上,如果您不知道子文件夹是否有 git 存储库,最好让find您为您获取存储库:

find . -type d -name .git -exec git --git-dir={} --work-tree=$PWD/{}/.. pull origin master \;

The PowerShell equivalent would be:

PowerShell 等效项是:

Get-ChildItem -Recurse -Directory -Hidden  -Filter .git | ForEach-Object { & git --git-dir="$($_.FullName)" --work-tree="$(Split-Path $_.FullName -Parent)" pull origin master }

回答by evadeflow

The mrutility (a.k.a., myrepos) provides an outstandingsolution to this very problem. Install it using your favorite package manager, or just grab the mrscript directly from githuband put it in $HOME/binor somewhere else on your PATH. Then, cdto the parent pluginsfolder shared by these repos and create a basic .mrconfigfile with contents similar to the following (adjusting the URLs as needed):

mr实用程序(又名myrepos)提供了一个优秀的解决方案,这非常的问题。安装它使用您喜欢的包管理,或只是抢mr脚本直接从GitHub,并把它$HOME/bin和别的地方在你的PATH。然后,cdplugins这些 repos 共享的父文件夹并创建一个.mrconfig内容类似于以下的基本文件(根据需要调整 URL):

# File: .mrconfig
[cms]
checkout = git clone 'https://<username>@github.com/<username>/cms' 'cms'

[admin]
checkout = git clone 'https://<username>@github.com/<username>/admin' 'admin'

[chart]
checkout = git clone 'https://<username>@github.com/<username>/chart' 'chart'

After that, you can run mr upfrom the top level pluginsfolder to pull updates from each repository. (Note that this will also do the initial clone if the target working copy doesn't yet exist.) Other commands you can execute include mr st, mr push, mr log, mr diff, etc—run mr helpto see what's possible. There's a mr runcommand that acts as a pass-through, allowing you to access VCS commands not directly suported by mritself (e.g., mr run git tag STAGING_081220015). And you can even create your own custom commands that execute arbitrary bits of shell script targeting all repos!

之后,您可以mr up从顶级plugins文件夹运行以从每个存储库中提取更新。(注意,这也将做初步克隆如果目标工作副本尚不存在)。你可以执行包括其他命令mr stmr pushmr logmr diff,等运行mr help,看看什么是可能的。有一个mr run作为传递的命令,允许您访问mr本身不直接支持的 VCS 命令(例如,mr run git tag STAGING_081220015)。您甚至可以创建自己的自定义命令,以执行针对所有存储库的任意位 shell 脚本!

mris an extremely useful tool for dealing with multiple repos. Since the pluginsfolder is in your home directory, you might also be interested in vcsh. Together with mr, it provides a powerful mechanism for managing allof your configuration files. See this blog postby Thomas Ferris Nicolaisen for an overview.

mr是处理多个 repos 的非常有用的工具。由于该plugins文件夹位于您的主目录中,您可能还对vcsh. 与 一起mr,它提供了一种强大的机制来管理您的所有配置文件。有关概述,请参阅Thomas Ferris Nicolaisen 的这篇博文

回答by Jamie Wong

This should happen automatically, so long as cms, admin and chart are all parts of the repository.

这应该自动发生,只要 cms、admin 和 chart 都是存储库的一部分。

A likely issue is that each of these plugins is a git submodule.

一个可能的问题是这些插件中的每一个都是一个 git 子模块。

Run git help submodulefor more information.

运行git help submodule以获取更多信息。

EDIT

编辑

For doing this in bash:

要在 bash 中执行此操作:

cd plugins
for f in cms admin chart
do 
  cd $f && git pull origin master && cd ..
done

回答by cmcginty

Most compact method, assuming all sub-dirs are git repos:

最紧凑的方法,假设所有子目录都是 git repos:

ls | parallel git -C {} pull

回答by Ryan

None of the top 5 answers worked for me, and the question talked about directories.

前 5 个答案中没有一个对我有用,问题是关于目录的。

This worked:

这有效:

for d in *; do pushd $d && git pull && popd; done

回答by eqfox

gitfoxis a tool to execute command on all subrepos

gitfox是一个在所有子仓库上执行命令的工具

npm install gitfox -g
g pull