繁体   English   中英

检查当前目录是否为 Git 存储库

[英]Check if current directory is a Git repository

我正在为zsh中的Git管理编写一系列脚本。

如何检查当前目录是否为 Git 存储库? (当我不在 Git 存储库中时,我不想执行一堆命令并得到一堆fatal: Not a git repository响应)。

复制自bash补全文件,下面是很幼稚的做法

# Copyright (C) 2006,2007 Shawn O. Pearce <spearce@spearce.org>
# Conceptually based on gitcompletion (http://gitweb.hawaga.org.uk/).
# Distributed under the GNU General Public License, version 2.0.

if [ -d .git ]; then
  echo .git;
else
  git rev-parse --git-dir 2> /dev/null;
fi;

您可以将其包装在函数中或在脚本中使用它。

浓缩成适合bashzsh的单行条件

[ -d .git ] && echo .git || git rev-parse --git-dir > /dev/null 2>&1

您可以使用:

git rev-parse --is-inside-work-tree

如果您在 git repos 工作树中,它将打印“true”。

请注意,如果您在 git 存储库之外(并且不打印“false”),它仍会将输出返回给 STDERR。

取自这个答案: https : //stackoverflow.com/a/2044714/12983

使用 git rev-parse --git-dir

if git rev-parse --git-dir > /dev/null 2>&1; then
  : # This is a valid git repository (but the current working
    # directory may not be the top level.
    # Check the output of the git rev-parse command if you care)
else
  : # this is not a git repository
fi

编辑: git-rev-parse现在(从 1.7.0 开始)支持--show-toplevel ,所以if test "$(pwd)" = "$(git rev-parse --show-toplevel)"到确定当前目录是否是顶级目录。

或者你可以这样做:

inside_git_repo="$(git rev-parse --is-inside-work-tree 2>/dev/null)"

if [ "$inside_git_repo" ]; then
  echo "inside git repo"
else
  echo "not in git repo"
fi

基于@Alex Cory 的回答

[ "$(git rev-parse --is-inside-work-tree 2>/dev/null)" == "true" ]

不包含任何冗余操作并在-e模式下工作。

  • 正如@go2null 指出的那样,这在裸仓库中不起作用。 如果您出于任何原因想使用裸仓库,您只需检查git rev-parse成功,忽略其输出。
    • 我不认为这是一个缺点,因为上面的行是为脚本编写的,而且几乎所有的git命令都只在工作树内有效。 因此,出于编写脚本的目的,您很可能不仅对“git repo”感兴趣,而且对工作树感兴趣。

不确定是否有公开访问/记录的方法来执行此操作(有一些内部 git 函数可以在 git 源本身中使用/滥用)

你可以做类似的事情;

if ! git ls-files >& /dev/null; then
  echo "not in git"
fi

另一种解决方案是检查命令的退出代码。

git rev-parse 2> /dev/null; [ $? == 0 ] && echo 1

如果您在 git 存储库文件夹中,这将打印 1。

这个答案提供了一个示例 POSIX shell 函数和一个使用示例来补充@jabbie 的答案

is_inside_git_repo() {
    git rev-parse --is-inside-work-tree >/dev/null 2>&1
}

如果 git 位于 git 存储库内,则git返回 errorlevel 0 ,否则返回 errorlevel 128 (如果它在 git 存储库中,它也会返回truefalse 。)

使用示例

for repo in *; do
    # skip files
    [ -d "$repo" ] || continue
    # run commands in subshell so each loop starts in the current dir
    (
        cd "$repo"
        # skip plain directories
        is_inside_git_repo || continue
        printf '== %s ==\n' "$repo"
        git remote update --prune 'origin' # example command
        # other commands here
    )
done

这对我有用。 您仍然会遇到错误,但它们很容易抑制。 它也适用于子文件夹内!

git status >/dev/null 2>&1 && echo Hello World!

如果您需要有条件地执行更多操作,您可以将其放在 if then 语句中。

为什么不使用退出代码? 如果当前目录存在 git 仓库,则git branchgit tag命令返回退出码 0; 否则,将返回非零退出代码。 通过这种方式,您可以确定 git 存储库是否存在。 简单地说,你可以运行:

git tag > /dev/null 2>&1

优点:便携。 它适用于裸和非裸存储库,以及 sh、zsh 和 bash。

解释

  1. git tag :获取存储库的标签以确定是否存在。
  2. > /dev/null 2>&1 :防止打印任何内容,包括正常和错误输出。

TLDR(R E中L L Y'!): check-git-repo

例如,您可以使用以下内容创建一个名为check-git-repo的文件,使其可执行并运行它:

#!/bin/sh

if git tag > /dev/null 2>&1; then
    echo "Repository exists!";
else
    echo "No repository here.";
fi

# 检查 git repo

if [ $(git rev-parse --is-inside-work-tree) = true ]; then
    echo "yes, is a git repo"
    git pull
else
    echo "no, is not a git repo"
    git clone url --depth 1
fi

您可以使用一个另一个 git-prompt工具在zshrc中添加或替换$ PS1。 通过这种方式,您可以方便地了解您是否处于git仓库并且回购状态是否存在。

if ! [[ $(pwd) = *.git/* || $(pwd) = *.git ]]; then 
  if type -P git >/dev/null; then
    ! git rev-parse --is-inside-work-tree >/dev/null 2>&1 || {
     printf '\n%s\n\n' "GIT repository detected." && git status
    }
  fi
fi

谢谢ivan_pozdeev ,现在我有一个测试,如果在 .git 目录中代码不会运行,那么没有打印出错误或错误的退出状态。

! [[ $(pwd) = .git/ || $(pwd) = *.git ]] ”测试如果你不在.git 存储库中,那么它将运行 git 命令。 内置type命令用于检查您是否安装了 git 或者它是否在您的 PATH 中。 查看帮助类型

在 linux 中的终端或 windows 上的 cmd 中打开该目录,然后输入git status ,这在 2021 年应该足以告诉你你在一个 git repo 中,并且你有x个分支和x个提交。

##Current branch
echo $(git branch --show-current 2> /dev/null && echo '')
echo $(git branch --show-current 2> /dev/null)

##OR
GIT_DIR=$(git rev-parse --git-dir 2> /dev/null)
! git rev-parse --is-inside-work-tree >/dev/null 2>&1 || { 
  printf '%s\n\n' "GIT repository detected." && git status
}

的! 否则所以即使你在一个不是git repo的目录中运行它也不会给你一些致命的错误

> / dev / null 2>&1将消息发送到/ dev / null,因为您刚刚退出状态。 {}用于命令分组,因此所有命令都在||之后 如果git rev-parse成功,因为我们使用了! 这否定了git rev-parse的退出状态。 printf只是打印一些消息和git状态来打印repo的状态。

将其包装在函数中或将其放在脚本中。 希望这可以帮助

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM