Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Posted Jan 20, 2024 22:21 UTC (Sat) by apoelstra (subscriber, #75205)In reply to: Jujutsu: a new, Git-compatible version control system by madscientist
Parent article: Jujutsu: a new, Git-compatible version control system
In complicated cases I can imagine using temporary branches in step (c) or before step (a) to avoid losing work.
Is there a way to do this without the reset step?
Posted Jan 20, 2024 22:38 UTC (Sat)
by madscientist (subscriber, #16861)
[Link] (20 responses)
I suppose under the covers Magit does need to use a reset operation (your step (b)) as part of "unstaging" all the changes in the commit-to-be-edited.
If I have a "complicated case", I usually just make more smaller commits in this interactive rebase, then after this interactive rebase is finished I start another one and move the smaller commits to where I want them and squash them. Magit makes interactive rebase so simple that it's easier to just run it multiple times than to get complicated and try to do it all in one go. I can't think of a situation where I'd need a temporary branch.
Posted Jan 21, 2024 5:01 UTC (Sun)
by intelfx (subscriber, #130118)
[Link]
That's exactly the semantics of a git (mixed) reset.
Posted Jan 21, 2024 5:49 UTC (Sun)
by roc (subscriber, #30627)
[Link] (18 responses)
You don't need the staging area if you just move changes directly from the working tree to commits. Hg has that, and even git can do that with "git commit -p".
Jujutsu (which I haven't used, but sounds excellent) takes the next step and gets rid of the working tree as well as a distinct concept. It's just the "working commit", so you can use the same commands to move changes from that commit to other commits that you would use to move changes between any pair of commits. Great!
Posted Jan 22, 2024 2:50 UTC (Mon)
by marcH (subscriber, #57642)
[Link] (1 responses)
With all due respect, you sound like you're not a magit user :-)
Magit presents everything as diff hunks, so I don't really think in terms of "trees" when using it (every day). I just move hunks around freely. I totally understand how the staging area can confuse a lot of people; I frequently use the command line too. But Magit makes it incredibly natural to use. Ask a friend for a demo?
Posted Jan 22, 2024 10:02 UTC (Mon)
by farnz (subscriber, #17727)
[Link]
Having used Magit, a good description of the way it handles things is: "the presence of three types of tree - working copy, index, and commits - is confusing to users. Unify all three into one type of tree, and hide the difference so that as far as a Magit user is concerned, it's all just commits". They do this because commits are the fully featured type of tree, and it's trivial to convert any operation on any type of tree into "turn the tree into a commit, operate on the commit, turn the new commit back into a working copy or an index".
Jujutsu makes Magit's implementation a lot simpler, because instead of Magit having to balance all three types of tree internally, and work out the "correct" way to implement any operation for you, it can instead only implement operations on commits, and get the same advantage. It also doesn't cost any Magit features, since Magit already works this way from a user perspective.
Posted Jan 22, 2024 14:53 UTC (Mon)
by madscientist (subscriber, #16861)
[Link] (14 responses)
It might just be a matter of how you look at things. I treat the index as a way to construct a commit. I expect this is how it was designed to work. So in my mind I have (a) work I'm doing that is not committed, (b) a staging area (usually empty) that I use to construct a new commit from either all or, very often, just selected parts of the work I'm doing, and (c) already committed code.
So yes it is three things but they are all on a continuum of work and it's pretty simple to understand. IMO of course.
I know that as CS folks we like to use a single model for everything, but the reality is that sometimes it's easier to understand things if they have distinct models. I haven't used Jujutsu so I can't say whether it really is simpler to treat everything as the same thing, or not.
I can say that based on the replies here showing command line operations, while Jujutsu may be simpler to use than the Git CLI (I mean... yeah) it seems to me that Magit is simpler than both of them :)
Posted Jan 22, 2024 15:08 UTC (Mon)
by farnz (subscriber, #17727)
[Link] (8 responses)
Note, though, that Magit makes things work by saying that you're always dealing with hunks in a commit - it hides the differences between the working copy, the index, and your forest of commits from you. If Magit makes things simpler, then it does so by reducing the number of things you need to juggle in your head by two - get rid of "working copy" and "index" as separate entities.
Posted Jan 22, 2024 19:25 UTC (Mon)
by madscientist (subscriber, #16861)
[Link] (7 responses)
I don't agree with this.
Staging is visible and important in Magit. It's up-front and clearly distinct. The Magit status buffer shows different sections for the unstaged files, the content of the staging area, and a list of recent commits. And staging files vs. hunks is just a difference in granularity; it doesn't use a separate workflow.
Maybe you mean, it hides the differences in the way you work with the different parts? That might be true to some extent. But it definitely doesn't try to pretend that they are all the same thing; it's more you don't have to remember the various commands and options. For example, it's clear in Magit that neither unstaged or staged hunks are "the same as" a commit.
Posted Jan 22, 2024 21:45 UTC (Mon)
by farnz (subscriber, #17727)
[Link] (6 responses)
Behaviourally, having used Magit, the staging area behaves exactly the same way as a commit does - it's something you can stage hunks to, and aside from naming it differently, it's possible to make Magit treat the staging area exactly the same as a commit.
Aside from it being given a funny name, it's functionally a commit - you don't get different commands for it, or different options, or different behaviours, or indeed anything to justify treating it specially.
Posted Jan 22, 2024 22:07 UTC (Mon)
by madscientist (subscriber, #16861)
[Link] (5 responses)
In addition to staging hunks into the staging area, which could be considered equivalent to amending a commit, you can unstage them again, delete them completely, etc. That is not possible with commits: the only way to modify a commit in that way is to go through a rebase operation.
It's actually more accurate to say that the staging area behaves exactly the same way that the unstaged changes area, except that you can create a commit from the staging area and you can't create a commit directly from the unstaged changes. Other than that staged and unstaged work pretty much identically in Magit, and are treated very differently than commits.
I understand that there could be a different implementation that uses a real commit instead of staging and hides all the work to "unstage" hunks behind the scenes, but that's not how it works and it's not how the mental model is presented.
Posted Jan 23, 2024 10:14 UTC (Tue)
by farnz (subscriber, #17727)
[Link] (4 responses)
Hmm. The version of Magit I've experimented with allowed me to unstage hunks and delete them from commits, and allows me to create a commit directly from the unstaged changes. Under the hood, it did a rebase operation in the process, but from my perspective it was completely transparent; Magit hid this from me.
From my perspective, Magit is completely hiding the staging area from existence - there's something that behaves just like any other commit, and is called the "staging area", and there's unstaged changes which also behave just like any other commit, but are also present in the working copy on disk, but otherwise Magit makes the differences go away, and just works in terms of moving hunks between the various places in the forest of VCS commits I could see. Perhaps you've configured Magit to be more explicit about the staging area? My configuration for Magit is quite large, and has built up over the last decade.
Posted Jan 23, 2024 15:48 UTC (Tue)
by madscientist (subscriber, #16861)
[Link] (3 responses)
It's true that you can ask to "unstage" a hunk in a commit, but what happens is that Magit will add a staged change that reverts that hunk, then an unstaged change that adds it back again. You can choose which one you want and if you want to keep the revert you can apply that change either by adding a new revert commit or by using Magit's fixup facility (which makes a commit then uses rebase to squash it into the original commit, but done for you).
It is pretty different from a UI perspective to unstaging a hunk from the staging area, which simply moves it back to unstaged as if you'd never staged it at all.
Posted Jan 23, 2024 15:51 UTC (Tue)
by farnz (subscriber, #17727)
[Link] (2 responses)
I've never seen that UI behaviour from Magit; you have it set up differently to me (I copied someone else's config ~10 years ago to get started, and stuck with that). I don't ask it to unstage a hunk; I ask it to move hunks between locations, and the staging area is just one of those locations. I can literally ask Magit to move a hunk straight from the commit to the unstaged work, or to the staging area, or to another commit, and it works out what sequence of operations makes that happen for me.
In this setup, there's no need for the staging area - it's just a commit with a funny name - as all the "move hunk" operations work just as well between two commits as they do between a commit and the staging area.
Posted Jan 26, 2024 16:44 UTC (Fri)
by madscientist (subscriber, #16861)
[Link] (1 responses)
I don't know what keys/commands you are using to get the behavior you see, but I'm using bog-standard Magit with all the basic settings and very little customization. The key I use to unstage a hunk is "u". If the cursor is on a hunk that's been staged, then the hunk is moved back to "unstaged changes" by pressing that key. If the cursor is on a hunk in a commit (I view the hunks in the commits by selecting a commit in my "Recent Commits" list then pressing ENTER to see its changes) then I get the behavior I described previously.
Perhaps you are entering some other "commit editing mode" in Magit, that I'm not using. It sounds cool! But in any case there is a clear difference in the UI behavior between staged hunks and hunks in commits.
Posted Jan 30, 2024 12:32 UTC (Tue)
by mathstuf (subscriber, #69389)
[Link]
Posted Jan 22, 2024 16:49 UTC (Mon)
by Wol (subscriber, #4433)
[Link] (4 responses)
Problem is, it's your *opinion*. Which you're welcome to.
But as someone who doesn't use git much, the index/staging to me is extremely confusing. And while I'm slowly trying to get into it, despite working with computers pretty much my entire career I've always avoided "software house" environments; with one exception spending it in "end user computer departments" or, as now, being the programming/computer guru in an end-user department.
I view things through end-user eyes. And as you'll know from my database rants, I simply cannot understand why main-stream computing is just so damn complicated! I quite get you don't see it that way, but probably that's all you've ever known. Just like end-user is pretty much all I've ever known...
Cheers,
Posted Jan 22, 2024 18:14 UTC (Mon)
by madscientist (subscriber, #16861)
[Link] (3 responses)
Also I'm not talking about Git. I'm talking about Magit. Whether you find the staging capability of Git confusing or not is irrelevant to my point, which is that Magit makes it clear why staging exists and what it's good for and how to use it, and makes it easy to use. And, Magit doesn't hide staging or pretend it's just a different way to talk about commits: it's a separate thing, which is integral to the workflow.
I don't really know what you mean by "software house environments"; Emacs is not exactly specialized or with limited availability.
Just to remind there's no such thing as a "programming/computer guru" who is not also an end-user. We are all end-users.
As for why it's complicated, well, some things are just complicated and the only way to simplify them is to remove functionality. Obviously it would be great to have a simple interface to support simple uses and save the complexity for more advanced users, and it would be great if the complex uses could also be made simpler, but to paraphrase Pascal "I am sorry for the complexity of the interface, I have not the time to make it simpler".
Posted Jan 22, 2024 22:00 UTC (Mon)
by Wol (subscriber, #4433)
[Link] (2 responses)
"Limited availabity" does not mean "in widespread use". I don't think I've ever known a regular user of Emacs apart from my brother.
> Just to remind there's no such thing as a "programming/computer guru" who is not also an end-user. We are all end-users.
You miss my point. All programming/computing gurus are end users, true. But not all (indeed, VERY FEW) end users are programming/computing gurus. In this environment (LWN) I may not be anything special, but *both* in my work and home environment I am a goliath amongst midgets.
In that sort of environment, where do I learn the things, that to you are second nature?
Cheers,
Posted Jan 22, 2024 23:47 UTC (Mon)
by anselm (subscriber, #2796)
[Link] (1 responses)
Yes, but perhaps Emacs would be in more widespread use if more people knew about Magit (and org-mode, and all the other goodies that make Emacs so unique and incredibly powerful).
Posted Jan 23, 2024 10:29 UTC (Tue)
by Wol (subscriber, #4433)
[Link]
I've already said I'm very much ALONE amongst my peer group of being a computer expert. MY peer group (which is far more representative of the general workforce than yours) wouldn't have a clue what a SCCS is if you hit them over the head with it! Even less a DVCS!
I don't have a problem with other peoples' opinions (we can all disagree quite friendlily?) UNTIL they assume their opinions apply to the majority. Guess what! We are a VERY SMALL minority!
Cheers,
Posted Jan 22, 2024 20:02 UTC (Mon)
by marcH (subscriber, #57642)
[Link]
BTW: https://lwn.net/Articles/949963/ (in "Evans: Confusing git terminology", Nov. 2023
> The staging area is unnecessary complexity. It's completely superfluous.
24 answers :-)
Posted Jan 21, 2024 5:39 UTC (Sun)
by roc (subscriber, #30627)
[Link]
Posted Jan 22, 2024 9:44 UTC (Mon)
by geert (subscriber, #98403)
[Link]
(a) Interactive rebase to the commit in question (called "sha1" below),
To split in more parts, have more b/c/d steps in between a and e.
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Wol
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Wol
Jujutsu: a new, Git-compatible version control system
"Limited availabity" does not mean "in widespread use".
Jujutsu: a new, Git-compatible version control system
Wol
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
Jujutsu: a new, Git-compatible version control system
(b) Revert the parts you don't want to be part of the first commit.
This can be as simple as "git show -- path/to/file/ | patch -p1 -R" if you just want to revert all changes to one file, or "git show > d", "vim d", "patch -p1 -R < d" for more complex cases.
(c) "git commit -a --amend", to edit the commit message for the first part,
(d) "git cherry-pick <sha1>" to pick up the remaining parts,
(e) "git commit --amend", to edit the commit message for the remaining parts.