forked from Egor-Skriptunoff/json4lua
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathexample.lua
executable file
·217 lines (181 loc) · 7.57 KB
/
example.lua
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
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
-- Example script for module "json.lua".
-- Demonstrates the functionality of the module.
local json = require('json')
print()
print('------------------------------------------')
print('-- encoding/decoding an object')
print('------------------------------------------')
local Lua_object = {
"t[1]", "t[2]", [-1]="t[-1]", -- integer indices will be converted to a string keys
str = 'Hello',
num = 17.4375,
array = {2, 3.0, 5.5},
nullval = json.null,
bool = false,
emptobj = json.empty, -- empty JSON object {}
emptarr = {}, -- empty JSON array []
-- the following members are not encodable to JSON, they will be skipped by encoder:
bad_number = 1/0, -- Inf and NaN are not available in JSON
func = math.sin, -- function
[json.null] = 0, -- key is not convertible to a string
[true] = 1, -- key is not convertible to a string
[3.5] = 2 -- numbers with fractional part are prohibited to be converted to a string keys
}
-- Encoding
local JSON_text = json.encode(Lua_object)
print'Encoded JSON text:'
print(JSON_text)
-- Decoding
local result = json.decode(JSON_text)
print'The decoded table "result":'
for k, v in pairs(result) do print('', k, v) end
print'The decoded table "result.array":'
for k, v in pairs(result.array) do print('', k, v) end
print()
print('------------------------------------------')
print('-- encoding/decoding an array')
print('------------------------------------------')
local Lua_array = { {x=1, y=2}, 2.5, {[10^9] = "mlrd"} }
Lua_array[7] = "arr[7]"
Lua_array[11] = json.null
local JSON_text = json.encode(Lua_array)
print'Encoded JSON text:'
print(JSON_text)
-- Now JSON decode the JSON string
local result = json.decode(JSON_text)
print ("The decoded table result:")
for k, v in pairs(result) do print('', k, v) end
print()
print('------------------------------------------')
print('-- decoding a JSON string containing UTF-16 surrogate pairs')
print('------------------------------------------')
local someJSON = [[ "Test \u00A7 \"\ud834\udd1e\" \\\uD83D\uDE02\/ " ]]
print('JSON: <'..someJSON..'>')
print('Decoded: <'..json.decode(someJSON)..'>') --> Test § "𝄞" \😂/
print()
print('------------------------------------------')
print('-- decoding a JSON array with omitted values')
print('------------------------------------------')
local input_JSON = [[ [,,42,,] ]]
local result = json.decode(input_JSON)
print ("The decoded result is a table:")
for k, v in pairs(result) do print('', k, v) end
print()
print('------------------------------------------')
print('-- decoding a JSON object with omitted values')
print('------------------------------------------')
local input_JSON = [[ {,,a:true,,,a$b_5:-0.01e99,,} ]]
local result = json.decode(input_JSON)
print("The decoded result is a table:")
for k, v in pairs(result) do print('', type(k), k, type(v), v) end
print()
print('------------------------------------------')
print('-- show information passed to callback function during JSON traverse')
print('------------------------------------------')
local function callback(path, json_type, value, pos, pos_last)
print(table.concat(path, '/'), json_type, value, pos, pos_last)
end
print('path', 'j_type', 'value', 'pos', 'pos_last')
json.traverse([[ 42 ]], callback)
print()
print('path', 'j_type', 'value', 'pos', 'pos_last')
json.traverse([[ {"a":true, "b":null, "c":["one","two"], "d":{ "e":{}, "f":[] } } ]], callback)
print()
print('------------------------------------------')
print('-- show information passed to callback function during JSON traverse-and-partially-decode')
print('------------------------------------------')
local function callback(path, json_type, value, pos, pos_last)
print(table.concat(path, '/'), json_type, value, pos, pos_last)
local elem_name = path[#path]
return elem_name == "c" or elem_name == "e" -- we want to decode elements "c" and "e" while traversing
end
print('path', 'j_type', 'value', 'pos', 'pos_last')
json.traverse([[ {"a":true, "b":null, "c":["one","two"], "d":{ "e":{}, "f":[] } } ]], callback)
print()
print('------------------------------------------')
print('-- traversing JSON string to search for data')
print('------------------------------------------')
local input_JSON = [[ { "the_answer":42, "greeting":"Hello", "Fermat_primes":[3, 5, 17, 257, 65537], "math_consts":{ "e":2.72, "pi":3.14 } } ]]
-- All we need to know from this JSON is: all Fermat primes, math constant "e" and greeting word
local function my_callback (path, json_type, value)
if
-- full check: whole path array and json_type are checked to be what we want
#path == 1
and path[1] == "greeting"
and json_type == "string"
then
print("greeting word = "..value)
elseif
-- simplified check: we assume here that field with name "e" is unique inside this JSON
path[#path] == "e"
then
print("math const e = "..value)
elseif
-- print all numeric items inside "Fermat_primes"
#path == 2 -- depth == 2 for elements inside array "Fermat_primes"
and path[1] == "Fermat_primes"
and json_type == "number"
then
print("F"..path[2].." = "..value) -- path[2] = index (1-based) inside JSON array
end
end
-- Traverse and print all needed values
json.traverse(input_JSON, my_callback)
print()
print('------------------------------------------')
print('-- partial decoding of JSON while traversing it')
print('------------------------------------------')
local input_JSON = [[ { "the_answer":42, "greeting":"Hello", "Fermat_primes":[3, 5, 17, 257, 65537], "math_consts":{ "e":2.72, "pi":3.14 } } ]]
-- All we need to know from this JSON is: all Fermat primes, math constant "e" and greeting word
-- But, unlike previous example, now we need these values stored in Lua variables (Fermat primes JSON array should be decoded as Lua array)
local FP, e, greeting
local function my_callback (path, json_type, value)
if
-- full check: whole path array and json_type are checked to be what we want
#path == 1
and path[1] == "greeting"
and json_type == "string"
then
greeting = value
elseif
-- simplified check: we assume here that field with name "e" is unique inside this JSON
path[#path] == "e"
then
e = value
elseif
-- print all numeric items inside "Fermat_primes"
#path == 1 -- depth == 1 for array "Fermat_primes" itself
and path[1] == "Fermat_primes"
and json_type == "array"
then
FP = value -- this line will be executed twice: first time "value" is nil
return true -- return true to signal "yes, we need this array decoded as Lua object"
end
end
-- Do traverse and partial decoding to get all the values we need
json.traverse(input_JSON, my_callback)
-- Now all values are ready in Lua variables
print("greeting word = "..greeting)
print("math const e = "..e)
print("The Fermat_primes array:")
for k, v in ipairs(FP) do print('', k, v) end
print()
print('------------------------------------------')
print('-- traverse large JSON file')
print('------------------------------------------')
-- Open file
local file = assert(io.open('large_json.txt', 'r'))
-- Define loader function which will read the file in 4KByte chunks
local function my_json_loader()
return file:read(4*1024)
end
-- Prepare callback function for traverse
local function my_callback (path, json_type, value, pos, last_pos)
-- Do whatever you need here
-- (see previous examples on using json.traverse)
end
-- Do traverse
-- Set initial position as 3-rd argument (default 1) if JSON is stored not from the beginning of your file
json.traverse(my_json_loader, my_callback)
-- Close file
file:close()