bash 如何从提交哈希中判断 git 分支名称?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/29707280/
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
How to tell git branch name from commit hash?
提问by k107
I have a bash script which accepts a string of either a branch name (e.g., "master", or "feature/foo") or a commit hash (e.g. "1234abcd").
我有一个 bash 脚本,它接受分支名称(例如“master”或“feature/foo”)或提交哈希(例如“1234abcd”)的字符串。
I have the repository checked out, so I can call git.
我已检出存储库,因此我可以调用 git。
What is the best way to determine whether the string is a branch name or a commit hash?
确定字符串是分支名称还是提交哈希的最佳方法是什么?
#!/bin/bash
commit_or_branch=""
cd /path/to/my_repo
git fetch
if <is_branch $commit_or_branch>
then
echo "it's a branch"
else
echo "it's a commit"
fi
回答by Eric Cousineau
If you would like a robust mechanism to tell relative names (e.g. you SHA1 is possibly one or so commits behind a named branch), you can use git name-rev
to resolve it.
如果您想要一个强大的机制来告诉相对名称(例如,您的 SHA1 可能是命名分支后面的一个左右提交),您可以使用git name-rev
它来解析它。
Examples:
例子:
$ git config remote.upstream.url
https://github.com/RobotLocomotion/drake.git
$ git log --oneline -n 5
7530a95 Merge pull request #5743 from soonho-tri/pr-reformat-mathematical_program
ebc8f25 Suppresses console output of speed_bump.obj genrule. (#5726)
d8b9a0b Merge pull request #5735 from david-german-tri/namespaces
79e10e8 Remove redundant 'symbolic::' prefix from mathematical_program code
b68b590 Clean up mathematical_program code by adding using std::*
$ git name-rev HEAD
HEAD master
$ git name-rev 79e10e8
79e10e8 master^2
$ git name-rev HEAD~20
HEAD~20 remotes/origin/issue/5646_return_binding~3
Reference: Git Tips (old commit)
UPDATE: As @kporter mentioned, there is also the --name-only
flag (with new commits as of 2020/04/21):
更新:正如@kporter 所提到的,还有一个--name-only
标志(截至 2020/04/21 有新的提交):
$ git name-rev HEAD
HEAD tags/last_sha_with_original_matlab~313
$ git name-rev --name-only HEAD~20
tags/last_sha_with_original_matlab~333
Command-Line Reference: git name-rev
命令行参考: git name-rev
回答by VonC
You can use git show-ref
:
您可以使用git show-ref
:
git show-ref --head | grep refs
If it is empty, it is a SHA1 (or an invalid object, which isn't good).
If not, it is a branch name.
如果它为空,则它是 SHA1(或无效对象,这不好)。
如果不是,它是一个分支名称。
A better technique comes from "Validate if commit exists", using git merge-base
:
更好的技术来自“验证是否存在提交”,使用git merge-base
:
A branch name will result in a different string (the SHA1)
分支名称将产生不同的字符串(SHA1)
C:\Users\vonc\prog\b2d>git merge-base master master
de4accfd28c5f25fcc057d56996b83450be5dc60
a SHA1 will result in the same result (or at least starts with the same result):
SHA1 将产生相同的结果(或至少以相同的结果开始):
C:\Users\vonc\prog\b2d>git merge-base 03949c3d3f88a378c6a08e57daa97059b52813f1 03949c3d3f88a378c6a08e57daa97059b52813f1
03949c3d3f88a378c6a08e57daa97059b52813f1
foobar will fail:
foobar 将失败:
C:\Users\vonc\prog\b2d>git merge-base xxx xxx
fatal: Not a valid object name xxx
That means something like:
这意味着:
if [[ git merge-base $string $string ]]; then
if [[ $(git merge-base $string $string) == $string* ]]; then
echo "SHA1"
else
echo "branch"
fi
else
echo "Not a valid object name '$string'"
fi
回答by hek2mgl
Imo you can't check this reliably, since a hash is also a valid branch name. Try:
我不能可靠地检查这个,因为哈希也是一个有效的分支名称。尝试:
git checkout -b 0c8158f47d7dda89226d4e816fee1fb9ac6c1204
This means there can be a situation where a branch with that name exists but also a commit.
这意味着可能存在具有该名称的分支但也存在提交的情况。
Since you can pass a branch name or a commit to most of the git commands, you don't need to differentiate between them.
由于您可以将分支名称或提交传递给大多数 git 命令,因此您无需区分它们。
回答by hinerm
As @VonC and @hek2mgl mentioned, this may not be a one or the other test. You could slightly modify your script to something like this (borrowed from this SO answer:
正如@VonC 和@hek2mgl 所提到的,这可能不是一个或另一个测试。您可以将脚本稍微修改为这样的内容(从这个 SO 答案中借用:
#!/bin/bash
commit_or_branch=""
cd /path/to/my_repo
git fetch
if git branch | grep $commit_or_branch 2> /dev/null
then
echo "it's a branch"
fi
if git cat-file -e $commit_or_branch 2> /dev/null
then
echo "it's a commit"
fi
Note that this only tests for local branches.. see this postif you're interested in remote branches.
请注意,这仅测试本地分支。如果您对远程分支感兴趣,请参阅此帖子。