256 lines
7.7 KiB
Lua
256 lines
7.7 KiB
Lua
if vim.g.loaded_git then
|
|
return
|
|
end
|
|
vim.g.loaded_git = 1
|
|
|
|
local DEFAULT_HIGHLIGHTS = {
|
|
GitIgnored = "Comment",
|
|
GitSha = "Identifier",
|
|
GitStaged = "Constant",
|
|
GitUnmerged = "Todo",
|
|
GitUnpulled = "Removed",
|
|
GitUnpushed = "Added",
|
|
GitUnstaged = "Changed",
|
|
GitUntracked = "Added",
|
|
|
|
GitStagedAdded = "GitStaged",
|
|
GitStagedCopied = "GitStaged",
|
|
GitStagedDeleted = "GitStaged",
|
|
GitStagedModified = "GitStaged",
|
|
GitStagedRenamed = "GitStaged",
|
|
GitStagedTypeChanged = "GitStaged",
|
|
|
|
GitUnstagedAdded = "GitUnstaged",
|
|
GitUnstagedCopied = "GitUnstaged",
|
|
GitUnstagedDeleted = "Removed",
|
|
GitUnstagedModified = "GitUnstaged",
|
|
GitUnstagedRenamed = "GitStaged",
|
|
GitUnstagedTypeChanged = "GitUnstaged",
|
|
|
|
GitUnmergedAddedByThem = "GitUnmerged",
|
|
GitUnmergedAddedByUs = "GitUnmerged",
|
|
GitUnmergedBothAdded = "GitUnmerged",
|
|
GitUnmergedBothDeleted = "GitUnmerged",
|
|
GitUnmergedBothModified = "GitUnmerged",
|
|
GitUnmergedDeletedByThem = "GitUnmerged",
|
|
GitUnmergedDeletedByUs = "GitUnmerged",
|
|
}
|
|
for name, link in pairs(DEFAULT_HIGHLIGHTS) do
|
|
vim.api.nvim_set_hl(0, name, { link = link, default = true })
|
|
end
|
|
|
|
local group = vim.api.nvim_create_augroup("ow.git", { clear = true })
|
|
|
|
vim.api.nvim_create_autocmd({ "BufReadPost", "BufNewFile" }, {
|
|
group = group,
|
|
callback = function(args)
|
|
require("git.core.repo").track(args.buf)
|
|
end,
|
|
})
|
|
vim.api.nvim_create_autocmd({ "BufWritePost", "FileChangedShellPost" }, {
|
|
group = group,
|
|
callback = function(args)
|
|
require("git.core.repo").refresh(args.buf)
|
|
end,
|
|
})
|
|
vim.api.nvim_create_autocmd({ "BufDelete", "BufWipeout" }, {
|
|
group = group,
|
|
callback = function(args)
|
|
require("git.core.repo").unbind(args.buf)
|
|
end,
|
|
})
|
|
vim.api.nvim_create_autocmd("FocusGained", {
|
|
group = group,
|
|
callback = function()
|
|
require("git.core.repo").refresh_all()
|
|
end,
|
|
})
|
|
vim.api.nvim_create_autocmd("VimLeavePre", {
|
|
group = group,
|
|
callback = function()
|
|
require("git.core.repo").stop_all()
|
|
end,
|
|
})
|
|
vim.api.nvim_create_autocmd({ "VimEnter", "DirChanged", "TabEnter" }, {
|
|
group = group,
|
|
callback = function()
|
|
require("git.core.repo").update_cwd_repo()
|
|
end,
|
|
})
|
|
vim.api.nvim_create_autocmd("TabClosed", {
|
|
group = group,
|
|
callback = function(args)
|
|
local tab = tonumber(args.file) --[[@as integer?]]
|
|
if tab then
|
|
require("git.core.repo").release_tab(tab)
|
|
end
|
|
end,
|
|
})
|
|
|
|
vim.api.nvim_create_autocmd("BufReadCmd", {
|
|
pattern = "git://*",
|
|
group = group,
|
|
callback = function(args)
|
|
require("git.object").read_uri(args.buf)
|
|
end,
|
|
})
|
|
vim.api.nvim_create_autocmd("BufReadCmd", {
|
|
pattern = "gitlog://*",
|
|
group = group,
|
|
callback = function(args)
|
|
require("git.log_view").read_uri(args.buf)
|
|
end,
|
|
})
|
|
vim.api.nvim_create_autocmd("BufReadCmd", {
|
|
pattern = "gitstatus://*",
|
|
group = group,
|
|
callback = function(args)
|
|
require("git.status_view").read_uri(args.buf)
|
|
end,
|
|
})
|
|
|
|
vim.api.nvim_create_user_command("G", function(opts)
|
|
local cmd = require("git.cmd")
|
|
cmd.run(cmd.parse_args(opts.args), { bang = opts.bang })
|
|
end, {
|
|
nargs = "*",
|
|
bang = true,
|
|
complete = function(...)
|
|
return require("git.cmd").complete(...)
|
|
end,
|
|
})
|
|
|
|
vim.api.nvim_create_user_command("Grefresh", function()
|
|
require("git.core.repo").refresh_all()
|
|
end, { desc = "Refresh git status for all repos" })
|
|
|
|
vim.api.nvim_create_user_command("Glog", function(opts)
|
|
require("git.log_view").run_glog(opts)
|
|
end, {
|
|
nargs = "*",
|
|
complete = function(...)
|
|
return require("git.log_view").complete_glog(...)
|
|
end,
|
|
desc = "Show git log",
|
|
})
|
|
|
|
local function complete_rev(...)
|
|
return require("git.cmd").complete_rev(...)
|
|
end
|
|
|
|
local DIFF_DIRECTIONS = { "vertical", "horizontal" }
|
|
|
|
local function default_vertical()
|
|
return vim.tbl_contains(vim.opt.diffopt:get(), "vertical")
|
|
end
|
|
|
|
vim.api.nvim_create_user_command("Gdiffsplit", function(opts)
|
|
local fargs = opts.fargs
|
|
local vertical = default_vertical()
|
|
local rev_idx = 1
|
|
if fargs[1] == "vertical" then
|
|
vertical = true
|
|
rev_idx = 2
|
|
elseif fargs[1] == "horizontal" then
|
|
vertical = false
|
|
rev_idx = 2
|
|
end
|
|
require("git.diff").split({ rev = fargs[rev_idx], vertical = vertical })
|
|
end, {
|
|
nargs = "*",
|
|
complete = function(arg_lead, cmd_line, _)
|
|
local rest = cmd_line:gsub("^%s*%S+%s*", "", 1)
|
|
local trailing_space = rest == "" or rest:sub(-1):match("%s") ~= nil
|
|
local tokens = vim.split(vim.trim(rest), "%s+", { trimempty = true })
|
|
local prior = trailing_space and tokens
|
|
or vim.list_slice(tokens, 1, #tokens - 1)
|
|
local results = {}
|
|
if #prior == 0 then
|
|
for _, d in ipairs(DIFF_DIRECTIONS) do
|
|
if vim.startswith(d, arg_lead) then
|
|
table.insert(results, d)
|
|
end
|
|
end
|
|
end
|
|
local first_is_direction = prior[1] == "vertical"
|
|
or prior[1] == "horizontal"
|
|
if #prior == 0 or (#prior == 1 and first_is_direction) then
|
|
vim.list_extend(results, complete_rev(arg_lead))
|
|
end
|
|
return results
|
|
end,
|
|
desc = "Open a diff split",
|
|
})
|
|
vim.api.nvim_create_user_command("Gedit", function(opts)
|
|
vim.cmd.edit({
|
|
args = { require("git.object").URI_PREFIX .. opts.args },
|
|
magic = { file = false },
|
|
})
|
|
end, {
|
|
nargs = 1,
|
|
complete = complete_rev,
|
|
desc = "Edit a git object (<rev>)",
|
|
})
|
|
|
|
vim.api.nvim_create_user_command("Gstatus", function(opts)
|
|
require("git.status_view").open({
|
|
placement = opts.fargs[1] --[[@as ow.Git.StatusView.Placement]]
|
|
or "split",
|
|
})
|
|
end, {
|
|
nargs = "?",
|
|
complete = function()
|
|
return require("git.status_view").PLACEMENTS
|
|
end,
|
|
desc = "Open git status view",
|
|
})
|
|
|
|
vim.keymap.set("n", "<Plug>(git-edit)", function()
|
|
local rev = vim.fn.input("Edit git object: ")
|
|
if rev == "" then
|
|
return
|
|
end
|
|
vim.cmd.edit({
|
|
args = { require("git.object").URI_PREFIX .. rev },
|
|
magic = { file = false },
|
|
})
|
|
end, { silent = true, desc = "Edit a git object" })
|
|
|
|
vim.keymap.set("n", "<Plug>(git-diff-vertical)", function()
|
|
require("git.diff").split({ vertical = true })
|
|
end, { silent = true, desc = "Diff against index (vertical)" })
|
|
vim.keymap.set("n", "<Plug>(git-diff-horizontal)", function()
|
|
require("git.diff").split({ vertical = false })
|
|
end, { silent = true, desc = "Diff against index (horizontal)" })
|
|
vim.keymap.set("n", "<Plug>(git-diff-vertical-head)", function()
|
|
require("git.diff").split({ rev = "HEAD", vertical = true })
|
|
end, { silent = true, desc = "Diff against HEAD (vertical)" })
|
|
vim.keymap.set("n", "<Plug>(git-diff-horizontal-head)", function()
|
|
require("git.diff").split({ rev = "HEAD", vertical = false })
|
|
end, { silent = true, desc = "Diff against HEAD (horizontal)" })
|
|
|
|
vim.keymap.set("n", "<Plug>(git-status-toggle)", function()
|
|
require("git.status_view").toggle()
|
|
end, { silent = true, desc = "Toggle git status sidebar" })
|
|
|
|
vim.keymap.set("n", "<Plug>(git-log)", function()
|
|
require("git.log_view").open({ max_count = 1000 })
|
|
end, { silent = true, desc = "Open git log" })
|
|
|
|
vim.keymap.set("n", "<Plug>(git-commit)", function()
|
|
require("git.commit").commit()
|
|
end, { silent = true, desc = "Start a git commit" })
|
|
vim.keymap.set("n", "<Plug>(git-commit-amend)", function()
|
|
require("git.commit").commit({ args = { "--amend" } })
|
|
end, { silent = true, desc = "Amend the last git commit" })
|
|
|
|
if vim.g.git_statusline ~= false then
|
|
vim.api.nvim_create_autocmd("BufWinEnter", {
|
|
group = group,
|
|
once = true,
|
|
callback = function()
|
|
require("git.statusline")
|
|
end,
|
|
})
|
|
end
|