'Is there a way to use wildcards with git checkout?

What I would like to do is to checkout a single file or a set of files with a common name part like this

git checkout myBranch */myFile.md and

git checkout myBranch -- */*Test* (not sure about the '--' part)

instead of

git checkout myBranch src/main/java/a/deep/package/structure/myFile.md and

git checkout myBranch src/test/java/a/deep/package/structure/TestOne.java
git checkout myBranch src/test/java/a/deep/package/structure/TestTwo.java
git checkout myBranch src/test/java/a/deep/package/structure/resources/TestData.sql

I know there is some limited wildcard functionality for some git command like diff and add but have found nothing for checkout. Is there a way?

EDIT: I am using git 1.7.9.5 on Linux. A working combination of git and shell commmands would be acceptable as well.



Solution 1:[1]

Git does not deal with the wildcard, but your shell does.

Try this :

git checkout myBranch **/myFile.md

and

git checkout myBranch  **/*Test*

With the **, your shell will look for files in all the subdirectories starting from the current working directory.

Solution 2:[2]

Powershell

@(gci -Recurse *test* | Resolve-Path -Relative) | %{git checkout mybranch -- $_)

gci generates a list of all files matching the criteria (*test*) then pipes it to Resolve-Path to get the relative path. Finally the flattened (@) list of filenames is piped into the git invokation (executes once per file found).

Solution 3:[3]

Windows git bash with xargs

git difftool myBranch --name-only *.java | xargs git checkout myBranch

Solution 4:[4]

None of the other answers worked for me, but bambams comment worked. I made it into a bash function that accepts two args. Usage:

gitcheckout myBranch '*file*'

gitcheckout()
{
    GIT_DIR=$(git rev-parse --git-dir 2>/dev/null); 
    pushd .;
    cd $GIT_DIR/../;
    git diff --name-only $1 -- $2 | xargs git checkout $1 --;
    popd;
}

Solution 5:[5]

If you have a gitignore or untracked files and you want to use wildcards with git checkout, then it might give you problems, and a solution could be:

git ls-files '*/myFile.md' | tr '\n' '\0' | xargs -0 -L1 -I '$' git checkout -- '$'

Solution 6:[6]

Knowing that git returns branch list names from 3rd char, one can just switch to needed branch defined via [mask]:

BRANCH_NAME=$(git branch --list | grep [mask] | cut -c3-)
git checkout ${BRANCH_NAME}

Solution 7:[7]

For me the task was to checkout several files named after one pattern:

  • ./a/b/c/FirstTest.java
  • .d/e/f/SecondTest.java
  • ./g/h/i/ThirdTest.java

I've used this bash command:

# 1. Find files named after "*Test.java" pattern.
# 2. Execute checkout command on every found file.

find . -name "*Test.java" -exec git checkout master {} \;

Also firstly you can test the find command with simple echo, which just prints a given text ({} in our case, which will be replaced with current found filename by shell):

find . -name "*Test.java" -exec echo {} \;

Solution 8:[8]

If you need to get the files from a commit regardless of whether they were changed in that commit, you can use the following:

git ls-tree --name-only -r myBranch | grep myFilePattern | xargs git checkout myBranch

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 Intrepidd
Solution 2 9Rune5
Solution 3 Sarath
Solution 4
Solution 5 ferdymercury
Solution 6 Ivan M
Solution 7 Yamashiro Rion
Solution 8 John Michelau