Instead of referencing "stash@{n}" explicitly, it can simply be referenced as "n". Most users only reference stashes by their position in the stash stask (what I refer to as the "index"). The syntax for the typical stash (stash@{n}) is slightly annoying and easy to forget, and sometimes difficult to escape properly in a script. Because of this the capability to do things with the stash by simply referencing the index is desirable.
This patch includes the superior implementation provided by Ă˜sse Walle (thanks for that), with a slight change to fix a broken test in the test suite. I also merged the test scripts as suggested by Jeff King, and un-wrapped the documentation as suggested by Junio Hamano. Signed-off-by: Aaron M Watson <watso...@gmail.com> --- Documentation/git-stash.txt | 3 ++- git-stash.sh | 17 +++++++++++++++-- t/t3903-stash.sh | 35 +++++++++++++++++++++++++++++++++++ 3 files changed, 52 insertions(+), 3 deletions(-) diff --git a/Documentation/git-stash.txt b/Documentation/git-stash.txt index 92df596..2e9cef0 100644 --- a/Documentation/git-stash.txt +++ b/Documentation/git-stash.txt @@ -39,7 +39,8 @@ The latest stash you created is stored in `refs/stash`; older stashes are found in the reflog of this reference and can be named using the usual reflog syntax (e.g. `stash@{0}` is the most recently created stash, `stash@{1}` is the one before it, `stash@{2.hours.ago}` -is also possible). +is also possible). Stashes may also be referenced by specifying just the +stash index (e.g. the integer `n` is equivalent to `stash@{n}`). OPTIONS ------- diff --git a/git-stash.sh b/git-stash.sh index 826af18..d8d3b8d 100755 --- a/git-stash.sh +++ b/git-stash.sh @@ -384,9 +384,10 @@ parse_flags_and_rev() i_tree= u_tree= - REV=$(git rev-parse --no-flags --symbolic --sq "$@") || exit 1 + REV=$(git rev-parse --no-flags --symbolic --sq "$@" 2> /dev/null) FLAGS= + ARGV= for opt do case "$opt" in @@ -404,10 +405,13 @@ parse_flags_and_rev() die "$(eval_gettext "unknown option: \$opt")" FLAGS="${FLAGS}${FLAGS:+ }$opt" ;; + *) + ARGV="${ARGV}${ARGV:+ }'$opt'" + ;; esac done - eval set -- $REV + eval set -- $ARGV case $# in 0) @@ -422,6 +426,15 @@ parse_flags_and_rev() ;; esac + case "$1" in + *[!0-9]*) + : + ;; + *) + set -- "${ref_stash}@{$1}" + ;; + esac + REV=$(git rev-parse --symbolic --verify --quiet "$1") || { reference="$1" die "$(eval_gettext "\$reference is not a valid reference")" diff --git a/t/t3903-stash.sh b/t/t3903-stash.sh index 2142c1f..f82a8c4 100755 --- a/t/t3903-stash.sh +++ b/t/t3903-stash.sh @@ -131,6 +131,26 @@ test_expect_success 'drop middle stash' ' test 1 = $(git show HEAD:file) ' +test_expect_success 'drop middle stash by index' ' + git reset --hard && + echo 8 > file && + git stash && + echo 9 > file && + git stash && + git stash drop 1 && + test 2 = $(git stash list | wc -l) && + git stash apply && + test 9 = $(cat file) && + test 1 = $(git show :file) && + test 1 = $(git show HEAD:file) && + git reset --hard && + git stash drop && + git stash apply && + test 3 = $(cat file) && + test 1 = $(git show :file) && + test 1 = $(git show HEAD:file) +' + test_expect_success 'stash pop' ' git reset --hard && git stash pop && @@ -604,6 +624,21 @@ test_expect_success 'invalid ref of the form stash@{n}, n >= N' ' git stash drop ' +test_expect_success 'invalid ref of the form "n", n >= N' ' + git stash clear && + test_must_fail git stash drop 0 && + echo bar5 > file && + echo bar6 > file2 && + git add file2 && + git stash && + test_must_fail git stash drop 1 && + test_must_fail git stash pop 1 && + test_must_fail git stash apply 1 && + test_must_fail git stash show 1 && + test_must_fail git stash branch tmp 1 && + git stash drop +' + test_expect_success 'stash branch should not drop the stash if the branch exists' ' git stash clear && echo foo >file && -- 2.7.4