1

Refresh generated neovim config

This commit is contained in:
2024-07-14 21:12:36 +02:00
parent f215ce2ab5
commit 00464e0e65
731 changed files with 6780 additions and 31110 deletions

View File

@ -215,10 +215,10 @@ local function get_hunks(bufnr, bcache, greedy, staged)
end
if staged then
return bcache.hunks_staged
return vim.deepcopy(bcache.hunks_staged)
end
return bcache.hunks
return vim.deepcopy(bcache.hunks)
end
--- @param bufnr integer
@ -478,6 +478,7 @@ end)
--- @field greedy boolean
--- @field preview boolean
--- @field count integer
--- @field target 'unstaged'|'staged'|'all'
--- @param x string
--- @param word string
@ -513,6 +514,10 @@ local function process_nav_opts(opts)
opts.count = vim.v.count1
end
if opts.target == nil then
opts.target = 'unstaged'
end
return opts
end
@ -532,6 +537,30 @@ local function has_preview_inline(bufnr)
return #api.nvim_buf_get_extmarks(bufnr, ns_inline, 0, -1, { limit = 1 }) > 0
end
--- @param bufnr integer
--- @param target 'unstaged'|'staged'|'all'
--- @param greedy boolean
--- @return Gitsigns.Hunk.Hunk[]
local function get_nav_hunks(bufnr, target, greedy)
local bcache = assert(cache[bufnr])
local hunks_main = get_hunks(bufnr, bcache, greedy, false) or {}
local hunks --- @type Gitsigns.Hunk.Hunk[]
if target == 'unstaged' then
hunks = hunks_main
else
local hunks_head = get_hunks(bufnr, bcache, greedy, true) or {}
hunks_head = Hunks.filter_common(hunks_head, hunks_main) or {}
if target == 'all' then
hunks = hunks_main
vim.list_extend(hunks, hunks_head)
elseif target == 'staged' then
hunks = hunks_head
end
end
return hunks
end
--- @async
--- @param direction 'first'|'last'|'next'|'prev'
--- @param opts? Gitsigns.NavOpts
@ -543,9 +572,7 @@ local function nav_hunk(direction, opts)
return
end
local hunks = get_hunks(bufnr, bcache, opts.greedy, false) or {}
local hunks_head = get_hunks(bufnr, bcache, opts.greedy, true) or {}
vim.list_extend(hunks, Hunks.filter_common(hunks_head, hunks) or {})
local hunks = get_nav_hunks(bufnr, opts.target, opts.greedy)
if not hunks or vim.tbl_isempty(hunks) then
if opts.navigation_message then
@ -629,6 +656,8 @@ end
--- • {greedy}: (boolean)
--- Only navigate between non-contiguous hunks. Only useful if
--- 'diff_opts' contains `linematch`. Defaults to `true`.
--- • {target}: (`'unstaged'|'staged'|'all'`)
--- Which kinds of hunks to target. Defaults to `'unstaged'`.
--- • {count}: (integer)
--- Number of times to advance. Defaults to |v:count1|.
M.nav_hunk = async.create(2, function(direction, opts)
@ -1023,6 +1052,19 @@ C.blame_line = function(args, _)
M.blame_line(args)
end
--- Run git-blame on the current file and open the results
--- in a scroll-bound vertical split.
---
--- <CR> is mapped to open a menu with the actions:
--- - [Show commit] in a vertical split.
--- - [Reblame at commit]
---
--- Attributes: ~
--- {async}
M.blame = async.create(0, function()
return require('gitsigns.blame').blame()
end)
--- @param bcache Gitsigns.CacheEntry
--- @param base string?
local function update_buf_base(bcache, base)
@ -1191,14 +1233,14 @@ CP.diffthis = complete_heads
---
--- Attributes: ~
--- {async}
M.show = function(revision)
M.show = function(revision, callback)
local bufnr = api.nvim_get_current_buf()
if not cache[bufnr] then
print('Error: Buffer is not attached.')
return
end
local diffthis = require('gitsigns.diffthis')
diffthis.show(bufnr, revision)
diffthis.show(bufnr, revision, callback)
end
CP.show = complete_heads

View File

@ -138,15 +138,16 @@ end
--- @param _bufnr integer
--- @param file string
--- @param revision string?
--- @param encoding string
--- @return Gitsigns.GitObj?
local function try_worktrees(_bufnr, file, encoding)
local function try_worktrees(_bufnr, file, revision, encoding)
if not config.worktrees then
return
end
for _, wt in ipairs(config.worktrees) do
local git_obj = git.Obj.new(file, encoding, wt.gitdir, wt.toplevel)
local git_obj = git.Obj.new(file, revision, encoding, wt.gitdir, wt.toplevel)
if git_obj and git_obj.object_name then
dprintf('Using worktree %s', vim.inspect(wt))
return git_obj
@ -211,13 +212,12 @@ local function get_buf_context(bufnr)
file = file,
gitdir = gitdir,
toplevel = toplevel,
-- Commit buffers have there base set back one revision with '^'
-- Stage buffers always compare against the common ancestor (':1')
-- :0: index
-- :1: common ancestor
-- :2: target commit (HEAD)
-- :3: commit which is being merged
base = commit and (commit:match('^:[1-3]') and ':1' or commit .. '^') or nil,
base = commit and (commit:match('^:[1-3]') and ':1' or commit) or nil,
}
end
@ -273,7 +273,7 @@ local attach_throttled = throttle_by_id(function(cbuf, ctx, aucmd)
local git_obj = git.Obj.new(file, revision, encoding, ctx.gitdir, ctx.toplevel)
if not git_obj and not passed_ctx then
git_obj = try_worktrees(cbuf, file, encoding)
git_obj = try_worktrees(cbuf, file, revision, encoding)
async.scheduler()
if not api.nvim_buf_is_valid(cbuf) then
return

View File

@ -67,15 +67,15 @@ end
-- at a time.
local BLAME_THRESHOLD_LEN = 1000000
--- @private
--- @param lnum integer
--- @async
--- @param lnum? integer
--- @param opts Gitsigns.BlameOpts
--- @return table<integer,Gitsigns.BlameInfo?>?
function CacheEntry:run_blame(lnum, opts)
local bufnr = self.bufnr
local blame_cache --- @type table<integer,Gitsigns.BlameInfo?>?
repeat
local buftext = util.buf_lines(bufnr)
local buftext = util.buf_lines(bufnr, true)
local tick = vim.b[bufnr].changedtick
local lnum0 = #buftext > BLAME_THRESHOLD_LEN and lnum or nil
-- TODO(lewis6991): Cancel blame on changedtick
@ -97,7 +97,7 @@ local function get_blame_nc(file, lnum)
return {
orig_lnum = 0,
final_lnum = lnum,
commit = Git.not_commited(file),
commit = Git.not_committed(file),
filename = file,
}
end

View File

@ -1,21 +1,10 @@
--- @class (exact) Gitsigns.SchemaElem.Deprecated
---
--- Used for renaming fields.
--- @field new_field? string
---
--- Documentation for deprecation. Will be added to the help file and used in
--- the notification if `hard = true`.
--- @field message? string
---
--- Emit a message via vim.notify
--- @field hard? boolean
--- @class (exact) Gitsigns.SchemaElem
--- @field type string|string[]
--- @field type string|string[]|fun(x:any): boolean
--- @field type_help? string
--- @field refresh? fun(cb: fun()) Function to refresh the config value
--- @field deep_extend? boolean
--- @field default any
--- @field deprecated? boolean|Gitsigns.SchemaElem.Deprecated
--- @field deprecated? boolean
--- @field default_help? string
--- @field description string
@ -45,10 +34,7 @@
--- | 'changedelete'
--- | 'untracked'
--- @class (exact) Gitsigns.CurrentLineBlameFmtOpts
--- @field relative_time boolean
--- @alias Gitsigns.CurrentLineBlameFmtFun fun(user: string, info: table<string,any>, opts: Gitsigns.CurrentLineBlameFmtOpts): {[1]:string,[2]:string}[]
--- @alias Gitsigns.CurrentLineBlameFmtFun fun(user: string, info: table<string,any>): {[1]:string,[2]:string}[]
--- @class (exact) Gitsigns.CurrentLineBlameOpts : Gitsigns.BlameOpts
--- @field virt_text? boolean
@ -69,8 +55,8 @@
--- @field diff_opts Gitsigns.DiffOpts
--- @field base? string
--- @field signs table<Gitsigns.SignType,Gitsigns.SignConfig>
--- @field _signs_staged table<Gitsigns.SignType,Gitsigns.SignConfig>
--- @field _signs_staged_enable boolean
--- @field signs_staged table<Gitsigns.SignType,Gitsigns.SignConfig>
--- @field signs_staged_enable boolean
--- @field count_chars table<string|integer,string>
--- @field signcolumn boolean
--- @field numhl boolean
@ -84,14 +70,12 @@
--- @field update_debounce integer
--- @field status_formatter fun(_: table<string,any>): string
--- @field current_line_blame boolean
--- @field current_line_blame_formatter_opts { relative_time: boolean }
--- @field current_line_blame_formatter string|Gitsigns.CurrentLineBlameFmtFun
--- @field current_line_blame_formatter_nc string|Gitsigns.CurrentLineBlameFmtFun
--- @field current_line_blame_opts Gitsigns.CurrentLineBlameOpts
--- @field preview_config table<string,any>
--- @field auto_attach boolean
--- @field attach_to_untracked boolean
--- @field yadm { enable: boolean }
--- @field worktrees {toplevel: string, gitdir: string}[]
--- @field word_diff boolean
--- @field trouble boolean
@ -108,9 +92,7 @@ local M = {
DiffOpts = {},
SignConfig = {},
watch_gitdir = {},
current_line_blame_formatter_opts = {},
current_line_blame_opts = {},
yadm = {},
Worktree = {},
},
}
@ -182,10 +164,50 @@ M.config = setmetatable({}, {
end,
})
local function warn(s, ...)
vim.notify_once(s:format(...), vim.log.levels.WARN, { title = 'gitsigns' })
end
--- @param x Gitsigns.SignConfig
--- @return boolean
local function validate_signs(x)
if type(x) ~= 'table' then
return false
end
local warnings --- @type table<string,true>?
--- @diagnostic disable-next-line:no-unknown
for kind, s in pairs(M.schema.signs.default) do
--- @diagnostic disable-next-line:no-unknown
for ty, v in pairs(s) do
if x[kind] and x[kind][ty] and vim.endswith(ty, 'hl') then
warnings = warnings or {}
local w = string.format(
"'signs.%s.%s' is now deprecated, please define highlight '%s'",
kind,
ty,
v
)
warnings[w] = true
end
end
end
if warnings then
for w in vim.spairs(warnings) do
warn(w)
end
end
return true
end
--- @type table<string,Gitsigns.SchemaElem>
M.schema = {
signs = {
type = 'table',
type_help = 'table',
type = validate_signs,
deep_extend = true,
default = {
add = { hl = 'GitSignsAdd', text = '', numhl = 'GitSignsAddNr', linehl = 'GitSignsAddLn' },
@ -244,7 +266,7 @@ M.schema = {
]],
},
_signs_staged = {
signs_staged = {
type = 'table',
deep_extend = true,
default = {
@ -293,9 +315,9 @@ M.schema = {
]],
},
_signs_staged_enable = {
signs_staged_enable = {
type = 'boolean',
default = false,
default = true,
description = [[
Show signs for staged hunks.
@ -649,24 +671,9 @@ M.schema = {
]],
},
current_line_blame_formatter_opts = {
type = 'table',
deep_extend = true,
deprecated = true,
default = {
relative_time = false,
},
description = [[
Options for the current line blame annotation formatter.
Fields: ~
• relative_time: boolean
]],
},
current_line_blame_formatter = {
type = { 'string', 'function' },
default = ' <author>, <author_time> - <summary> ',
default = ' <author>, <author_time:%R> - <summary> ',
description = [[
String or function used to format the virtual text of
|gitsigns-config-current_line_blame|.
@ -735,9 +742,6 @@ M.schema = {
Note that the keys map onto the output of:
`git blame --line-porcelain`
{opts} Passed directly from
|gitsigns-config-current_line_blame_formatter_opts|.
Return: ~
The result of this function is passed directly to the `opts.virt_text`
field of |nvim_buf_set_extmark| and thus must be a list of
@ -769,17 +773,6 @@ M.schema = {
]],
},
yadm = {
type = 'table',
deprecated = {
message = 'Please use |gitsigns-config-on_attach_pre| instead',
},
default = { enable = false },
description = [[
yadm configuration.
]],
},
_git_version = {
type = 'string',
default = 'auto',
@ -861,22 +854,18 @@ M.schema = {
},
}
local function warn(s, ...)
vim.notify(s:format(...), vim.log.levels.WARN, { title = 'gitsigns' })
end
--- @param config Gitsigns.Config
local function validate_config(config)
--- @diagnostic disable-next-line:no-unknown
for k, v in pairs(config) do
for k, v in
pairs(config --[[@as table<string,any>]])
do
local kschema = M.schema[k]
if kschema == nil then
warn("gitsigns: Ignoring invalid configuration field '%s'", k)
elseif kschema.type then
if type(kschema.type) == 'string' then
vim.validate({
[k] = { v, kschema.type },
})
else
local ty = kschema.type
if type(ty) == 'string' or type(ty) == 'function' then
vim.validate({ [k] = { v, ty } })
end
end
end
@ -888,28 +877,15 @@ local function handle_deprecated(cfg)
local dep = v.deprecated
if dep and cfg[k] ~= nil then
if type(dep) == 'table' then
if dep.new_field then
local opts_key, field = dep.new_field:match('(.*)%.(.*)')
if opts_key and field then
-- Field moved to an options table
local opts = (cfg[opts_key] or {}) --[[@as table<any,any>]]
opts[field] = cfg[k]
cfg[opts_key] = opts
else
-- Field renamed
cfg[dep.new_field] = cfg[k]
end
end
if dep.hard then
if dep.message then
warn(dep.message)
elseif dep.new_field then
warn('%s is now deprecated, please use %s', k, dep.new_field)
else
warn('%s is now deprecated; ignoring', k)
end
end
else
warn('%s is now deprecated; ignoring', k)
end
end
end

View File

@ -28,7 +28,7 @@ local function expand_blame_format(fmt, name, info)
if info.author == name then
info.author = 'You'
end
return util.expand_format(fmt, info, config.current_line_blame_formatter_opts.relative_time)
return util.expand_format(fmt, info)
end
--- @param virt_text {[1]: string, [2]: string}[]
@ -41,7 +41,6 @@ local function flatten_virt_text(virt_text)
return table.concat(res)
end
--- @param winid integer
--- @return integer
local function win_width()
local winid = api.nvim_get_current_win()
@ -61,7 +60,7 @@ end
--- @param fmt string
--- @return Gitsigns.CurrentLineBlameFmtFun
local function default_formatter(fmt)
return function(username, blame_info, _opts)
return function(username, blame_info)
return {
{
expand_blame_format(fmt, username, blame_info),
@ -85,7 +84,7 @@ local function get_blame_virt_text(bufnr, blame_info)
clb_formatter = default_formatter(clb_formatter)
end
return clb_formatter(git_obj.repo.username, blame_info, config.current_line_blame_formatter_opts)
return clb_formatter(git_obj.repo.username, blame_info)
end
--- @param bufnr integer

View File

@ -43,20 +43,7 @@ function M.dump_cache()
vim.api.nvim_echo({ { text } }, false, {})
end
--- @param noecho boolean
--- @return string[]?
function M.debug_messages(noecho)
if noecho then
return log.messages
else
for _, m in ipairs(log.messages) do
vim.api.nvim_echo({ { m } }, false, {})
end
end
end
function M.clear_debug()
log.messages = {}
end
M.debug_messages = log.show
M.clear_debug = log.clear
return M

View File

@ -1,7 +1,9 @@
local start_time = vim.loop.hrtime()
local M = {
debug_mode = false,
verbose = false,
messages = {}, --- @type string[]
messages = {} --- @type [number, string, string, string][]
}
--- @param name string
@ -44,7 +46,6 @@ local function getvarvalue(name, lvl)
end
-- not found; get global
--- @diagnostic disable-next-line:deprecated
return getfenv(func)[name]
end
@ -52,71 +53,72 @@ end
--- @return {name:string, bufnr: integer}
local function get_context(lvl)
lvl = lvl + 1
local ret = {} --- @type {name:string, bufnr: integer}
ret.name = getvarvalue('__FUNC__', lvl)
if not ret.name then
local name = getvarvalue('__FUNC__', lvl)
if not name then
local name0 = debug.getinfo(lvl, 'n').name or ''
ret.name = name0:gsub('(.*)%d+$', '%1')
name = name0:gsub('(.*)%d+$', '%1')
end
ret.bufnr = getvarvalue('bufnr', lvl)
local bufnr = getvarvalue('bufnr', lvl)
or getvarvalue('_bufnr', lvl)
or getvarvalue('cbuf', lvl)
or getvarvalue('buf', lvl)
return ret
return {name=name, bufnr=bufnr}
end
-- If called in a callback then make sure the callback defines a __FUNC__
-- variable which can be used to identify the name of the function.
--- @param kind string
--- @param obj any
--- @param lvl integer
local function cprint(obj, lvl)
local function cprint(kind, obj, lvl)
lvl = lvl + 1
--- @type string
local msg = type(obj) == 'string' and obj or vim.inspect(obj)
local ctx = get_context(lvl)
local msg2 --- @type string
local time = (vim.loop.hrtime() - start_time) / 1e6
local ctx1 = ctx.name
if ctx.bufnr then
msg2 = string.format('%s(%s): %s', ctx.name, ctx.bufnr, msg)
else
msg2 = string.format('%s: %s', ctx.name, msg)
ctx1 = string.format('%s(%s)', ctx1, ctx.bufnr)
end
table.insert(M.messages, msg2)
table.insert(M.messages, {time, kind, ctx1, msg})
end
function M.dprint(obj)
if not M.debug_mode then
return
end
cprint(obj, 2)
cprint('debug', obj, 2)
end
function M.dprintf(obj, ...)
if not M.debug_mode then
return
end
cprint(obj:format(...), 2)
cprint('debug', obj:format(...), 2)
end
function M.vprint(obj)
if not (M.debug_mode and M.verbose) then
return
end
cprint(obj, 2)
cprint('info', obj, 2)
end
function M.vprintf(obj, ...)
if not (M.debug_mode and M.verbose) then
return
end
cprint(obj:format(...), 2)
cprint('info', obj:format(...), 2)
end
local function eprint(msg, level)
local info = debug.getinfo(level + 2, 'Sl')
if info then
msg = string.format('(ERROR) %s(%d): %s', info.short_src, info.currentline, msg)
end
M.messages[#M.messages + 1] = debug.traceback(msg)
local ctx = info and string.format('%s<%d>', info.short_src, info.currentline) or '???'
local time = (vim.loop.hrtime() - start_time) / 1e6
table.insert(M.messages, { time, 'error', ctx, debug.traceback(msg) })
if M.debug_mode then
error(msg, 3)
end
@ -141,4 +143,49 @@ function M.assert(cond, msg)
return not cond
end
local sev_to_hl = {
debug = 'Title',
info = 'MoreMsg',
warn = 'WarningMsg',
error = 'ErrorMsg',
}
function M.clear()
M.messages = {}
end
--- @param m [number, string, string, string]
--- @return [string,string][]
local function build_msg(m)
local time, kind, ctx, msg = m[1], m[2], m[3], m[4]
local hl = sev_to_hl[kind]
return {
{ string.format('%.2f ', time), 'Comment' },
{ kind:upper():sub(1,1), hl },
{ string.format(' %s:', ctx), 'Tag'},
{ ' ' },
{ msg }
}
end
function M.show()
for _, m in ipairs(M.messages) do
vim.api.nvim_echo(build_msg(m), false, {})
end
end
--- @return string[]?
function M.get()
local r = {} --- @type string[]
for _, m in ipairs(M.messages) do
local e = build_msg(m)
local e1 = {} --- @type string[]
for _, x in ipairs(e) do
e1[#e1+1] = x[1]
end
r[#r+1] = table.concat(e1)
end
return r
end
return M

View File

@ -7,6 +7,7 @@ local manager = require('gitsigns.manager')
local message = require('gitsigns.message')
local Status = require('gitsigns.status')
local dprint = require('gitsigns.debug.log').dprint
local throttle_by_id = require('gitsigns.debounce').throttle_by_id
local M = {}
@ -176,11 +177,14 @@ end)
--- @param bufnr integer
--- @param base string
M.show = async.create(2, function(bufnr, base)
__FUNC__ = 'show'
local bufname = create_show_buf(bufnr, base)
if not bufname then
dprint('No bufname for revision ' .. base)
return
end
dprint('bufname ' .. bufname)
vim.cmd.edit(bufname)
end)

View File

@ -327,35 +327,6 @@ function Repo:update_abbrev_head()
self.abbrev_head = M.get_repo_info(self.toplevel).abbrev_head
end
--- @private
--- @param dir string
--- @param gitdir? string
--- @param toplevel? string
function Repo:try_yadm(dir, gitdir, toplevel)
if not config.yadm.enable or self.gitdir then
return
end
local home = os.getenv('HOME')
if not home or not vim.startswith(dir, home) then
return
end
if #git_command({ 'ls-files', dir }, { command = 'yadm' }) == 0 then
return
end
M.get_repo_info(dir, 'yadm', gitdir, toplevel)
local yadm_info = M.get_repo_info(dir, 'yadm', gitdir, toplevel)
for k, v in
pairs(yadm_info --[[@as table<string,any>]])
do
---@diagnostic disable-next-line:no-unknown
self[k] = v
end
end
--- @async
--- @param dir string
--- @param gitdir? string
@ -373,8 +344,6 @@ function Repo.new(dir, gitdir, toplevel)
self[k] = v
end
self:try_yadm(dir, gitdir, toplevel)
return self
end
@ -424,11 +393,15 @@ end
--- @field object_name? string
--- @field has_conflicts? true
function Obj:from_tree()
return self.revision and not vim.startswith(self.revision, ':')
end
--- @param file? string
--- @param silent? boolean
--- @return Gitsigns.FileInfo
function Obj:file_info(file, silent)
if self.revision and not vim.startswith(self.revision, ':') then
if self:from_tree() then
return self:file_info_tree(file, silent)
else
return self:file_info_index(file, silent)
@ -436,12 +409,16 @@ function Obj:file_info(file, silent)
end
--- @private
--- Get information about files in the index and the working tree
--- @param file? string
--- @param silent? boolean
--- @return Gitsigns.FileInfo
function Obj:file_info_index(file, silent)
local has_eol = check_version({ 2, 9 })
-- --others + --exclude-standard means ignored files won't return info, but
-- untracked files will. Unlike file_info_tree which won't return untracked
-- files.
local cmd = {
'-c',
'core.quotepath=off',
@ -499,6 +476,7 @@ function Obj:file_info_index(file, silent)
end
--- @private
--- Get information about files in a certain revision
--- @param file? string
--- @param silent? boolean
--- @return Gitsigns.FileInfo
@ -615,7 +593,7 @@ local NOT_COMMITTED = {
--- @param file string
--- @return Gitsigns.CommitInfo
function M.not_commited(file)
function M.not_committed(file)
local time = os.time()
return {
sha = string.rep('0', 40),
@ -649,7 +627,7 @@ function Obj:run_blame(lines, lnum, opts)
-- As we support attaching to untracked files we need to return something if
-- the file isn't isn't tracked in git.
-- If abbrev_head is empty, then assume the repo has no commits
local commit = M.not_commited(self.file)
local commit = M.not_committed(self.file)
for i in ipairs(lines) do
ret[i] = {
orig_lnum = 0,

View File

@ -283,7 +283,8 @@ local function cmul(x, factor)
end
local function dprintf(fmt, ...)
require('gitsigns.debug.log').dprintf(fmt, ...)
dprintf = require('gitsigns.debug.log').dprintf
dprintf(fmt, ...)
end
--- @param hl string

View File

@ -432,7 +432,6 @@ function M.filter_common(a, b)
end
a, b = a or {}, b or {}
local max_iter = math.max(#a, #b)
local a_i = 1
local b_i = 1
@ -440,7 +439,9 @@ function M.filter_common(a, b)
--- @type Gitsigns.Hunk.Hunk[]
local ret = {}
for _ = 1, max_iter do
-- Need an offset of 1 in order to process when we hit the end of either
-- a or b
for _ = 1, math.max(#a, #b) + 1 do
local a_h, b_h = a[a_i], b[b_i]
if not a_h then

View File

@ -488,9 +488,10 @@ M.update = throttle_by_id(function(bufnr)
return
end
if config._signs_staged_enable and not file_mode and not git_obj.revision then
if config.signs_staged_enable and not file_mode then
if not bcache.compare_text_head or config._refresh_staged_on_update then
bcache.compare_text_head = git_obj:get_show_text('HEAD')
local staged_rev = git_obj:from_tree() and git_obj.revision .. '^' or 'HEAD'
bcache.compare_text_head = git_obj:get_show_text(staged_rev)
if not M.schedule(bufnr, true) then
return
end
@ -581,8 +582,8 @@ function M.setup()
})
signs_normal = Signs.new(config.signs)
if config._signs_staged_enable then
signs_staged = Signs.new(config._signs_staged, 'staged')
if config.signs_staged_enable then
signs_staged = Signs.new(config.signs_staged, 'staged')
end
M.update_debounced = debounce_trailing(config.update_debounce, async.create(1, M.update))

View File

@ -126,7 +126,7 @@ function M.new(cfg, name)
local self = setmetatable({}, { __index = M })
self.config = cfg
self.hls = name == 'staged' and config._signs_staged or config.signs
self.hls = name == 'staged' and config.signs_staged or config.signs
self.group = 'gitsigns_signs_' .. (name or '')
self.ns = api.nvim_create_namespace(self.group)
return self

View File

@ -71,8 +71,9 @@ local function add_bom(x, encoding)
end
--- @param bufnr integer
--- @param noendofline? boolean
--- @return string[]
function M.buf_lines(bufnr)
function M.buf_lines(bufnr, noendofline)
-- nvim_buf_get_lines strips carriage returns if fileformat==dos
local buftext = vim.api.nvim_buf_get_lines(bufnr, 0, -1, false)
@ -84,7 +85,7 @@ function M.buf_lines(bufnr)
end
end
if vim.bo[bufnr].endofline then
if not noendofline and vim.bo[bufnr].endofline then
-- Add CR to the last line
if dos then
buftext[#buftext] = buftext[#buftext] .. '\r'
@ -116,6 +117,15 @@ function M.buf_rename(bufnr, name)
delete_alt(bufnr)
end
--- @param events string[]
--- @param f fun()
function M.noautocmd(events, f)
local ei = vim.o.eventignore
vim.o.eventignore = table.concat(events, ',')
f()
vim.o.eventignore = ei
end
--- @param bufnr integer
--- @param start_row integer
--- @param end_row integer
@ -254,9 +264,8 @@ end
---@param fmt string
---@param info table<string,any>
---@param reltime? boolean Use relative time as the default date format
---@return string
function M.expand_format(fmt, info, reltime)
function M.expand_format(fmt, info)
local ret = {} --- @type string[]
for _ = 1, 20 do -- loop protection
@ -277,7 +286,7 @@ function M.expand_format(fmt, info, reltime)
end
if vim.endswith(key, '_time') then
if time_fmt == '' then
time_fmt = reltime and '%R' or '%Y-%m-%d'
time_fmt = '%Y-%m-%d'
end
v = expand_date(time_fmt, v)
end

View File

@ -8,6 +8,7 @@ local util = require('gitsigns.util')
local cache = require('gitsigns.cache').cache
local config = require('gitsigns.config').config
local throttle_by_id = require('gitsigns.debounce').throttle_by_id
local debounce_trailing = require('gitsigns.debounce').debounce_trailing
local manager = require('gitsigns.manager')
@ -52,15 +53,21 @@ local function handle_moved(bufnr, old_relpath)
local old_name = api.nvim_buf_get_name(bufnr)
if not bufexists then
util.buf_rename(bufnr, bcache.file)
-- Do not trigger BufFilePre/Post
-- TODO(lewis6991): figure out how to avoid reattaching without
-- disabling all autocommands.
util.noautocmd({ 'BufFilePre', 'BufFilePost' }, function()
util.buf_rename(bufnr, bcache.file)
end)
end
local msg = bufexists and 'Cannot rename' or 'Renamed'
dprintf('%s buffer %d from %s to %s', msg, bufnr, old_name, bcache.file)
end
--- @async
--- @param bufnr integer
local watcher_handler = async.create(1, function(bufnr)
local function watcher_handler0(bufnr)
local __FUNC__ = 'watcher_handler'
-- Avoid cache hit for detached buffer
@ -99,9 +106,13 @@ local watcher_handler = async.create(1, function(bufnr)
cache[bufnr]:invalidate(true)
require('gitsigns.manager').update(bufnr)
end)
end
local watcher_handler_debounced = debounce_trailing(200, watcher_handler, 1)
--- Debounce and throttle the handler.
--- We also throttle in case the debounce delay is not enough and to prevent
--- too many handlers from being launched (and interleaved).
local watcher_handler =
debounce_trailing(200, async.create(1, throttle_by_id(watcher_handler0, true)), 1)
--- vim.inspect but on one line
--- @param x any
@ -142,7 +153,7 @@ function M.watch_gitdir(bufnr, gitdir)
dprint(info)
watcher_handler_debounced(bufnr)
watcher_handler(bufnr)
end)
return w
end