aboutsummaryrefslogtreecommitdiff
path: root/serialize.lua
blob: 0a54212fb70a78e794dbd2303407b6c02aff5e8c (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
57
58
59
60
61
62
63
64
65
66
67
68
69
70

local function repr(x)
	if type(x) == "string" then
		return ("%q"):format(x)
	else
		return tostring(x)
	end
end

local function my_serialize_2(t, level)
	level = level or 0
	local lines = { }
	local indent = ("\t"):rep(level)
	for k, v in pairs(t) do
		local typ = type(v)
		if typ == "table" then
			table.insert(lines,
			  indent..("[%s] = {\n"):format(repr(k))
			  ..my_serialize_2(v, level + 1).."\n"
			  ..indent.."},")
		else
			table.insert(lines,
			  indent..("[%s] = %s,"):format(repr(k), repr(v)))
		end
	end
	return table.concat(lines, "\n")
end

function xban.serialize(t)
	minetest.log("warning", "[xban2] xban.serialize() is deprecated")
	return "return {\n"..my_serialize_2(t, 1).."\n}"
end

-- JSON doesn't allow combined string+number keys, this function moves any
-- number keys into an "entries" table
function xban.serialize_db(t)
	local res = {}
	local entries = {}
	for k, v in pairs(t) do
		if type(k) == "number" then
			entries[k] = v
		else
			res[k] = v
		end
	end
	res.entries = entries
	return minetest.write_json(res, true)
end

function xban.deserialize_db(s)
	if s:sub(1, 1) ~= "{" then
		-- Load legacy databases
		return minetest.deserialize(s)
	end

	local res, err = minetest.parse_json(s)
	if not res then
		return nil, err
	end

	-- Remove all "null"s added by empty tables
	for i, entry in ipairs(res.entries or {}) do
		entry.names = entry.names or {}
		entry.record = entry.record or {}
		res[i] = entry
	end
	res.entries = nil

	return res
end