{"thread":{"id":"28078","subject":"[PATCH] update-index: add --swap to swap index and worktree content","startedAt":"2011-08-12T14:07:38Z","lastAt":"2011-08-18T01:01:35Z","messageCount":16,"participants":["Nguyễn Thái Ngọc Duy","Michael J Gruber","Nguyen Thai Ngoc Duy","Junio C Hamano","Jeff King","Martin von Zweigbergk"],"isPatch":true,"patchVersion":1,"patchTotal":null},"messages":[{"id":"173400","messageId":"1313158058-7684-1-git-send-email-pclouds@gmail.com","threadId":"28078","inReplyTo":null,"subject":"[PATCH] update-index: add --swap to swap index and worktree content","fromName":"Nguyễn Thái Ngọc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2011-08-12T14:07:38Z","receivedAt":"2011-08-12T14:07:38Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"Sometimes \"git add -p\" with \"e\" to edit the patch does not satisfy me.\nWhat I want is a quick way to modify index content without changing\nworktree, then I can continue adding more hunks to the index.\n\nWith this option, I can swap index out for a quick edit, then swap it in\nagain.\n\nSigned-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n---\n Not sure if anybody has the same needs, enough to polish it and make\n it to master.\n\n builtin/update-index.c |   16 ++++++++++++++++\n 1 files changed, 16 insertions(+), 0 deletions(-)\n\ndiff --git a/builtin/update-index.c b/builtin/update-index.c\nindex a6a23fa..b96065a 100644\n--- a/builtin/update-index.c\n+++ b/builtin/update-index.c\n@@ -22,6 +22,7 @@\n static int allow_add;\n static int allow_remove;\n static int allow_replace;\n+static int swap_entry;\n static int info_only;\n static int force_remove;\n static int verbose;\n@@ -104,6 +105,19 @@ static int add_one_path(struct cache_entry *old, const char *path, int len, stru\n \t\tfree(ce);\n \t\treturn -1;\n \t}\n+\tif (swap_entry) {\n+\t\tstruct checkout state;\n+\t\tif (allow_add || allow_remove)\n+\t\t\tdie(\"--add, --replace and --swap do not play together\");\n+\t\tmemset(&state, 0, sizeof(state));\n+\t\tstate.force = 1;\n+\t\tstate.not_new = 1;\n+\t\tif (add_cache_entry(ce, 0))\n+\t\t\treturn error(\"%s: cannot add to the index\", path);\n+\t\tif (checkout_entry(old, &state, NULL))\n+\t\t\treturn error(\"%s: cannot swap\", path);\n+\t\treturn 0;\n+\t}\n \toption = allow_add ? ADD_CACHE_OK_TO_ADD : 0;\n \toption |= allow_replace ? ADD_CACHE_OK_TO_REPLACE : 0;\n \tif (add_cache_entry(ce, option))\n@@ -727,6 +741,8 @@ int cmd_update_index(int argc, const char **argv, const char *prefix)\n \t\t\t\"let files replace directories and vice-versa\", 1),\n \t\tOPT_SET_INT(0, \"remove\", &allow_remove,\n \t\t\t\"notice files missing from worktree\", 1),\n+\t\tOPT_SET_INT(0, \"swap\", &swap_entry,\n+\t\t\t\"swap the content of index and worktree\", 1),\n \t\tOPT_BIT(0, \"unmerged\", &refresh_args.flags,\n \t\t\t\"refresh even if index contains unmerged entries\",\n \t\t\tREFRESH_UNMERGED),\n-- \n1.7.4.74.g639db\n"},{"id":"173605","messageId":"4E4A6A43.7040706@drmicha.warpmail.net","threadId":"28078","inReplyTo":"1313158058-7684-1-git-send-email-pclouds@gmail.com","subject":"Re: [PATCH] update-index: add --swap to swap index and worktree content","fromName":"Michael J Gruber","fromEmail":"git@drmicha.warpmail.net","sentAt":"2011-08-16T13:01:55Z","receivedAt":"2011-08-16T13:01:55Z","isPatch":true,"sender":{"key":"git@grubix.eu","avatar":"https://avatars.githubusercontent.com/u/233215?v=4"},"body":"Nguyễn Thái Ngọc Duy venit, vidit, dixit 12.08.2011 16:07:\n> Sometimes \"git add -p\" with \"e\" to edit the patch does not satisfy me.\n> What I want is a quick way to modify index content without changing\n> worktree, then I can continue adding more hunks to the index.\n> \n> With this option, I can swap index out for a quick edit, then swap it in\n> again.\n\nI had to think about that explanation for a while (partly because \"git\nadd\" does not alter the wt either). So, your patch would support the\nfollowing workflow:\n\ngit add foo # have index == wt\nhack foo # change foo in wt\ngit update-index --swap foo # add foo and reset to previous state\n\nAm I understanding you right? The option could trickle down to \"add\".\n\nI share the pov that \"add -p with e\" sometimes doesn't cut it. But\nsimilarly, the fact that \"add -p\" can't be used to undo a previous \"add\n-p\" is suboptimal. Both issues could be solved with a 3way stage tool. I\nhave this on my todo/wish list, and I seem to recall that Jeff or Junio\ncame up with a few lines of (scripting) code for that. That would depend\non the availability of proper tools, though (e.g. vim in diff mode).\n\n--swap might be useful nevertheless.\n\n> Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>\n> ---\n>  Not sure if anybody has the same needs, enough to polish it and make\n>  it to master.\n> \n>  builtin/update-index.c |   16 ++++++++++++++++\n>  1 files changed, 16 insertions(+), 0 deletions(-)\n> \n> diff --git a/builtin/update-index.c b/builtin/update-index.c\n> index a6a23fa..b96065a 100644\n> --- a/builtin/update-index.c\n> +++ b/builtin/update-index.c\n> @@ -22,6 +22,7 @@\n>  static int allow_add;\n>  static int allow_remove;\n>  static int allow_replace;\n> +static int swap_entry;\n>  static int info_only;\n>  static int force_remove;\n>  static int verbose;\n> @@ -104,6 +105,19 @@ static int add_one_path(struct cache_entry *old, const char *path, int len, stru\n>  \t\tfree(ce);\n>  \t\treturn -1;\n>  \t}\n> +\tif (swap_entry) {\n> +\t\tstruct checkout state;\n> +\t\tif (allow_add || allow_remove)\n> +\t\t\tdie(\"--add, --replace and --swap do not play together\");\n> +\t\tmemset(&state, 0, sizeof(state));\n> +\t\tstate.force = 1;\n> +\t\tstate.not_new = 1;\n> +\t\tif (add_cache_entry(ce, 0))\n> +\t\t\treturn error(\"%s: cannot add to the index\", path);\n> +\t\tif (checkout_entry(old, &state, NULL))\n> +\t\t\treturn error(\"%s: cannot swap\", path);\n> +\t\treturn 0;\n> +\t}\n>  \toption = allow_add ? ADD_CACHE_OK_TO_ADD : 0;\n>  \toption |= allow_replace ? ADD_CACHE_OK_TO_REPLACE : 0;\n>  \tif (add_cache_entry(ce, option))\n> @@ -727,6 +741,8 @@ int cmd_update_index(int argc, const char **argv, const char *prefix)\n>  \t\t\t\"let files replace directories and vice-versa\", 1),\n>  \t\tOPT_SET_INT(0, \"remove\", &allow_remove,\n>  \t\t\t\"notice files missing from worktree\", 1),\n> +\t\tOPT_SET_INT(0, \"swap\", &swap_entry,\n> +\t\t\t\"swap the content of index and worktree\", 1),\n>  \t\tOPT_BIT(0, \"unmerged\", &refresh_args.flags,\n>  \t\t\t\"refresh even if index contains unmerged entries\",\n>  \t\t\tREFRESH_UNMERGED),\n"},{"id":"173614","messageId":"CACsJy8DMwqM4rPfAeaXnvDEg1Pv4Y8q7+eJJBeO+ZyaN-m0oZw@mail.gmail.com","threadId":"28078","inReplyTo":"4E4A6A43.7040706@drmicha.warpmail.net","subject":"Re: [PATCH] update-index: add --swap to swap index and worktree content","fromName":"Nguyen Thai Ngoc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2011-08-16T14:45:25Z","receivedAt":"2011-08-16T14:45:25Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"2011/8/16 Michael J Gruber <git@drmicha.warpmail.net>:\n> I had to think about that explanation for a while (partly because \"git\n> add\" does not alter the wt either). So, your patch would support the\n> following workflow:\n>\n> git add foo # have index == wt\n> hack foo # change foo in wt\n> git update-index --swap foo # add foo and reset to previous state\n>\n> Am I understanding you right? The option could trickle down to \"add\".\n\nWell, the point is I want to skip the first phase of normal edit path\n(wt -> index -> commit) and edit index directly (even in parts that\nare not touched by wt, which means \"git add -e\" is useless), leaving\nmy wt \"unchanged\". Sometimes wt is just too dirty I don't want to make\nany more changes to it while I focus on \"index -> commit\" phase.\n\nI could add an option to fire up editor with a temporary file\ncontaining current index content and automatically update index after\neditor is closed. But I'd lose the ability to diff my changes. So I do\nneed to wt to change index without losing my current wt. I have to\nstash my wt somewhere, and index seems a safe place for that.\n\nAfter swapping, it'd look like index -> wt -> commit, I can do \"diff\nHEAD\" to check index vs head. Once I'm done (and create index'), I can\nswap it back to wt -> index' -> commit.\n\nThinking a bit more, this may have another use case (for lazy guys\nlike me, anyway). Assume I have separate changes in wt and I'm ready\nto make many commit. I should make good commits, which means tests (or\nat least a compile to see I don't miss any changes). So I add related\nchanges to index, then swap wt/index so index becomes wt (and old wt\nhidden in index). Test what is to be committed. Good? Swap back,\ncommit. Repeat with the rest of changes in wt.\n\nMy current workflow is picking changes I believe should go together,\ncommit, then \"rebase -i\", stopping at each commit to test. It takes\nlonger (especially when I mis-pick changes).\n\n> I share the pov that \"add -p with e\" sometimes doesn't cut it. But\n> similarly, the fact that \"add -p\" can't be used to undo a previous \"add\n> -p\" is suboptimal. Both issues could be solved with a 3way stage tool. I\n> have this on my todo/wish list, and I seem to recall that Jeff or Junio\n> came up with a few lines of (scripting) code for that. That would depend\n> on the availability of proper tools, though (e.g. vim in diff mode).\n\nThat'd be great.\n-- \nDuy\n"},{"id":"173636","messageId":"7vippxgm6y.fsf@alter.siamese.dyndns.org","threadId":"28078","inReplyTo":"1313158058-7684-1-git-send-email-pclouds@gmail.com","subject":"Re: [PATCH] update-index: add --swap to swap index and worktree content","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2011-08-16T20:01:41Z","receivedAt":"2011-08-16T20:01:41Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Nguyễn Thái Ngọc Duy  <pclouds@gmail.com> writes:\n\n> What I want is a quick way to modify index content without changing\n> worktree, then I can continue adding more hunks to the index.\n\nWhy would you even want to do that?\n\nSuppose you want to update hello.c in the index but not in the working\ntree for whatever reason I do not understand.  Presumably you would with\nthis patch do this:\n\n\tedit hello.c\n        git update-index --swap hello.c\n\nassuming that the state of hello.c _before_ the edit was pristine.  But\nthen after that what would you do?  Probably you would commit that\nuntested change, and rebase-i to clean them up later, which is fine.\n\nBUT\n\nAfter swapping, the file in the working tree lacks the change you made to\nthe index, so if you keep working on it after the above \"swap\" in your\neditor, the next \"git add\" will revert whatever you did with the first\n\"edit\".\n\nI think that makes it too error prone and difficult to understand for both\nnew and experienced people.\n\nWhatever the expected use case is, it needs to be explained a lot better.\n"},{"id":"173638","messageId":"20110816210108.GA13710@sigill.intra.peff.net","threadId":"28078","inReplyTo":"7vippxgm6y.fsf@alter.siamese.dyndns.org","subject":"Re: [PATCH] update-index: add --swap to swap index and worktree content","fromName":"Jeff King","fromEmail":"peff@peff.net","sentAt":"2011-08-16T21:01:08Z","receivedAt":"2011-08-16T21:01:08Z","isPatch":true,"sender":{"key":"peff@peff.net","avatar":"https://avatars.githubusercontent.com/u/45925?v=4"},"body":"On Tue, Aug 16, 2011 at 01:01:41PM -0700, Junio C Hamano wrote:\n\n> Nguyễn Thái Ngọc Duy  <pclouds@gmail.com> writes:\n> \n> > What I want is a quick way to modify index content without changing\n> > worktree, then I can continue adding more hunks to the index.\n> \n> Why would you even want to do that?\n> \n> Suppose you want to update hello.c in the index but not in the working\n> tree for whatever reason I do not understand.  Presumably you would with\n> this patch do this:\n> \n> \tedit hello.c\n>         git update-index --swap hello.c\n> \n> assuming that the state of hello.c _before_ the edit was pristine.  But\n> then after that what would you do?  Probably you would commit that\n> untested change, and rebase-i to clean them up later, which is fine.\n\nI suspect (or at least, this is how I would use it) it is more about\nhaving some changes in the index and some changes in the working tree,\nbut realizing that what's in the index needs tweaked. Something like:\n\n  # add some content with an error\n  echo 'printf(\"hello word!\\n\")' >hello.c\n  git add hello.c\n\n  # work on it more, realizing the error\n  echo 'printf(\"goodbye world!\\n\") >hello.c\n\n  # now what? you want to stage the s/word/world/ fixup,\n  # but you want to keep the hello/goodbye thing as a separate change.\n  # Using anything line-based is going to conflate the two.\n  # The change is simple, though, so you can just as easily edit the\n  # index file, if only you could get to it. So you do:\n  git update-index --swap hello.c\n  sed -i s/word/world/ hello.c\n  git update-index --swap hello.c\n\nSo the swap really functions as a toggle of \"I would like to work on\nthe index version for a minute\", and then you toggle back when you're\ndone.\n\nI can think of two ways to do the same thing that are a little less\nconfusing or error-prone, though:\n\n  1. A command to dump the index version to a tempfile, run $EDITOR on\n     it, and then read it back in. Technically this restricts you to\n     using $EDITOR to make the changes, but in practice that is probably\n     fine.\n\n  2. You can dump the file to a pipe yourself, but getting it back into\n     the index is a little bit awkward. You have to do something like:\n\n       blob=`git cat-file blob :hello.c |\n             sed 's/word/world/ |\n             git hash-object --stdin -w`\n       mode=`git ls-files -s hello.c | cut -d' ' -f1`\n       git update-index --cacheinfo $mode $blob hello.c\n\n     it would be much nicer if this was:\n\n       git cat-file blob :hello.c |\n       sed 's/word/world/ |\n       git add --stdin-contents hello.c\n\n     However, I expect this sort of piping is the minority case, and\n     most people would be happy with (1).\n\n-Peff\n"},{"id":"173640","messageId":"7vbovpggva.fsf@alter.siamese.dyndns.org","threadId":"28078","inReplyTo":"20110816210108.GA13710@sigill.intra.peff.net","subject":"Re: [PATCH] update-index: add --swap to swap index and worktree content","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2011-08-16T21:56:41Z","receivedAt":"2011-08-16T21:56:41Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Jeff King <peff@peff.net> writes:\n\n>   # add some content with an error\n>   echo 'printf(\"hello word!\\n\")' >hello.c\n>   git add hello.c\n>\n>   # work on it more, realizing the error\n>   echo 'printf(\"goodbye world!\\n\") >hello.c\n>\n>   # now what? you want to stage the s/word/world/ fixup,\n>   # but you want to keep the hello/goodbye thing as a separate change.\n>   # Using anything line-based is going to conflate the two.\n>   # The change is simple, though, so you can just as easily edit the\n>   # index file, if only you could get to it. So you do:\n>   git update-index --swap hello.c\n>   sed -i s/word/world/ hello.c\n>   git update-index --swap hello.c\n>\n> So the swap really functions as a toggle of \"I would like to work on\n> the index version for a minute\", and then you toggle back when you're\n> done.\n\nAnd you have to redo what you did to the index version in the working tree\nafter the second \"swap\", no?\n"},{"id":"173641","messageId":"20110816222212.GA19471@sigill.intra.peff.net","threadId":"28078","inReplyTo":"7vbovpggva.fsf@alter.siamese.dyndns.org","subject":"Re: [PATCH] update-index: add --swap to swap index and worktree content","fromName":"Jeff King","fromEmail":"peff@peff.net","sentAt":"2011-08-16T22:22:12Z","receivedAt":"2011-08-16T22:22:12Z","isPatch":true,"sender":{"key":"peff@peff.net","avatar":"https://avatars.githubusercontent.com/u/45925?v=4"},"body":"On Tue, Aug 16, 2011 at 02:56:41PM -0700, Junio C Hamano wrote:\n\n> Jeff King <peff@peff.net> writes:\n> \n> >   # add some content with an error\n> >   echo 'printf(\"hello word!\\n\")' >hello.c\n> >   git add hello.c\n> >\n> >   # work on it more, realizing the error\n> >   echo 'printf(\"goodbye world!\\n\") >hello.c\n> >\n> >   # now what? you want to stage the s/word/world/ fixup,\n> >   # but you want to keep the hello/goodbye thing as a separate change.\n> >   # Using anything line-based is going to conflate the two.\n> >   # The change is simple, though, so you can just as easily edit the\n> >   # index file, if only you could get to it. So you do:\n> >   git update-index --swap hello.c\n> >   sed -i s/word/world/ hello.c\n> >   git update-index --swap hello.c\n> >\n> > So the swap really functions as a toggle of \"I would like to work on\n> > the index version for a minute\", and then you toggle back when you're\n> > done.\n> \n> And you have to redo what you did to the index version in the working tree\n> after the second \"swap\", no?\n\nNo. The point is that I _already_ did it in the working tree version\nwhile doing my s/hello/goodbye/ change (let's call this the \"new\nchange\"). And ideally I would just use \"git add -p\" to stage only the\ns/word/world/ change (let's call this the \"fixup\"). But they're tangled\nin a single hunk, and I need some way of splitting them.\n\nYou could also use \"add -e\" to solve this situation. In this case, you\nend up removing the \"new change\" from the patch, leaving only the fixup.\nIn this toy case, it would be pretty easy. But in more complex cases,\nthe fixup is a one-liner, but the \"new change\" is many lines. So rather\nthan edit out the new changes, it is simpler to recreate the fixup on\ntop of the index version.\n\n-Peff\n"},{"id":"173645","messageId":"7vzkj9eza2.fsf@alter.siamese.dyndns.org","threadId":"28078","inReplyTo":"20110816222212.GA19471@sigill.intra.peff.net","subject":"Re: [PATCH] update-index: add --swap to swap index and worktree content","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2011-08-16T23:01:57Z","receivedAt":"2011-08-16T23:01:57Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Jeff King <peff@peff.net> writes:\n\n>> > So the swap really functions as a toggle of \"I would like to work on\n>> > the index version for a minute\", and then you toggle back when you're\n>> > done.\n>> \n>> And you have to redo what you did to the index version in the working tree\n>> after the second \"swap\", no?\n>\n> No. The point is that I _already_ did it in the working tree version\n\nBut that does not change that you have to do that twice. You may already\nhave done so in the working tree, and then redo it in the old indexed\nversion again.\n\n> while doing my s/hello/goodbye/ change (let's call this the \"new\n> change\"). And ideally I would just use \"git add -p\" to stage only the\n> s/word/world/ change (let's call this the \"fixup\"). But they're tangled\n> in a single hunk, and I need some way of splitting them.\n\nAs a way to punt from making \"add -e\" usable, I'd think it would be a\nworkable q&d workaround, even though it feels wrong, and I would imagine\nthat normal people would probably prefer the \"check out to a temporary\nfile to be edited\" solution you wrote in your previous message.\n"},{"id":"173646","messageId":"20110816230654.GA21793@sigill.intra.peff.net","threadId":"28078","inReplyTo":"7vzkj9eza2.fsf@alter.siamese.dyndns.org","subject":"Re: [PATCH] update-index: add --swap to swap index and worktree content","fromName":"Jeff King","fromEmail":"peff@peff.net","sentAt":"2011-08-16T23:06:54Z","receivedAt":"2011-08-16T23:06:54Z","isPatch":true,"sender":{"key":"peff@peff.net","avatar":"https://avatars.githubusercontent.com/u/45925?v=4"},"body":"On Tue, Aug 16, 2011 at 04:01:57PM -0700, Junio C Hamano wrote:\n\n> > No. The point is that I _already_ did it in the working tree version\n> \n> But that does not change that you have to do that twice. You may already\n> have done so in the working tree, and then redo it in the old indexed\n> version again.\n\nRight. The point is that the changes are tangled, to the point that it\nis simpler to recreate them on one side than it is to instruct a tool\nabout how to untangle them. If they weren't tangled, then I would simply\nmake the change in the working tree, and then \"add -p\" it into the\nindex.\n\nIt's certainly not the dominant case. I'd say I run into it no more\nfrequently than once every week or so. I usually end up using \"add -e\"\nto do what I want, but it's very error prone and annoying.\n\n> > while doing my s/hello/goodbye/ change (let's call this the \"new\n> > change\"). And ideally I would just use \"git add -p\" to stage only the\n> > s/word/world/ change (let's call this the \"fixup\"). But they're tangled\n> > in a single hunk, and I need some way of splitting them.\n> \n> As a way to punt from making \"add -e\" usable, I'd think it would be a\n> workable q&d workaround, even though it feels wrong, and I would imagine\n> that normal people would probably prefer the \"check out to a temporary\n> file to be edited\" solution you wrote in your previous message.\n\nYeah, I think that is the sanest of the options brought up in this\nthread. I'm curious if Duy had another use case, though, that made him\nthink of --swap.\n\n-Peff\n"},{"id":"173657","messageId":"CACsJy8Ad4xPz79jT3O64c3XsCeM8XETJ9bnjK0aisagrYN0CMA@mail.gmail.com","threadId":"28078","inReplyTo":"20110816230654.GA21793@sigill.intra.peff.net","subject":"Re: [PATCH] update-index: add --swap to swap index and worktree content","fromName":"Nguyen Thai Ngoc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2011-08-17T02:11:32Z","receivedAt":"2011-08-17T02:11:32Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"2011/8/17 Jeff King <peff@peff.net>:\n>> As a way to punt from making \"add -e\" usable, I'd think it would be a\n>> workable q&d workaround, even though it feels wrong, and I would imagine\n>> that normal people would probably prefer the \"check out to a temporary\n>> file to be edited\" solution you wrote in your previous message.\n>\n> Yeah, I think that is the sanest of the options brought up in this\n\nI blame git for training me always do \"git diff\" before update index.\nBut if we add \"add -e\", I could also make \"add -e -p\" work, (edit\ntemporary file first, then fall back to interactive mode and let me\nreview my changes).\n\n> thread. I'm curious if Duy had another use case, though, that made him\n> think of --swap.\n\nTwo reasons. I already mentioned the ability to quickly checkout index\nfor a quick test (though there could be more problems down that road).\n\nThe other one could be done another way too. I translation\ncoordinator. When a translator sends their translations to me, I'd\npick good translations and commit them, leaving the rest for\ndiscussion. This is why I don't want to touch wt. While adding\ntranslations to index, I may find a mistake in current translation\n(ie. in index) and want to fix it too.\n-- \nDuy\n"},{"id":"173658","messageId":"20110817021727.GA29585@sigill.intra.peff.net","threadId":"28078","inReplyTo":"CACsJy8Ad4xPz79jT3O64c3XsCeM8XETJ9bnjK0aisagrYN0CMA@mail.gmail.com","subject":"Re: [PATCH] update-index: add --swap to swap index and worktree content","fromName":"Jeff King","fromEmail":"peff@peff.net","sentAt":"2011-08-17T02:17:27Z","receivedAt":"2011-08-17T02:17:27Z","isPatch":true,"sender":{"key":"peff@peff.net","avatar":"https://avatars.githubusercontent.com/u/45925?v=4"},"body":"On Wed, Aug 17, 2011 at 09:11:32AM +0700, Nguyen Thai Ngoc Duy wrote:\n\n> I blame git for training me always do \"git diff\" before update index.\n> But if we add \"add -e\", I could also make \"add -e -p\" work, (edit\n> temporary file first, then fall back to interactive mode and let me\n> review my changes).\n\nYeah, that would be cool. But note that \"git add -e\" already exists for\npatch editing.\n\n> Two reasons. I already mentioned the ability to quickly checkout index\n> for a quick test (though there could be more problems down that road).\n\nThat's a good thought. However, in practice, I find I also need other\nfiles from the index to do a successful test. So I end up just\ncommitting what I think is right, and then afterwards do:\n\n  GIT_EDITOR='sed -i \"/^pick .*/aexec make test/\"' git rebase -i\n\nto test and fixup each commit individually.\n\nYou could probably use \"checkout-index\" to create a pristine workspace\nto test. It's a little inefficient to write out all of the files again,\nbut probably the actual build and test procedure would be much more\nexpensive, anyway.\n\n-Peff\n"},{"id":"173672","messageId":"CAOeW2eFx-ETS+1a5b2bUXeT8JJ0WGudKGyF6mxuqyK2OM35qQA@mail.gmail.com","threadId":"28078","inReplyTo":"20110817021727.GA29585@sigill.intra.peff.net","subject":"Re: [PATCH] update-index: add --swap to swap index and worktree content","fromName":"Martin von Zweigbergk","fromEmail":"martin.von.zweigbergk@gmail.com","sentAt":"2011-08-17T14:13:08Z","receivedAt":"2011-08-17T14:13:08Z","isPatch":true,"sender":{"key":"martinvonz@gmail.com","avatar":"https://avatars.githubusercontent.com/u/891642?v=4"},"body":"Hi,\n\nOn Tue, Aug 16, 2011 at 10:17 PM, Jeff King <peff@peff.net> wrote:\n> On Wed, Aug 17, 2011 at 09:11:32AM +0700, Nguyen Thai Ngoc Duy wrote:\n>\n>> Two reasons. I already mentioned the ability to quickly checkout index\n>> for a quick test (though there could be more problems down that road).\n>\n> That's a good thought. However, in practice, I find I also need other\n> files from the index to do a successful test. So I end up just\n> committing what I think is right, and then afterwards do:\n\nMaybe a stupid question, but \"update-index --swap\" would swap all\nfiles, right? So what \"other files from the index\" would there be?\n\nMaybe the above shows that I'm missing something. Still, would it be\npossible to achieve the use case with something like the following?\n\ngit stash --keep-index\n# fix up files, test etc.\ngit add ....\ngit commit\ngit cherry-pick --strategy=theirs stash && git stash drop\n\nMartin\n"},{"id":"173674","messageId":"CACsJy8Cc5PLLXj8TgGS0EjZ5SRyBGfo6WUnYaZNkdnZv62WQZQ@mail.gmail.com","threadId":"28078","inReplyTo":"CAOeW2eFx-ETS+1a5b2bUXeT8JJ0WGudKGyF6mxuqyK2OM35qQA@mail.gmail.com","subject":"Re: [PATCH] update-index: add --swap to swap index and worktree content","fromName":"Nguyen Thai Ngoc Duy","fromEmail":"pclouds@gmail.com","sentAt":"2011-08-17T14:32:55Z","receivedAt":"2011-08-17T14:32:55Z","isPatch":true,"sender":{"key":"pclouds@gmail.com","avatar":"https://avatars.githubusercontent.com/u/720?v=4"},"body":"On Wed, Aug 17, 2011 at 9:13 PM, Martin von Zweigbergk\n<martin.von.zweigbergk@gmail.com> wrote:\n> Hi,\n>\n> On Tue, Aug 16, 2011 at 10:17 PM, Jeff King <peff@peff.net> wrote:\n>> On Wed, Aug 17, 2011 at 09:11:32AM +0700, Nguyen Thai Ngoc Duy wrote:\n>>\n>>> Two reasons. I already mentioned the ability to quickly checkout index\n>>> for a quick test (though there could be more problems down that road).\n>>\n>> That's a good thought. However, in practice, I find I also need other\n>> files from the index to do a successful test. So I end up just\n>> committing what I think is right, and then afterwards do:\n>\n> Maybe a stupid question, but \"update-index --swap\" would swap all\n> files, right? So what \"other files from the index\" would there be?\n\nThat's some of the \"problems down that road\", another one being\nremoved files in index. Still the ability to do a quick compile on a\nsingle file is cool.\n\n> Maybe the above shows that I'm missing something. Still, would it be\n> possible to achieve the use case with something like the following?\n>\n> git stash --keep-index\n> # fix up files, test etc.\n> git add ....\n> git commit\n> git cherry-pick --strategy=theirs stash && git stash drop\n\nPretty much (if I understand git-stash correctly, I haven't used it\nmuch), except that if I change my mind mid way, I can switch back to\nthe original state and keep working:\n\n1. git add -p ...\n2. git update-index --swap foo # index <-> wt\n3. # make some minor edit, \"make foo.o\", oops failed, I missed some hunks\n4. git checkout -p ...\n5. # still not happy, more changes should be made on both index and wt\n6. git update-index --swap foo # now index is index, wt is wt\n7. # edit some more, when ready to commit, repeat steps 2-6 again\n8. git commit\n-- \nDuy\n"},{"id":"173682","messageId":"7vr54jevxp.fsf@alter.siamese.dyndns.org","threadId":"28078","inReplyTo":"CAOeW2eFx-ETS+1a5b2bUXeT8JJ0WGudKGyF6mxuqyK2OM35qQA@mail.gmail.com","subject":"Re: [PATCH] update-index: add --swap to swap index and worktree content","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2011-08-17T18:26:26Z","receivedAt":"2011-08-17T18:26:26Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Martin von Zweigbergk <martin.von.zweigbergk@gmail.com> writes:\n\n> Maybe the above shows that I'm missing something. Still, would it be\n> possible to achieve the use case with something like the following?\n>\n> git stash --keep-index\n\nWhile I sense a vague aversion to committing in general in this\ndiscussion, which I am not particularly fond of, the whole point of\n\"stash\" is to avoid the mental burden of going over the \"hump\" of\ncommitting something not ready and to replace it with a \"save it as a\ntemporary state\" that technically has the same overhead of committing but\nhas a lot less mental overhead. Perhaps \"swapping the state of all and/or\nselected paths\" fits better in \"stash\", not \"update-index\"?\n\nI dunno, but in general, a new feature to cater to _common_ end user needs\nshould fit in the Porcelain layer. We would be doing something wrong if we\nneed to teach an obscure option of lower plumbing to end users.\n\nI personally used to feel that \"ls-files -u\" during a conflicted merge to\nbe the single sore-thumb that stuck out from this point of view, but these\ndays \"status -s\" gives the same information in a more useful way to the\nend users, and I am reasonably happy with that. It may be that the end\nuser operation (perhaps \"stash --swap\", but I am not married to that) that\nfits well in common workflows ends up using \"update-index --swap\" as an\nunderlying implementation detail, but I'd prefer to see how the final end\nuser experience using Porcelain would look like first.\n"},{"id":"173690","messageId":"20110817194621.GA352@sigill.intra.peff.net","threadId":"28078","inReplyTo":"CAOeW2eFx-ETS+1a5b2bUXeT8JJ0WGudKGyF6mxuqyK2OM35qQA@mail.gmail.com","subject":"Re: [PATCH] update-index: add --swap to swap index and worktree content","fromName":"Jeff King","fromEmail":"peff@peff.net","sentAt":"2011-08-17T19:46:22Z","receivedAt":"2011-08-17T19:46:22Z","isPatch":true,"sender":{"key":"peff@peff.net","avatar":"https://avatars.githubusercontent.com/u/45925?v=4"},"body":"On Wed, Aug 17, 2011 at 10:13:08AM -0400, Martin von Zweigbergk wrote:\n\n> >> Two reasons. I already mentioned the ability to quickly checkout index\n> >> for a quick test (though there could be more problems down that road).\n> >\n> > That's a good thought. However, in practice, I find I also need other\n> > files from the index to do a successful test. So I end up just\n> > committing what I think is right, and then afterwards do:\n> \n> Maybe a stupid question, but \"update-index --swap\" would swap all\n> files, right? So what \"other files from the index\" would there be?\n\nHmm. I hadn't really considered swapping everything. I suppose that\nwould work, though I do worry about getting into a confused state when\nyou have swapped one or more files individually, and then want to swap\nthe rest out for testing.\n\nThat is, there is no flag to say \"this file was swapped\", so there is no\nway to say \"swap all of the index files out, except those I have already\nswapped\". But if you were disciplined to only do:\n\n  git update-index --swap\n  $EDITOR foo.c\n  make test\n  git update-index --swap\n\nand never:\n\n  git update-index --swap foo.c\n  $EDITOR foo.c\n  git update-index --swap ;# oops, we put the WT foo.c back\n  make test\n  git update-index --swap\n\nthen it would work.\n\n-Peff\n"},{"id":"173704","messageId":"CAOeW2eG5LsNLCpdXvphRqkDZZMTRrHiA1-82ckkfWntKvQ7XFg@mail.gmail.com","threadId":"28078","inReplyTo":"20110817194621.GA352@sigill.intra.peff.net","subject":"Re: [PATCH] update-index: add --swap to swap index and worktree content","fromName":"Martin von Zweigbergk","fromEmail":"martin.von.zweigbergk@gmail.com","sentAt":"2011-08-18T01:01:35Z","receivedAt":"2011-08-18T01:01:35Z","isPatch":true,"sender":{"key":"martinvonz@gmail.com","avatar":"https://avatars.githubusercontent.com/u/891642?v=4"},"body":"On Wed, Aug 17, 2011 at 3:46 PM, Jeff King <peff@peff.net> wrote:\n> On Wed, Aug 17, 2011 at 10:13:08AM -0400, Martin von Zweigbergk wrote:\n>\n>> >> Two reasons. I already mentioned the ability to quickly checkout index\n>> >> for a quick test (though there could be more problems down that road).\n>> >\n>> > That's a good thought. However, in practice, I find I also need other\n>> > files from the index to do a successful test. So I end up just\n>> > committing what I think is right, and then afterwards do:\n>>\n>> Maybe a stupid question, but \"update-index --swap\" would swap all\n>> files, right? So what \"other files from the index\" would there be?\n>\n> Hmm. I hadn't really considered swapping everything.\n\nAh, then I see where the misunderstanding lay. I didn't read the\npatch; maybe it would have been clear if I did (and understood it).\n\n> I suppose that\n> would work, though I do worry about getting into a confused state when\n> you have swapped one or more files individually, and then want to swap\n> the rest out for testing.\n\nI have a feeling that I would get confused if I started swapping more\nthan one individual file, so to me it feels like it's more the\npossibility of swapping individual files that could cause confusion,\nwhether or not it is possible to swap all.\n\nI think stashing the work tree feels more right, though. All you\nreally want is to get the work tree version out of the way for a\nwhile, you don't really want it in the index.\n\nMartin\n"}]}