Software /
code /
prosody
Comparison
teal-src/util/datamapper.tl @ 11456:4e376a43fe40
util.datamapper: Factor out common schema unpacking
This code extracts the bits from the schema that determines how the data
is to be mapped to/from XML.
author | Kim Alvefur <zash@zash.se> |
---|---|
date | Sun, 14 Mar 2021 16:50:49 +0100 |
parent | 11455:a5050e21ab08 |
child | 11457:6a51749af7f4 |
comparison
equal
deleted
inserted
replaced
11455:a5050e21ab08 | 11456:4e376a43fe40 |
---|---|
49 "in_attribute" | 49 "in_attribute" |
50 "in_single_attribute" | 50 "in_single_attribute" |
51 "in_children" | 51 "in_children" |
52 end | 52 end |
53 | 53 |
54 local function unpack_propschema( propschema : js.schema_t | js.schema_t.type_e, propname : string, current_ns : string ) | |
55 : js.schema_t.type_e, value_goes, string, string, string, string, { any } | |
56 local proptype : js.schema_t.type_e = "string" | |
57 local value_where : value_goes = "in_text_tag" | |
58 local name = propname | |
59 local namespace = current_ns | |
60 local prefix : string | |
61 local single_attribute : string | |
62 local enums : { any } | |
63 | |
64 if propschema is js.schema_t then | |
65 proptype = propschema.type | |
66 elseif propschema is js.schema_t.type_e then | |
67 proptype = propschema | |
68 end | |
69 | |
70 if propschema is js.schema_t then | |
71 local xml = propschema.xml | |
72 if xml then | |
73 if xml.name then | |
74 name = xml.name | |
75 end | |
76 if xml.namespace then | |
77 namespace = xml.namespace | |
78 end | |
79 if xml.prefix then | |
80 prefix = xml.prefix | |
81 end | |
82 | |
83 if xml.attribute then | |
84 value_where = "in_attribute" | |
85 elseif xml.text then | |
86 value_where = "in_text" | |
87 elseif xml.x_name_is_value then | |
88 value_where = "in_tag_name" | |
89 elseif xml.x_single_attribute then | |
90 single_attribute = xml.x_single_attribute | |
91 value_where = "in_single_attribute" | |
92 end | |
93 end | |
94 if propschema["const"] then | |
95 enums = { propschema["const"] } | |
96 elseif propschema["enum"] then | |
97 enums = propschema["enum"] | |
98 end | |
99 end | |
100 | |
101 if proptype == "object" or proptype == "array" then | |
102 value_where = "in_children" | |
103 end | |
104 | |
105 return proptype, value_where, name, namespace, prefix, single_attribute, enums | |
106 end | |
107 | |
108 | |
54 local function parse_object (schema : js.schema_t, s : st.stanza_t) : table | 109 local function parse_object (schema : js.schema_t, s : st.stanza_t) : table |
55 local out : { string : any } = {} | 110 local out : { string : any } = {} |
56 if schema.properties then | 111 if schema.properties then |
57 for prop, propschema in pairs(schema.properties) do | 112 for prop, propschema in pairs(schema.properties) do |
58 -- TODO factor out, if it's generic enough | 113 |
59 local name = prop | 114 local proptype, value_where, name, namespace, prefix, single_attribute, enums = unpack_propschema(propschema, prop, s.attr.xmlns) |
60 local namespace = s.attr.xmlns; | |
61 local prefix : string = nil | |
62 local value_where : value_goes = "in_text_tag" | |
63 local single_attribute : string | |
64 local enums : { any } | |
65 | |
66 local proptype : js.schema_t.type_e | |
67 if propschema is js.schema_t then | |
68 proptype = propschema.type | |
69 elseif propschema is js.schema_t.type_e then | |
70 proptype = propschema | |
71 end | |
72 | |
73 if proptype == "object" or proptype == "array" then | |
74 value_where = "in_children" | |
75 end | |
76 | |
77 if propschema is js.schema_t and propschema.xml then | |
78 if propschema.xml.name then | |
79 name = propschema.xml.name | |
80 end | |
81 if propschema.xml.namespace then | |
82 namespace = propschema.xml.namespace | |
83 end | |
84 if propschema.xml.prefix then | |
85 prefix = propschema.xml.prefix | |
86 end | |
87 if propschema.xml.attribute then | |
88 value_where = "in_attribute" | |
89 elseif propschema.xml.text then | |
90 -- XXX Not yet in OpenAPI | |
91 value_where = "in_text" | |
92 elseif propschema.xml.x_name_is_value then | |
93 -- XXX Custom extension | |
94 value_where = "in_tag_name" | |
95 elseif propschema.xml.x_single_attribute then | |
96 -- XXX Custom extension | |
97 single_attribute = propschema.xml.x_single_attribute | |
98 value_where = "in_single_attribute" | |
99 end | |
100 if propschema["const"] then | |
101 enums = { propschema["const"] } | |
102 elseif propschema["enum"] then | |
103 enums = propschema["enum"] | |
104 end | |
105 end | |
106 | 115 |
107 local value : string | 116 local value : string |
108 if value_where == "in_tag_name" then | 117 if value_where == "in_tag_name" then |
109 local c : st.stanza_t | 118 local c : st.stanza_t |
110 if proptype == "boolean" then | 119 if proptype == "boolean" then |
179 | 188 |
180 for prop, propschema in pairs(schema.properties) do | 189 for prop, propschema in pairs(schema.properties) do |
181 local v = t[prop] | 190 local v = t[prop] |
182 | 191 |
183 if v ~= nil then | 192 if v ~= nil then |
184 local proptype : js.schema_t.type_e | 193 |
185 if propschema is js.schema_t then | 194 local proptype, value_where, name, namespace, prefix, single_attribute = unpack_propschema(propschema, prop, current_ns) |
186 proptype = propschema.type | |
187 elseif propschema is js.schema_t.type_e then | |
188 proptype = propschema | |
189 end | |
190 | |
191 local name = prop | |
192 local namespace = current_ns | |
193 local prefix : string = nil | |
194 local value_where : value_goes = "in_text_tag" | |
195 local single_attribute : string | |
196 | |
197 if propschema is js.schema_t and propschema.xml then | |
198 | |
199 if propschema.xml.name then | |
200 name = propschema.xml.name | |
201 end | |
202 if propschema.xml.namespace then | |
203 namespace = propschema.xml.namespace | |
204 end | |
205 | |
206 if propschema.xml.prefix then | |
207 prefix = propschema.xml.prefix | |
208 end | |
209 | |
210 if propschema.xml.attribute then | |
211 value_where = "in_attribute" | |
212 elseif propschema.xml.text then | |
213 value_where = "in_text" | |
214 elseif propschema.xml.x_name_is_value then | |
215 value_where = "in_tag_name" | |
216 elseif propschema.xml.x_single_attribute then | |
217 single_attribute = propschema.xml.x_single_attribute | |
218 value_where = "in_single_attribute" | |
219 end | |
220 end | |
221 | 195 |
222 if value_where == "in_attribute" then | 196 if value_where == "in_attribute" then |
223 local attr = name | 197 local attr = name |
224 if prefix then | 198 if prefix then |
225 attr = prefix .. ':' .. name | 199 attr = prefix .. ':' .. name |