jujutsu file annotations for neovim (like blame)
Lua 100%

README.md

Display Jujutsu's jj file annotate (like git blame) in an interactive buffer. Works in any JJ repo, even in workspaces!

Dark Light
Dark Light

Installation #

Requires Nvim 0.12+.

vim.pack.add({
  "https://tangled.org/ronshavit.com/jjannotate.nvim",
})

Usage #

require("jjannotate").open()
require("jjannotate").toggle()

Options #

-- config is absolutely optional, no `.setup()` needed
vim.g.jjannotate_opts = {
  view = {
    -- whether to collapse repeating lines into a single line
    collapse_repeating_lines = true,
    -- whether to highlight all lines changed by cursor's change id
    highlight_changed_lines = true,
    -- how to highlight lines related to current change
    -- * "none": no highlighting
    -- * "bold": bold text
    highlight_current_change = "bold",
    -- color palette for annotate highlights
    -- "auto": pick dark/light palette based on vim.o.background (live-updates on ColorScheme/OptionSet)
    -- { auto = true, multiplier = { sat = 1.0, light = 1.0 } }: same as "auto", but with a color multiplier
    -- or pass a `jjannotate.Config.ResolvedPalette` to set colors directly
    palette = "auto",
  },
  -- disable any mapping by setting it to `false`
  mappings = {
    -- close the annotate window
    close = "q",
    -- show revision under the cursor in a new tab
    show = "<CR>",
    -- follow revision under the cursor and re-run annotate in a new tab
    follow = "f",
    -- jump to the previous/next change
    prev_change = "[[",
    next_change = "]]",
  },
}

Autocmds #

Customize the buffer with the FileType autocmd. For example, to enable listchars:

vim.api.nvim_create_autocmd("FileType", {
  pattern = "jjannotate",
  desc = "Enable listchars for jjannotate",
  callback = vim.schedule_wrap(function() vim.opt_local.list = true end),
})

There are also some user autocmds:

There are also some User autocmds. For those that are triggered for a specific window, :<win_id> is appended and can be matched on. If you don't want to match on a specific window, use :* instead.

  • JjAnnotateOpen:<win_id> is triggered when the annotate buffer is opened.
  • JjAnnotateUpdate:<win_id> is triggered when the annotate buffer is updated.

For autocmds that are triggered for a specific window, args.data.id is the Window's id. Given a win_id, you can retrieve its Window object:

vim.api.nvim_create_autocmd("User", {
  pattern = "JjAnnotateUpdate:*",
  callback = function(args)
    local w = require("jjannotate").get_by_id(args.data.id)
    if w then print("Annotate window " .. w.id .. " updated!") end
  end,
})

Inspirations #

I used blame.nvim before creating this plugin, but needed something specifically for JJ.