feat(git): added support for --git-dir, --work-tree (yadm)

main
bhagwan 2 years ago
parent 1b200d3bdc
commit 604e4cf4c8

@ -432,11 +432,11 @@ end
M.git_switch = function(selected, opts)
local cmd = path.git_cwd({"git", "checkout"}, opts.cwd)
local cmd = path.git_cwd({"git", "checkout"}, opts)
local git_ver = utils.git_version()
-- git switch was added with git version 2.23
if git_ver and git_ver >= 2.23 then
cmd = path.git_cwd({"git", "switch"}, opts.cwd)
cmd = path.git_cwd({"git", "switch"}, opts)
end
-- remove anything past space
local branch = selected[1]:match("[^ ]+")
@ -456,8 +456,8 @@ M.git_switch = function(selected, opts)
end
M.git_checkout = function(selected, opts)
local cmd_checkout = path.git_cwd({"git", "checkout"}, opts.cwd)
local cmd_cur_commit = path.git_cwd({"git", "rev-parse", "--short HEAD"}, opts.cwd)
local cmd_checkout = path.git_cwd({"git", "checkout"}, opts)
local cmd_cur_commit = path.git_cwd({"git", "rev-parse", "--short HEAD"}, opts)
local commit_hash = selected[1]:match("[^ ]+")
if vim.fn.input("Checkout commit " .. commit_hash .. "? [y/n] ") == "y" then
local current_commit = utils.io_systemlist(cmd_cur_commit)
@ -488,18 +488,18 @@ local git_exec = function(selected, opts, cmd)
end
M.git_stage = function(selected, opts)
local cmd = path.git_cwd({"git", "add", "--"}, opts.cwd)
local cmd = path.git_cwd({"git", "add", "--"}, opts)
git_exec(selected, opts, cmd)
end
M.git_unstage = function(selected, opts)
local cmd = path.git_cwd({"git", "reset", "--"}, opts.cwd)
local cmd = path.git_cwd({"git", "reset", "--"}, opts)
git_exec(selected, opts, cmd)
end
M.git_buf_edit = function(selected, opts)
local cmd = path.git_cwd({"git", "show"}, opts.cwd)
local git_root = path.git_root(opts.cwd, true)
local cmd = path.git_cwd({"git", "show"}, opts)
local git_root = path.git_root(opts, true)
local win = vim.api.nvim_get_current_win()
local buffer_filetype = vim.bo.filetype
local file = path.relative(vim.fn.expand("%:p"), git_root)

@ -761,7 +761,7 @@ function M.normalize_opts(opts, defaults)
end
-- test for valid git_repo
opts.git_icons = opts.git_icons and path.is_git_repo(opts.cwd, true)
opts.git_icons = opts.git_icons and path.is_git_repo(opts, true)
local executable = function(binary, fncerr, strerr)
if binary and vim.fn.executable(binary) ~= 1 then

@ -339,6 +339,8 @@ M.mt_cmd_wrapper = function(opts)
"argv_expr",
"cmd",
"cwd",
"git_dir",
"git_worktree",
"git_icons",
"file_icons",
"color_icons",

@ -192,7 +192,7 @@ M.get_diff_files = function(opts)
local diff_files = {}
local cmd = opts.git_status_cmd or config.globals.files.git_status_cmd
if not cmd then return {} end
local ok, status, err = pcall(utils.io_systemlist, path.git_cwd(cmd, opts.cwd))
local ok, status, err = pcall(utils.io_systemlist, path.git_cwd(cmd, opts))
if ok and err == 0 then
for i = 1, #status do
local icon = status[i]:match("[MUDARC?]+")

@ -228,26 +228,47 @@ function M.entry_to_file(entry, cwd, force_uri)
}
end
function M.git_cwd(cmd, cwd)
if not cwd then return cmd end
cwd = vim.fn.expand(cwd)
function M.git_cwd(cmd, opts)
-- backward compat, used to be single cwd param
local o = opts or {}
if type(o) == 'string' then
o = { cwd = o }
end
local git_args = {
{ "cwd", "-C" },
{ "git_dir", "--git-dir" },
{ "git_worktree", "--work-tree" },
}
if type(cmd) == 'string' then
local arg_cwd = ("-C %s "):format(vim.fn.shellescape(cwd))
cmd = cmd:gsub("^git ", "git " .. arg_cwd)
local args = ""
for _, a in ipairs(git_args) do
if o[a[1]] then
o[a[1]] = vim.fn.expand(o[a[1]])
args = args .. ("%s %s "):format(a[2], vim.fn.shellescape(o[a[1]]))
end
end
cmd = cmd:gsub("^git ", "git " .. args)
else
local idx = 2
cmd = utils.tbl_deep_clone(cmd)
table.insert(cmd, 2, "-C")
table.insert(cmd, 3, cwd)
for _, a in ipairs(git_args) do
if o[a[1]] then
o[a[1]] = vim.fn.expand(o[a[1]])
table.insert(cmd, idx, a[2])
table.insert(cmd, idx+1, o[a[1]])
idx = idx + 2
end
end
end
return cmd
end
function M.is_git_repo(cwd, noerr)
return not not M.git_root(cwd, noerr)
function M.is_git_repo(opts, noerr)
return not not M.git_root(opts, noerr)
end
function M.git_root(cwd, noerr)
local cmd = M.git_cwd({"git", "rev-parse", "--show-toplevel"}, cwd)
function M.git_root(opts, noerr)
local cmd = M.git_cwd({"git", "rev-parse", "--show-toplevel"}, opts)
local output, err = utils.io_systemlist(cmd)
if err ~= 0 then
if not noerr then utils.info(unpack(output)) end

@ -239,9 +239,9 @@ Previewer.git_diff = Previewer.base:extend()
function Previewer.git_diff:new(o, opts)
Previewer.git_diff.super.new(self, o, opts)
self.cmd_deleted = path.git_cwd(o.cmd_deleted, opts.cwd)
self.cmd_modified = path.git_cwd(o.cmd_modified, opts.cwd)
self.cmd_untracked = path.git_cwd(o.cmd_untracked, opts.cwd)
self.cmd_deleted = path.git_cwd(o.cmd_deleted, opts)
self.cmd_modified = path.git_cwd(o.cmd_modified, opts)
self.cmd_untracked = path.git_cwd(o.cmd_untracked, opts)
self.pager = o.pager
do
-- populate the icon mappings

@ -8,10 +8,18 @@ local shell = require "fzf-lua.shell"
local M = {}
local function set_git_cwd_args(opts)
opts.cwd = path.git_root(opts)
if opts.git_dir or opts.git_worktree then
opts.cmd = path.git_cwd(opts.cmd, opts)
end
return opts
end
M.files = function(opts)
opts = config.normalize_opts(opts, config.globals.git.files)
if not opts then return end
opts.cwd = path.git_root(opts.cwd)
opts = set_git_cwd_args(opts)
if not opts.cwd then return end
local contents = core.mt_cmd_wrapper(opts)
opts = core.set_header(opts, 2)
@ -21,10 +29,10 @@ end
M.status = function(opts)
opts = config.normalize_opts(opts, config.globals.git.status)
if not opts then return end
opts.cwd = path.git_root(opts.cwd)
opts = set_git_cwd_args(opts)
if not opts.cwd then return end
if opts.preview then
opts.preview = vim.fn.shellescape(path.git_cwd(opts.preview, opts.cwd))
opts.preview = vim.fn.shellescape(path.git_cwd(opts.preview, opts))
end
-- we don't need git icons since we get them
-- as part of our `git status -s`
@ -76,7 +84,7 @@ M.status = function(opts)
end
local function git_cmd(opts)
opts.cwd = path.git_root(opts.cwd)
opts = set_git_cwd_args(opts)
if not opts.cwd then return end
opts = core.set_header(opts, 2)
core.fzf_wrap(opts, opts.cmd, function(selected)
@ -88,14 +96,14 @@ end
M.commits = function(opts)
opts = config.normalize_opts(opts, config.globals.git.commits)
if not opts then return end
opts.preview = vim.fn.shellescape(path.git_cwd(opts.preview, opts.cwd))
opts.preview = vim.fn.shellescape(path.git_cwd(opts.preview, opts))
return git_cmd(opts)
end
M.bcommits = function(opts)
opts = config.normalize_opts(opts, config.globals.git.bcommits)
if not opts then return end
local git_root = path.git_root(opts.cwd)
local git_root = path.git_root(opts)
if not git_root then return end
local file = path.relative(vim.fn.expand("%:p"), git_root)
opts.cmd = opts.cmd .. " " .. file
@ -104,7 +112,7 @@ M.bcommits = function(opts)
if git_ver and git_ver >= 2.31 then
opts.preview = opts.preview .. " --rotate-to=" .. vim.fn.shellescape(file)
end
opts.preview = vim.fn.shellescape(path.git_cwd(opts.preview, opts.cwd))
opts.preview = vim.fn.shellescape(path.git_cwd(opts.preview, opts))
return git_cmd(opts)
end
@ -112,7 +120,7 @@ M.branches = function(opts)
opts = config.normalize_opts(opts, config.globals.git.branches)
if not opts then return end
opts.fzf_opts["--no-multi"] = ''
opts._preview = path.git_cwd(opts.preview, opts.cwd)
opts._preview = path.git_cwd(opts.preview, opts)
opts.preview = shell.preview_action_cmd(function(items)
local branch = items[1]:gsub("%*", "") -- remove the * from current branch
if branch:find("%)") ~= nil then

Loading…
Cancel
Save