4 ms·
Yeah, I had this misconception for a while. I think it's useful to understand how git actually stores objects as blobs and trees, but the mental model of "comm
by dkbrk 5y ago
Yeah, I had this misconception for a while.
I think it's useful to understand how git actually stores objects as blobs and trees, but the mental model of "commits are diffs" is still useful. Commands like git-cherry-pick really make the most sense when thought of in terms of diffs. Internally, for a command like that, git is taking the diff and applying it, anyway, so the model isn't really that inaccurate.
I think the main place I've seen where the mental model of "commits are diffs" breaks down and actually leads to significant confusion and/or mistakes, is when the tree ends up in a weird state, such as in the middle of resolving a merge conflict.
In that situation, it's important to keep in mind there's three separate tree-like things: the actual working tree; the index; and HEAD. And git status shows nothing more or less than the diff between the working tree and the index. I've gotten myself out of some confusing situations just by reminding myself of that and thinking things through very carefully.
- viraptor 5y ago> Commands like git-cherry-pick really make the most sense when thought of in terms of diffs. Also "git show <commit>" will show you some metadata + diff, which doesn't really help either. Then again I'm just happy remembering that parent commit + diff is effectively equivalent to a specific tree. So as long as your think of a patch attached to a specific parent commit you're not really wrong.
- omegalulw 5y ago> I think the main place I've seen where the mental model of "commits are diffs" breaks down and actually leads to significant confusion and/or mistakes, is when the tree ends up in a weird state, such as in the middle of resolving a merge conflict. Not really? With git you just keep track of three things: 1. The actual committed code 2. Code that's in the staging area 3. Code on disk right now (git has official names for these but I forget) Then during a rebase, if there a conflict, the base comes from the parent of the commit (in 1) you are applying the new commit on top of and the conflict is basically how the new commit makes changes w.r.t to the latest commit in 1. This conflict is written to 3 for files that are in conflict (and to 2 for files that aren't) and then you can resolve the conflict in 3, move the new code to 2 and commit that to 1. You can think of all of it in terms of diffs.