git/list[1] front-page[2] threads[3] people[4] search[5] about
 

Re: How to reset selected lines?

From
Pratyush Yadav <me@yadavpratyush.com>
Date
Aug 14, 2019, 11:48 UTC
Message-ID
<20190814114844.gvb5znje7cpzehkd@localhost.localdomain>
In-Reply-To
<20190813154239.GA22514@sigill.intra.peff.net>
On 13/08/19 11:42AM, Jeff King wrote:
Show 37 quoted lines
> 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.

Ah, so that means I do have to dive into generating diffs. Too bad, I was hoping for a cleaner (read: easier) way.

On that note, I don't suppose there is a way to use git-add--interactive's diff engine from a script, is there? That'd allow me to not write potentially buggy code and solve problems someone already solved.

Thanks for your detailed answer.
-- 
Regards,
Pratyush Yadav
Previous: Junio C HamanoNext: Jeff King
Message 4 of 7 in “How to reset selected lines?”
  1. Pratyush YadavAug 13, 2019
  2. Jeff KingAug 13, 2019
  3. Junio C HamanoAug 13, 2019
  4. Pratyush YadavAug 14, 2019
  5. Jeff KingAug 14, 2019
  6. Johannes SixtAug 13, 2019
  7. Pratyush YadavAug 14, 2019

Read the whole thread, see it on lore, or plain text.

$ cat FOOTERMessages come from the public archive at lore.kernel.org/git, fetched every hour. The front page is chosen and written each morning by an AI editor and can be wrong; the threads themselves are the record. About and API. For agents: an MCP server at https://gitlist.dev/mcp, and any thread, story or person page as Markdown by adding .md to its URL (or sending Accept: text/markdown). Details in /llms.txt.