{"thread":{"id":"34148","subject":"[PATCH v3 4/5] stash: introduce 'git stash store'","startedAt":"2013-06-15T13:13:21Z","lastAt":"2013-06-18T14:31:40Z","messageCount":10,"participants":["Ramkumar Ramachandra","Junio C Hamano"],"isPatch":true,"patchVersion":3,"patchTotal":5},"messages":[{"id":"220946","messageId":"1371302006-29775-1-git-send-email-artagnon@gmail.com","threadId":"34148","inReplyTo":null,"subject":"[PATCH v3 0/5] Write a good 'stash store' for autostash","fromName":"Ramkumar Ramachandra","fromEmail":"artagnon@gmail.com","sentAt":"2013-06-15T13:13:21Z","receivedAt":"2013-06-15T13:13:21Z","isPatch":true,"sender":{"key":"r@artagnon.com","avatar":"https://avatars.githubusercontent.com/u/37226?v=4"},"body":"The interface actually makes sense in this iteration, thanks to Junio.\nAlso fix minor nits pointed out by Phil Hord.\n\nThanks.\n\nRamkumar Ramachandra (5):\n  stash doc: add a warning about using create\n  stash doc: document short form -p in synopsis\n  stash: simplify option parser for create\n  stash: introduce 'git stash store'\n  rebase: use 'git stash store' to simplify logic\n\n Documentation/git-stash.txt | 13 ++++++++++--\n git-rebase.sh               |  7 ++----\n git-stash.sh                | 52 ++++++++++++++++++++++++++++++++++++---------\n t/t3903-stash.sh            | 19 +++++++++++++++++\n 4 files changed, 74 insertions(+), 17 deletions(-)\n\n-- \n1.8.3.1.441.gd7d6b72.dirty\n"},{"id":"220944","messageId":"1371302006-29775-2-git-send-email-artagnon@gmail.com","threadId":"34148","inReplyTo":"1371302006-29775-1-git-send-email-artagnon@gmail.com","subject":"[PATCH v3 1/5] stash doc: add a warning about using create","fromName":"Ramkumar Ramachandra","fromEmail":"artagnon@gmail.com","sentAt":"2013-06-15T13:13:22Z","receivedAt":"2013-06-15T13:13:22Z","isPatch":true,"sender":{"key":"r@artagnon.com","avatar":"https://avatars.githubusercontent.com/u/37226?v=4"},"body":"Add a note saying that the user probably wants \"save\" in the create\ndescription.  While at it, document that it can optionally take a\nmessage in the synopsis.\n\nSigned-off-by: Ramkumar Ramachandra <artagnon@gmail.com>\n---\n Documentation/git-stash.txt | 4 +++-\n 1 file changed, 3 insertions(+), 1 deletion(-)\n\ndiff --git a/Documentation/git-stash.txt b/Documentation/git-stash.txt\nindex 711ffe1..cb0c1a6 100644\n--- a/Documentation/git-stash.txt\n+++ b/Documentation/git-stash.txt\n@@ -16,7 +16,7 @@ SYNOPSIS\n 'git stash' [save [--patch] [-k|--[no-]keep-index] [-q|--quiet]\n \t     [-u|--include-untracked] [-a|--all] [<message>]]\n 'git stash' clear\n-'git stash' create\n+'git stash' create [<message>]\n \n DESCRIPTION\n -----------\n@@ -151,6 +151,8 @@ create::\n \n \tCreate a stash (which is a regular commit object) and return its\n \tobject name, without storing it anywhere in the ref namespace.\n+\tThis is intended to be useful for scripts.  It is probably not\n+\tthe command you want to use; see \"save\" above.\n \n \n DISCUSSION\n-- \n1.8.3.1.441.gd7d6b72.dirty\n"},{"id":"220945","messageId":"1371302006-29775-3-git-send-email-artagnon@gmail.com","threadId":"34148","inReplyTo":"1371302006-29775-1-git-send-email-artagnon@gmail.com","subject":"[PATCH v3 2/5] stash doc: document short form -p in synopsis","fromName":"Ramkumar Ramachandra","fromEmail":"artagnon@gmail.com","sentAt":"2013-06-15T13:13:23Z","receivedAt":"2013-06-15T13:13:23Z","isPatch":true,"sender":{"key":"r@artagnon.com","avatar":"https://avatars.githubusercontent.com/u/37226?v=4"},"body":"'git stash save' can take -p, the short form of --patch, as an option.\nDocument this.\n\nSigned-off-by: Ramkumar Ramachandra <artagnon@gmail.com>\n---\n Documentation/git-stash.txt | 2 +-\n 1 file changed, 1 insertion(+), 1 deletion(-)\n\ndiff --git a/Documentation/git-stash.txt b/Documentation/git-stash.txt\nindex cb0c1a6..632d4fb 100644\n--- a/Documentation/git-stash.txt\n+++ b/Documentation/git-stash.txt\n@@ -13,7 +13,7 @@ SYNOPSIS\n 'git stash' drop [-q|--quiet] [<stash>]\n 'git stash' ( pop | apply ) [--index] [-q|--quiet] [<stash>]\n 'git stash' branch <branchname> [<stash>]\n-'git stash' [save [--patch] [-k|--[no-]keep-index] [-q|--quiet]\n+'git stash' [save [-p|--patch] [-k|--[no-]keep-index] [-q|--quiet]\n \t     [-u|--include-untracked] [-a|--all] [<message>]]\n 'git stash' clear\n 'git stash' create [<message>]\n-- \n1.8.3.1.441.gd7d6b72.dirty\n"},{"id":"220943","messageId":"1371302006-29775-4-git-send-email-artagnon@gmail.com","threadId":"34148","inReplyTo":"1371302006-29775-1-git-send-email-artagnon@gmail.com","subject":"[PATCH v3 3/5] stash: simplify option parser for create","fromName":"Ramkumar Ramachandra","fromEmail":"artagnon@gmail.com","sentAt":"2013-06-15T13:13:24Z","receivedAt":"2013-06-15T13:13:24Z","isPatch":true,"sender":{"key":"r@artagnon.com","avatar":"https://avatars.githubusercontent.com/u/37226?v=4"},"body":"The option parser for create unnecessarily checks \"$1\" inside a case\nstatement that matches \"$1\" in the first place.\n\nSigned-off-by: Ramkumar Ramachandra <artagnon@gmail.com>\n---\n git-stash.sh | 5 +----\n 1 file changed, 1 insertion(+), 4 deletions(-)\n\ndiff --git a/git-stash.sh b/git-stash.sh\nindex bbefdf6..64800b8 100755\n--- a/git-stash.sh\n+++ b/git-stash.sh\n@@ -546,10 +546,7 @@ clear)\n \tclear_stash \"$@\"\n \t;;\n create)\n-\tif test $# -gt 0 && test \"$1\" = create\n-\tthen\n-\t\tshift\n-\tfi\n+\tshift\n \tcreate_stash \"$*\" && echo \"$w_commit\"\n \t;;\n drop)\n-- \n1.8.3.1.441.gd7d6b72.dirty\n"},{"id":"220941","messageId":"1371302006-29775-5-git-send-email-artagnon@gmail.com","threadId":"34148","inReplyTo":"1371302006-29775-1-git-send-email-artagnon@gmail.com","subject":"[PATCH v3 4/5] stash: introduce 'git stash store'","fromName":"Ramkumar Ramachandra","fromEmail":"artagnon@gmail.com","sentAt":"2013-06-15T13:13:25Z","receivedAt":"2013-06-15T13:13:25Z","isPatch":true,"sender":{"key":"r@artagnon.com","avatar":"https://avatars.githubusercontent.com/u/37226?v=4"},"body":"save_stash() contains the logic for doing two potentially independent\noperations; the first is preparing the stash merge commit, and the\nsecond is updating the stash ref/ reflog accordingly.  While the first\noperation is abstracted out into a create_stash() for callers to access\nvia 'git stash create', the second one is not.  Fix this by factoring\nout the logic for storing the stash into a store_stash() that callers\ncan access via 'git stash store'.\n\nLike create, store is not intended for end user interactive use, but for\ncallers in other scripts.  We can simplify the logic in the\nrebase.autostash feature using this new subcommand.\n\nSigned-off-by: Ramkumar Ramachandra <artagnon@gmail.com>\n---\n Documentation/git-stash.txt |  7 +++++++\n git-stash.sh                | 47 +++++++++++++++++++++++++++++++++++++++------\n t/t3903-stash.sh            | 19 ++++++++++++++++++\n 3 files changed, 67 insertions(+), 6 deletions(-)\n\ndiff --git a/Documentation/git-stash.txt b/Documentation/git-stash.txt\nindex 632d4fb..db7e803 100644\n--- a/Documentation/git-stash.txt\n+++ b/Documentation/git-stash.txt\n@@ -17,6 +17,7 @@ SYNOPSIS\n \t     [-u|--include-untracked] [-a|--all] [<message>]]\n 'git stash' clear\n 'git stash' create [<message>]\n+'git stash' store [-m|--message <message>] [-q|--quiet] <commit>\n \n DESCRIPTION\n -----------\n@@ -154,6 +155,12 @@ create::\n \tThis is intended to be useful for scripts.  It is probably not\n \tthe command you want to use; see \"save\" above.\n \n+store::\n+\n+\tStore a given stash created via 'git stash create' (which is a\n+\tdangling merge commit) in the stash ref, updating the stash\n+\treflog.  This is intended to be useful for scripts.  It is\n+\tprobably not the command you want to use; see \"save\" above.\n \n DISCUSSION\n ----------\ndiff --git a/git-stash.sh b/git-stash.sh\nindex 64800b8..62e8cb6 100755\n--- a/git-stash.sh\n+++ b/git-stash.sh\n@@ -156,6 +156,41 @@ create_stash () {\n \tdie \"$(gettext \"Cannot record working tree state\")\"\n }\n \n+store_stash () {\n+\twhile test $# != 0\n+\tdo\n+\t\tcase \"$1\" in\n+\t\t-m|--message)\n+\t\t\tshift\n+\t\t\tstash_msg=\"$1\"\n+\t\t\t;;\n+\t\t-q|--quiet)\n+\t\t\tquiet=t\n+\t\t\t;;\n+\t\t*)\n+\t\t\tbreak\n+\t\t\t;;\n+\t\tesac\n+\t\tshift\n+\tdone\n+\ttest $# == 1 ||\n+\tdie \"$(eval_gettext \"\\\"$dashless store\\\" requires one <commit> argument\")\"\n+\n+\tw_commit=\"$1\"\n+\tif test -z \"$stash_msg\"\n+\tthen\n+\t\tstash_msg=\"Created via \\\"git stash store\\\".\"\n+\tfi\n+\n+\t# Make sure the reflog for stash is kept.\n+\t: >>\"$GIT_DIR/logs/$ref_stash\"\n+\tgit update-ref -m \"$stash_msg\" $ref_stash $w_commit\n+\tret=$?\n+\ttest $ret != 0 && test -z $quiet &&\n+\tdie \"$(eval_gettext \"Cannot update \\$ref_stash with \\$w_commit\")\"\n+\treturn $ret\n+}\n+\n save_stash () {\n \tkeep_index=\n \tpatch_mode=\n@@ -227,12 +262,8 @@ save_stash () {\n \t\tclear_stash || die \"$(gettext \"Cannot initialize stash\")\"\n \n \tcreate_stash \"$stash_msg\" $untracked\n-\n-\t# Make sure the reflog for stash is kept.\n-\t: >>\"$GIT_DIR/logs/$ref_stash\"\n-\n-\tgit update-ref -m \"$stash_msg\" $ref_stash $w_commit ||\n-\t\tdie \"$(gettext \"Cannot save the current status\")\"\n+\tstore_stash -m \"$stash_msg\" -q $w_commit ||\n+\tdie \"$(gettext \"Cannot save the current status\")\"\n \tsay Saved working directory and index state \"$stash_msg\"\n \n \tif test -z \"$patch_mode\"\n@@ -549,6 +580,10 @@ create)\n \tshift\n \tcreate_stash \"$*\" && echo \"$w_commit\"\n \t;;\n+store)\n+\tshift\n+\tstore_stash \"$@\"\n+\t;;\n drop)\n \tshift\n \tdrop_stash \"$@\"\ndiff --git a/t/t3903-stash.sh b/t/t3903-stash.sh\nindex 5dfbda7..75189ec 100755\n--- a/t/t3903-stash.sh\n+++ b/t/t3903-stash.sh\n@@ -637,4 +637,23 @@ test_expect_success 'stash where working directory contains \"HEAD\" file' '\n \ttest_cmp output expect\n '\n \n+test_expect_success 'store called with invalid commit' '\n+\ttest_must_fail git stash store foo\n+'\n+\n+test_expect_success 'store updates stash ref and reflog' '\n+\tgit stash clear &&\n+\tgit reset --hard &&\n+\techo quux >bazzy &&\n+\tgit add bazzy &&\n+\tSTASH_ID=$(git stash create) &&\n+\tgit reset --hard &&\n+\t! grep quux bazzy &&\n+\tgit stash store -m quuxery $STASH_ID &&\n+\ttest $(cat .git/refs/stash) = $STASH_ID &&\n+\tgrep $STASH_ID .git/logs/refs/stash &&\n+\tgit stash pop &&\n+\tgrep quux bazzy\n+'\n+\n test_done\n-- \n1.8.3.1.441.gd7d6b72.dirty\n"},{"id":"220942","messageId":"1371302006-29775-6-git-send-email-artagnon@gmail.com","threadId":"34148","inReplyTo":"1371302006-29775-1-git-send-email-artagnon@gmail.com","subject":"[PATCH v3 5/5] rebase: use 'git stash store' to simplify logic","fromName":"Ramkumar Ramachandra","fromEmail":"artagnon@gmail.com","sentAt":"2013-06-15T13:13:26Z","receivedAt":"2013-06-15T13:13:26Z","isPatch":true,"sender":{"key":"r@artagnon.com","avatar":"https://avatars.githubusercontent.com/u/37226?v=4"},"body":"rebase has no reason to know about the implementation of the stash.  In\nthe case when applying the autostash results in conflicts, replace the\nrelevant code in finish_rebase () to simply call 'git stash store'.\n\nSigned-off-by: Ramkumar Ramachandra <artagnon@gmail.com>\n---\n git-rebase.sh | 7 ++-----\n 1 file changed, 2 insertions(+), 5 deletions(-)\n\ndiff --git a/git-rebase.sh b/git-rebase.sh\nindex d0c11a9..17be392 100755\n--- a/git-rebase.sh\n+++ b/git-rebase.sh\n@@ -153,11 +153,8 @@ finish_rebase () {\n \t\tthen\n \t\t\techo \"$(gettext 'Applied autostash.')\"\n \t\telse\n-\t\t\tref_stash=refs/stash &&\n-\t\t\t>>\"$GIT_DIR/logs/$ref_stash\" &&\n-\t\t\tgit update-ref -m \"autostash\" $ref_stash $stash_sha1 ||\n-\t\t\tdie \"$(eval_gettext 'Cannot store $stash_sha1')\"\n-\n+\t\t\tgit stash store -m \"autostash\" -q $stash_sha1 ||\n+\t\t\tdie \"$(eval_gettext \"Cannot store \\$stash_sha1\")\"\n \t\t\tgettext 'Applying autostash resulted in conflicts.\n Your changes are safe in the stash.\n You can run \"git stash pop\" or \"git stash drop\" it at any time.\n-- \n1.8.3.1.441.gd7d6b72.dirty\n"},{"id":"220971","messageId":"7vtxkykfxl.fsf@alter.siamese.dyndns.org","threadId":"34148","inReplyTo":"1371302006-29775-1-git-send-email-artagnon@gmail.com","subject":"Re: [PATCH v3 0/5] Write a good 'stash store' for autostash","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2013-06-16T01:22:30Z","receivedAt":"2013-06-16T01:22:30Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Ramkumar Ramachandra <artagnon@gmail.com> writes:\n\n> Ramkumar Ramachandra (5):\n>   stash doc: add a warning about using create\n>   stash doc: document short form -p in synopsis\n>   stash: simplify option parser for create\n>   stash: introduce 'git stash store'\n>   rebase: use 'git stash store' to simplify logic\n\nLooked sensible overall. I briefly debated myself if \"git stash\nstore\" even needs its own error message that needs to be squelched\nwith -q (as there is no reason for the end user to invoke it), but I\nthink it does not matter that much, and we can remove that part\nfairly easily before it hits 'next'.\n\nWill queue (but I am not on my main machine today, so not very\nsoon).\n\nThanks.\n"},{"id":"221087","messageId":"7vtxkwd1cw.fsf@alter.siamese.dyndns.org","threadId":"34148","inReplyTo":"1371302006-29775-5-git-send-email-artagnon@gmail.com","subject":"Re: [PATCH v3 4/5] stash: introduce 'git stash store'","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2013-06-17T18:43:43Z","receivedAt":"2013-06-17T18:43:43Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Ramkumar Ramachandra <artagnon@gmail.com> writes:\n\n> +\ttest $# == 1 ||\n\nThis is broken under POSIX shells.  No need to resend (will locally\npatch up).\n"},{"id":"221165","messageId":"CALkWK0n3aEC+BxM7iAY=pcy7fKzpLeTAeRf8UttJ+K1PURP2rQ@mail.gmail.com","threadId":"34148","inReplyTo":"7vtxkwd1cw.fsf@alter.siamese.dyndns.org","subject":"Re: [PATCH v3 4/5] stash: introduce 'git stash store'","fromName":"Ramkumar Ramachandra","fromEmail":"artagnon@gmail.com","sentAt":"2013-06-18T08:50:21Z","receivedAt":"2013-06-18T08:50:21Z","isPatch":true,"sender":{"key":"r@artagnon.com","avatar":"https://avatars.githubusercontent.com/u/37226?v=4"},"body":"Junio C Hamano wrote:\n>> +     test $# == 1 ||\n>\n> This is broken under POSIX shells.  No need to resend (will locally\n> patch up).\n\nUgh, my C habit.  Thanks for catching it.\n"},{"id":"221227","messageId":"7v61xba3sj.fsf@alter.siamese.dyndns.org","threadId":"34148","inReplyTo":"CALkWK0n3aEC+BxM7iAY=pcy7fKzpLeTAeRf8UttJ+K1PURP2rQ@mail.gmail.com","subject":"Re: [PATCH v3 4/5] stash: introduce 'git stash store'","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2013-06-18T14:31:40Z","receivedAt":"2013-06-18T14:31:40Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Ramkumar Ramachandra <artagnon@gmail.com> writes:\n\n> Junio C Hamano wrote:\n>>> +     test $# == 1 ||\n>>\n>> This is broken under POSIX shells.  No need to resend (will locally\n>> patch up).\n>\n> Ugh, my C habit.  Thanks for catching it.\n\nYou're welcome---that is what the reviews are for.\n"}]}