Software /
code /
prosody-modules
Annotate
mod_rest/jsonmap.lib.lua @ 3866:c0df50ce96f0
mod_rest: Handle internal http request errors early and then return
Skips over attempted parsing of the payload which usually failed since
the body is an error string like "connection refused", so this produced
useless errors.
author | Kim Alvefur <zash@zash.se> |
---|---|
date | Sat, 25 Jan 2020 20:22:12 +0100 |
parent | 3860:9752a6f1b9f3 |
child | 3870:3261a82884bb |
rev | line source |
---|---|
3813 | 1 local array = require "util.array"; |
2 local jid = require "util.jid"; | |
3823
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
3 local json = require "util.json"; |
3813 | 4 local st = require "util.stanza"; |
5 local xml = require "util.xml"; | |
6 | |
7 local simple_types = { | |
8 -- basic message | |
9 body = "text_tag", | |
10 subject = "text_tag", | |
11 thread = "text_tag", | |
12 | |
13 -- basic presence | |
14 show = "text_tag", | |
15 status = "text_tag", | |
16 priority = "text_tag", | |
17 | |
18 state = {"name", "http://jabber.org/protocol/chatstates"}, | |
19 nick = {"text_tag", "http://jabber.org/protocol/nick", "nick"}, | |
20 delay = {"attr", "urn:xmpp:delay", "delay", "stamp"}, | |
21 replace = {"attr", "urn:xmpp:message-correct:0", "replace", "id"}, | |
22 | |
23 -- XEP-0045 MUC | |
24 -- TODO history, password, ??? | |
25 join = {"bool_tag", "http://jabber.org/protocol/muc", "x"}, | |
26 | |
27 -- XEP-0071 | |
28 html = { | |
29 "func", "http://jabber.org/protocol/xhtml-im", "html", | |
30 function (s) --> json string | |
3856
8bdb1729529b
mod_rest: Make XHTML-IM mapping more convenient
Kim Alvefur <zash@zash.se>
parents:
3855
diff
changeset
|
31 return (tostring(s:get_child("body", "http://www.w3.org/1999/xhtml")):gsub(" xmlns='[^']*'","", 1)); |
3813 | 32 end; |
33 function (s) --> xml | |
3817
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
34 if type(s) == "string" then |
3856
8bdb1729529b
mod_rest: Make XHTML-IM mapping more convenient
Kim Alvefur <zash@zash.se>
parents:
3855
diff
changeset
|
35 return assert(xml.parse([[<x:html xmlns:x='http://jabber.org/protocol/xhtml-im' xmlns='http://www.w3.org/1999/xhtml'>]]..s..[[</x:html>]])); |
3817
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
36 end |
3813 | 37 end; |
38 }; | |
39 | |
3855
0e1e900577c4
mod_rest: Improve some comments
Kim Alvefur <zash@zash.se>
parents:
3854
diff
changeset
|
40 -- XEP-0199: XMPP Ping |
3813 | 41 ping = {"bool_tag", "urn:xmpp:ping", "ping"}, |
42 | |
3854
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
43 -- XEP-0092: Software Version |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
44 version = {"func", "jabber:iq:version", "query", |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
45 function (s) |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
46 return { |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
47 name = s:get_child_text("name"); |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
48 version = s:get_child_text("version"); |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
49 os = s:get_child_text("os"); |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
50 } |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
51 end, |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
52 function (s) |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
53 local v = st.stanza("query", { xmlns = "jabber:iq:version" }); |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
54 if type(s) == "table" then |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
55 v:text_tag("name", s.name); |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
56 v:text_tag("version", s.version); |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
57 if s.os then |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
58 v:text_tag("os", s.os); |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
59 end |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
60 end |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
61 return v; |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
62 end |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
63 }; |
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
64 |
3813 | 65 -- XEP-0030 |
66 disco = { | |
67 "func", "http://jabber.org/protocol/disco#info", "query", | |
68 function (s) --> array of features | |
69 local identities, features = array(), array(); | |
70 for tag in s:childtags() do | |
71 if tag.name == "identity" and tag.attr.category and tag.attr.type then | |
72 identities:push({ category = tag.attr.category, type = tag.attr.type, name = tag.attr.name }); | |
73 elseif tag.name == "feature" and tag.attr.var then | |
74 features:push(tag.attr.var); | |
75 end | |
76 end | |
3822
f0a1d113dce4
mod_rest: Add support for mapping 'node' attr in disco#info
Kim Alvefur <zash@zash.se>
parents:
3819
diff
changeset
|
77 return { node = s.attr.node, identities = identities, features = features, }; |
3813 | 78 end; |
79 function (s) | |
3860
9752a6f1b9f3
mod_rest: Avoid treating special json.null value as any other table
Kim Alvefur <zash@zash.se>
parents:
3859
diff
changeset
|
80 if type(s) == "table" and s ~= json.null then |
3859
da3a0f055526
mod_rest: Fix handling of 'node' attribute in disco#info
Kim Alvefur <zash@zash.se>
parents:
3856
diff
changeset
|
81 local disco = st.stanza("query", { xmlns = "http://jabber.org/protocol/disco#info", node = s.node }); |
3813 | 82 if s.identities then |
3848
1b9834500123
mod_rest: Fix iteration over disco#info identities
Kim Alvefur <zash@zash.se>
parents:
3823
diff
changeset
|
83 for _, identity in ipairs(s.identities) do |
3850
8d13b9c9ba75
mod_rest: Fix disco#info identities data mapping
Kim Alvefur <zash@zash.se>
parents:
3849
diff
changeset
|
84 disco:tag("identity", { category = identity.category, type = identity.type, name = identity.name }):up(); |
3813 | 85 end |
86 end | |
87 if s.features then | |
3849
11c34e97fe1a
mod_rest: Fix iteration over disco#info features
Kim Alvefur <zash@zash.se>
parents:
3848
diff
changeset
|
88 for _, feature in ipairs(s.features) do |
3813 | 89 disco:tag("feature", { var = feature }):up(); |
90 end | |
91 end | |
3859
da3a0f055526
mod_rest: Fix handling of 'node' attribute in disco#info
Kim Alvefur <zash@zash.se>
parents:
3856
diff
changeset
|
92 return disco; |
da3a0f055526
mod_rest: Fix handling of 'node' attribute in disco#info
Kim Alvefur <zash@zash.se>
parents:
3856
diff
changeset
|
93 else |
da3a0f055526
mod_rest: Fix handling of 'node' attribute in disco#info
Kim Alvefur <zash@zash.se>
parents:
3856
diff
changeset
|
94 st.stanza("query", { xmlns = "http://jabber.org/protocol/disco#info", }); |
3813 | 95 end |
96 end; | |
97 }; | |
98 | |
99 items = { | |
100 "func", "http://jabber.org/protocol/disco#items", "query", | |
101 function (s) --> array of features | |
102 local items = array(); | |
103 for item in s:childtags("item") do | |
104 items:push({ jid = item.attr.jid, node = item.attr.node, name = item.attr.name }); | |
105 end | |
106 return items; | |
107 end; | |
108 function (s) | |
109 local disco = st.stanza("query", { xmlns = "http://jabber.org/protocol/disco#items" }); | |
3860
9752a6f1b9f3
mod_rest: Avoid treating special json.null value as any other table
Kim Alvefur <zash@zash.se>
parents:
3859
diff
changeset
|
110 if type(s) == "table" and s ~= json.null then |
3813 | 111 for _, item in ipairs(s) do |
3852
66f96b98d219
mod_rest: Allow returning an array of JID strings as disco#items
Kim Alvefur <zash@zash.se>
parents:
3851
diff
changeset
|
112 if type(item) == "string" then |
66f96b98d219
mod_rest: Allow returning an array of JID strings as disco#items
Kim Alvefur <zash@zash.se>
parents:
3851
diff
changeset
|
113 disco:tag("item", { jid = item }); |
66f96b98d219
mod_rest: Allow returning an array of JID strings as disco#items
Kim Alvefur <zash@zash.se>
parents:
3851
diff
changeset
|
114 elseif type(item) == "table" then |
66f96b98d219
mod_rest: Allow returning an array of JID strings as disco#items
Kim Alvefur <zash@zash.se>
parents:
3851
diff
changeset
|
115 disco:tag("item", { jid = item.jid, node = item.node, name = item.name }); |
66f96b98d219
mod_rest: Allow returning an array of JID strings as disco#items
Kim Alvefur <zash@zash.se>
parents:
3851
diff
changeset
|
116 end |
3813 | 117 end |
118 end | |
119 return disco; | |
120 end; | |
121 }; | |
122 | |
3855
0e1e900577c4
mod_rest: Improve some comments
Kim Alvefur <zash@zash.se>
parents:
3854
diff
changeset
|
123 -- XEP-0066: Out of Band Data |
3813 | 124 oob_url = {"func", "jabber:iq:oob", "query", |
125 function (s) | |
126 return s:get_child_text("url"); | |
127 end; | |
128 function (s) | |
3817
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
129 if type(s) == "string" then |
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
130 return st.stanza("query", { xmlns = "jabber:iq:oob" }):text_tag("url", s); |
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
131 end |
3813 | 132 end; |
133 }; | |
3823
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
134 |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
135 -- XEP-XXXX: User-defined Data Transfer |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
136 payload = {"func", "urn:xmpp:udt:0", "payload", |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
137 function (s) |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
138 local rawjson = s:get_child_text("json", "urn:xmpp:json:0"); |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
139 if not rawjson then return nil, "missing-json-payload"; end |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
140 local parsed, err = json.decode(rawjson); |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
141 if not parsed then return nil, err; end |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
142 return { |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
143 datatype = s.attr.datatype; |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
144 data = parsed; |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
145 }; |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
146 end; |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
147 function (s) |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
148 if type(s) == "table" then |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
149 return st.stanza("payload", { xmlns = "urn:xmpp:udt:0", datatype = s.datatype }) |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
150 :tag("json", { xmlns = "urn:xmpp:json:0" }):text(json.encode(s.data)); |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
151 end; |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
152 end |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
153 }; |
31b1797a78e1
mod_rest: Add support for XEP-XXXX: User-defined Data Transfer
Kim Alvefur <zash@zash.se>
parents:
3822
diff
changeset
|
154 |
3813 | 155 }; |
156 | |
157 local implied_kinds = { | |
158 disco = "iq", | |
159 items = "iq", | |
160 ping = "iq", | |
3854
25c34c9f755c
mod_rest: Add mapping of XEP-0092: Software Version
Kim Alvefur <zash@zash.se>
parents:
3852
diff
changeset
|
161 version = "iq", |
3813 | 162 |
163 body = "message", | |
164 html = "message", | |
165 replace = "message", | |
166 state = "message", | |
167 subject = "message", | |
168 thread = "message", | |
169 | |
170 join = "presence", | |
171 priority = "presence", | |
172 show = "presence", | |
173 status = "presence", | |
174 } | |
175 | |
176 local kind_by_type = { | |
177 get = "iq", set = "iq", result = "iq", | |
178 normal = "message", chat = "message", headline = "message", groupchat = "message", | |
179 available = "presence", unavailable = "presence", | |
180 subscribe = "presence", unsubscribe = "presence", | |
181 subscribed = "presence", unsubscribed = "presence", | |
182 } | |
183 | |
184 local function st2json(s) | |
185 local t = { | |
186 kind = s.name, | |
187 type = s.attr.type, | |
188 to = s.attr.to, | |
189 from = s.attr.from, | |
190 id = s.attr.id, | |
191 }; | |
192 if s.name == "presence" and not s.attr.type then | |
193 t.type = "available"; | |
194 end | |
195 | |
196 if t.to then | |
197 t.to = jid.prep(t.to); | |
198 if not t.to then return nil, "invalid-jid-to"; end | |
199 end | |
200 if t.from then | |
201 t.from = jid.prep(t.from); | |
202 if not t.from then return nil, "invalid-jid-from"; end | |
203 end | |
204 | |
205 if t.type == "error" then | |
206 local err_typ, err_condition, err_text = s:get_error(); | |
207 t.error = { | |
208 type = err_typ, | |
209 condition = err_condition, | |
210 text = err_text | |
211 }; | |
212 return t; | |
213 end | |
214 | |
215 for k, typ in pairs(simple_types) do | |
216 if typ == "text_tag" then | |
217 t[k] = s:get_child_text(k); | |
218 elseif typ[1] == "text_tag" then | |
219 t[k] = s:get_child_text(typ[3], typ[2]); | |
220 elseif typ[1] == "name" then | |
221 local child = s:get_child(nil, typ[2]); | |
222 if child then | |
223 t[k] = child.name; | |
224 end | |
225 elseif typ[1] == "attr" then | |
226 local child = s:get_child(typ[3], typ[2]) | |
227 if child then | |
228 t[k] = child.attr[typ[4]]; | |
229 end | |
230 elseif typ[1] == "bool_tag" then | |
231 if s:get_child(typ[3], typ[2]) then | |
232 t[k] = true; | |
233 end | |
234 elseif typ[1] == "func" then | |
235 local child = s:get_child(typ[3], typ[2] or k); | |
236 -- TODO handle err | |
237 if child then | |
238 t[k] = typ[4](child); | |
239 end | |
240 end | |
241 end | |
242 | |
243 return t; | |
244 end | |
245 | |
3817
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
246 local function str(s) |
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
247 if type(s) == "string" then |
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
248 return s; |
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
249 end |
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
250 end |
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
251 |
3813 | 252 local function json2st(t) |
3817
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
253 if type(t) ~= "table" or not str(next(t)) then |
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
254 return nil, "invalid-json"; |
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
255 end |
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
256 local kind = str(t.kind) or kind_by_type[str(t.type)]; |
3813 | 257 if not kind then |
258 for k, implied in pairs(implied_kinds) do | |
259 if t[k] then | |
260 kind = implied; | |
261 break | |
262 end | |
263 end | |
264 end | |
265 | |
266 local s = st.stanza(kind or "message", { | |
3817
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
267 type = t.type ~= "available" and str(t.type) or nil, |
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
268 to = str(t.to) and jid.prep(t.to); |
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
269 from = str(t.to) and jid.prep(t.from); |
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
270 id = str(t.id), |
3813 | 271 }); |
272 | |
273 if t.to and not s.attr.to then | |
274 return nil, "invalid-jid-to"; | |
275 end | |
276 if t.from and not s.attr.from then | |
277 return nil, "invalid-jid-from"; | |
278 end | |
3819 | 279 if kind == "iq" and not s.attr.type then |
280 s.attr.type = "get"; | |
3818
a607c69d0804
mod_rest: Guess 'get' as default type for 'iq' stanzas in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3817
diff
changeset
|
281 end |
3813 | 282 |
3817
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
283 if type(t.error) == "table" then |
937f8c463be6
mod_rest: Stricter type checks in JSON mapping
Kim Alvefur <zash@zash.se>
parents:
3813
diff
changeset
|
284 return st.error_reply(st.reply(s), str(t.error.type), str(t.error.condition), str(t.error.text)); |
3813 | 285 elseif t.type == "error" then |
286 s:text_tag("error", t.body, { code = t.error_code and tostring(t.error_code) }); | |
287 return s; | |
288 end | |
289 | |
290 for k, v in pairs(t) do | |
291 local typ = simple_types[k]; | |
292 if typ then | |
293 if typ == "text_tag" then | |
294 s:text_tag(k, v); | |
295 elseif typ[1] == "text_tag" then | |
296 s:text_tag(typ[3] or k, v, typ[2] and { xmlns = typ[2] }); | |
297 elseif typ[1] == "name" then | |
298 s:tag(v, { xmlns = typ[2] }):up(); | |
299 elseif typ[1] == "attr" then | |
300 s:tag(typ[3] or k, { xmlns = typ[2], [ typ[4] or k ] = v }):up(); | |
301 elseif typ[1] == "bool_tag" then | |
302 s:tag(typ[3] or k, { xmlns = typ[2] }):up(); | |
303 elseif typ[1] == "func" then | |
304 s:add_child(typ[5](v)):up(); | |
305 end | |
306 end | |
307 end | |
308 | |
309 s:reset(); | |
310 | |
311 return s; | |
312 end | |
313 | |
314 return { | |
315 st2json = st2json; | |
316 json2st = json2st; | |
317 }; |