My Jujutsu workflow, tips & tricks
This is sort-of a followup post to my previous post.
I’ve been using Jujutsu exclusively for a month and a bit. While not perfect, I consider it a substantial improvement over git. I’m considering removing the git command from my $PATH all together.
Operating on a merge
I use a workflow that’s similar if not identical to ‘megamerges’. This involves working on a revision that merges in a whole bunch of different changes. Typically it looks something like this in the log:
@
├─┬─┬─╮
│ │ │ ○
| | | |
│ │ ○ │
| | | |
│ │ │ │ ○
├───────╯
○ │ │ │
| | | |
◆ │ │ │
├─╯ │ │
This could be work for 2 different pull requests, 1 pull request merged with master, changes that I don’t want to upstream (e.g. adding a flake.nix) mixed in with ones that I do, whatever.
Making Revisions
Generally you want to write changes into this merge revision then try and ‘empty’ it into other branches. I almost always use jj split -A <bookmark> for this. This will bring up an interactive screen and I can select what changes I want to put into a new revision on top of the destination.
If the merge revision is empty, you can switch which branches are being merged in by just running jj new X Y Z and it’ll create a new merge revision and delete the old one provided it didn’t have a description. But if you’re still working on whatever is in the merge revision, you’ll need to rebase in order to take those changes with you. jj rebase -s @ -d '@-~<rev to remove>' -d <rev to add> works well for this, where @ is the current revision, @- is its ancestors and ~ is an set exclusion operator.
Bookmarks
Updating bookmarks is fairly standard. Often I use jj bookmark move <bookmark> -t <bookmark>+ if I’m just moving things ahead by 1 revision and don’t care about its ID.
Unwanted changes
If you have a bunch of changes in a merge revision that you’re almost certain you don’t want (e.g. a bunch of debugging lines) then you might as well keep them around, but in a side revision that won’t be merged in. Use jj split -d <bookmark> for this.
Local-only changes
Additionally, if you want a bunch of changes you need in the working set but don’t want to push, simply use jj split -A <bookmark> as per normal but don’t update the bookmark. They any of these local-only changes will be rebased onto whatever new changes you add to the bookmark.
Other commands
- I occasionally squash revisions. Generally after I’ve already created them with with
jj split -Athough. - I don’t use
jj absorb. I really like the idea but it seems to squash revisions rather than create new ones.
Grips
- Flags are inconsistent.
jj rebaseuses-sand-d,jj squashuses-fand-t.jj bookmark setuses-r,jj bookmark moveuses-t. - There are too many redundant commands. Why even have
bookmark setandmove? Why not havejj splitbe an alias ofjj commit -ior something?