git@vger.kernel.org mailing list mirror (one of many)
 help / color / mirror / code / Atom feed
From: Jeff King <peff@peff.net>
To: Pratyush Yadav <me@yadavpratyush.com>
Cc: git@vger.kernel.org
Subject: Re: How to reset selected lines?
Date: Tue, 13 Aug 2019 11:42:39 -0400	[thread overview]
Message-ID: <20190813154239.GA22514@sigill.intra.peff.net> (raw)
In-Reply-To: <20190813141816.yoer6pfjdnlgtj76@localhost.localdomain>

On Tue, Aug 13, 2019 at 07:48:16PM +0530, Pratyush Yadav wrote:

> To put things into context of why I am asking this, git-gui has a 
> feature where you can select parts of a displayed diff, and can 
> stage/unstage those parts. That feature is implemented in git-gui by 
> just generating a diff from the selected lines, and then applying it. 
> Check git-gui/lib/diff.tcl:643 for the implementation.
> 
> Now, I want to add a similar feature, but one that discards/resets the 
> selected lines. And I'd like to avoid the hack that git-gui's 
> apply_range_or_line is. So, is there a cleaner way to do this that does 
> not involve generating a diff and then applying it?

To answer your second question first:

Git's index and trees only understand whole files, so at some point you
must generate the final file content. A diff is an easy way to represent
the changes, apply them to the existing state, and then get that final
content. But it doesn't _have_ to be. You could make some modifications
to what is in the working tree and then say "OK, now stage this.".

BUT. That is probably not what the user wants, if the content in the
index actually has some modifications that are not in the working tree
(i.e., you wouldn't want to overwrite them). Hence we tend to work with
diffs, saying "make these changes to what is already in the index, and
if they conflict, then bail".

So "git add -p", for example, also works by creating diffs, modifying
them, and feeding the result to "apply". You can see the implementation
in git-add--interactive.perl, where it literally calls diff and apply
commands.

And that leads us to the answer to the first question. That script
implements "add -p", but also "checkout -p" (which is what you want),
"reset -p", "stash -p", etc. They differ only in what we diff and how we
apply the result; the main engine of slicing and dicing the diff through
user interaction is the same. See the %patch_modes hash for the list.

-Peff

  reply	other threads:[~2019-08-13 15:42 UTC|newest]

Thread overview: 7+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2019-08-13 14:18 How to reset selected lines? Pratyush Yadav
2019-08-13 15:42 ` Jeff King [this message]
2019-08-13 17:32   ` Junio C Hamano
2019-08-14 11:48   ` Pratyush Yadav
2019-08-14 14:52     ` Jeff King
2019-08-13 22:07 ` Johannes Sixt
2019-08-14 11:11   ` Pratyush Yadav

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

  List information: http://vger.kernel.org/majordomo-info.html

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20190813154239.GA22514@sigill.intra.peff.net \
    --to=peff@peff.net \
    --cc=git@vger.kernel.org \
    --cc=me@yadavpratyush.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
Code repositories for project(s) associated with this public inbox

	https://80x24.org/mirrors/git.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).