-- :TabWidth <N> set the tab width for the current buffer
vim.api.nvim_create_user_command('TabWidth', function(opts)
  -- Set the tab width for the current filetype
  -- FIXME: Doesn't seem to cover all bases in neovim when editorconfig is
  -- involved, specifically with pressing o/O in C++ from a line with a brace.
  -- This might be related to tree-sitter indentation? Or could be that I've
  -- not ported over all my filetype settings yet.
  local width = tonumber(opts.args)
  vim.opt.tabstop = width
  vim.opt.shiftwidth = width
  vim.opt.softtabstop = width
end, { nargs = 1 })

-- :Remove the file associated with the current buffer, then delete the buffer
vim.api.nvim_create_user_command('Remove', function(opts)
  local path = vim.fn.expand('%:p')
  -- Using opts.bang in the callback can cause a SEGFAULT, instead use it
  -- before invoking the async unlink to select which callback should be called
  -- on completion.
  local callback = nil
  if opts.bang then
    -- Invoked as :Remove! so also delete the buffer.
    callback = function(err, success)
      if success then
        vim.schedule(function()
          vim.api.nvim_buf_delete(vim.api.nvim_get_current_buf(), {})
        end)
      else
        error(err)
      end
    end
  else
    -- Invoked as :Remove so don't delete the buffer.
    callback = function(err, success)
      if not success then
        error(err)
      end
    end
  end
  -- Actually remove the file using the selecte callback.
  vim.loop.fs_unlink(path, callback)
end, { bang = true })

-- TODO: :Move

-- :Rename the file associated with current buffer
vim.api.nvim_create_user_command('Rename', function(opts)
  local from = vim.fn.expand('%')
  local buffer = vim.api.nvim_get_current_buf()
  local to = nil
  local dir = vim.fn.expand('%:h')
  if dir == '.' then
    to = opts.args
  else
    to = dir .. '/' .. opts.args
  end
  vim.loop.fs_rename(from, to, function(err, success)
    if not success then
      error(err)
    else
      vim.schedule(function()
        vim.cmd('edit ' .. to)
        vim.api.nvim_buf_delete(buffer, {})
      end)
    end
  end)
end, {
  nargs = 1,
  complete = function()
    return { vim.fn.expand('%:t') }
  end
})

-- TODO: :Chmod

-- TODO: :Mkdir