summaryrefslogtreecommitdiff
path: root/lua/telescope/_compat.lua
blob: 62530746446c3c467f6b301bf1c626b82b2416ae (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
vim.deepcopy = (function()
  local function _id(v)
    return v
  end

  local deepcopy_funcs = {
    table = function(orig)
      local copy = {}

      if vim._empty_dict_mt ~= nil and getmetatable(orig) == vim._empty_dict_mt then
        copy = vim.empty_dict()
      end

      for k, v in pairs(orig) do
        copy[vim.deepcopy(k)] = vim.deepcopy(v)
      end

      if getmetatable(orig) then
        setmetatable(copy, getmetatable(orig))
      end

      return copy
    end,
    ['function'] = _id or function(orig)
      local ok, dumped = pcall(string.dump, orig)
      if not ok then
        error(debug.traceback(dumped))
      end

      local cloned = loadstring(dumped)
      local i = 1
      while true do
        local name = debug.getupvalue(orig, i)
        if not name then
          break
        end
        debug.upvaluejoin(cloned, i, orig, i)
        i = i + 1
      end
      return cloned
    end,
    number = _id,
    string = _id,
    ['nil'] = _id,
    boolean = _id,
  }

  return function(orig)
    local f = deepcopy_funcs[type(orig)]
    if f then
      return f(orig)
    else
      error("Cannot deepcopy object of type "..type(orig))
    end
  end
end)()