Comparison

plugins/mod_vcard_legacy.lua @ 9255:2aa40526df7b

mod_vcard_legacy: Respond to attempts to set the legacy vcard-temp
author Kim Alvefur <zash@zash.se>
date Tue, 21 Aug 2018 17:16:27 +0200
parent 9254:2ffbcad8ec50
child 9256:12d3d96e3918
comparison
equal deleted inserted replaced
9254:2ffbcad8ec50 9255:2aa40526df7b
1 local st = require "util.stanza" 1 local st = require "util.stanza"
2 local jid_split = require "util.jid".split; 2 local jid_split = require "util.jid".split;
3 3
4 local mod_pep = module:depends("pep"); 4 local mod_pep = module:depends("pep");
5
6 local sha1 = require "util.hashes".sha1;
7 local base64_decode = require "util.encodings".base64.decode;
5 8
6 module:add_feature("vcard-temp"); 9 module:add_feature("vcard-temp");
7 module:add_feature("urn:xmpp:pep-vcard-conversion:0"); 10 module:add_feature("urn:xmpp:pep-vcard-conversion:0");
8 11
9 -- Simple translations 12 -- Simple translations
108 111
109 origin.send(st.reply(stanza):add_child(vcard_temp)); 112 origin.send(st.reply(stanza):add_child(vcard_temp));
110 return true; 113 return true;
111 end); 114 end);
112 115
116 module:hook("iq-set/self/vcard-temp:vCard", function (event)
117 local origin, stanza = event.origin, event.stanza;
118 local pep_service = mod_pep.get_pep_service(origin.username);
119
120 local vcard_temp = stanza.tags[1];
121
122 local vcard4 = st.stanza("item", { xmlns = "http://jabber.org/protocol/pubsub", id = "current" })
123 :tag("vcard", { xmlns = 'urn:ietf:params:xml:ns:vcard-4.0' });
124
125 vcard4:tag("fn"):text_tag("text", vcard_temp:get_child_text("FN")):up();
126
127 local N = vcard_temp:get_child("N");
128
129 vcard4:tag("n")
130 :text_tag("surname", N and N:get_child_text("FAMILY"))
131 :text_tag("given", N and N:get_child_text("GIVEN"))
132 :text_tag("additional", N and N:get_child_text("MIDDLe"))
133 :text_tag("prefix", N and N:get_child_text("PREFIX"))
134 :text_tag("suffix", N and N:get_child_text("SUFFIX"))
135 :up();
136
137 for tag in vcard_temp:childtags() do
138 local typ = simple_map[tag.name:lower()];
139 if typ then
140 local text = tag:get_text();
141 if text then
142 vcard4:tag(tag.name:lower()):text_tag(typ, text):up();
143 end
144 elseif tag.name == "EMAIL" then
145 local text = tag:get_child_text("USERID");
146 if text then
147 vcard4:tag("email")
148 vcard4:text_tag("text", text)
149 vcard4:tag("parameters"):tag("type");
150 if tag:get_child("HOME") then
151 vcard4:text_tag("text", "home");
152 elseif tag:get_child("WORK") then
153 vcard4:text_tag("text", "work");
154 end
155 vcard4:up():up():up();
156 end
157 elseif tag.name == "TEL" then
158 local text = tag:get_child_text("NUMBER");
159 if text then
160 vcard4:tag("tel"):text_tag("uri", "tel:"..text);
161 end
162 vcard4:tag("parameters"):tag("type");
163 if tag:get_child("HOME") then
164 vcard4:text_tag("text", "home");
165 elseif tag:get_child("WORK") then
166 vcard4:text_tag("text", "work");
167 end
168 vcard4:up():up():up();
169 elseif tag.name == "ORG" then
170 local text = tag:get_child_text("ORGNAME");
171 if text then
172 vcard4:tag("org"):text_tag("text", text):up();
173 end
174 elseif tag.name == "DESC" then
175 local text = tag:get_text();
176 if text then
177 vcard4:tag("note"):text_tag("text", text):up();
178 end
179 elseif tag.name == "ADR" then
180 vcard4:tag("adr")
181 :text_tag("pobox", tag:get_child_text("POBOX"))
182 :text_tag("ext", tag:get_child_text("EXTADD"))
183 :text_tag("street", tag:get_child_text("STREET"))
184 :text_tag("locality", tag:get_child_text("LOCALITY"))
185 :text_tag("region", tag:get_child_text("REGION"))
186 :text_tag("code", tag:get_child_text("PCODE"))
187 :text_tag("country", tag:get_child_text("CTRY"));
188 vcard4:tag("parameters"):tag("type");
189 if tag:get_child("HOME") then
190 vcard4:text_tag("text", "home");
191 elseif tag:get_child("WORK") then
192 vcard4:text_tag("text", "work");
193 end
194 vcard4:up():up():up();
195 elseif tag.name == "PHOTO" then
196 local avatar_type = tag:get_child_text("TYPE");
197 local avatar_payload = tag:get_child_text("BINVAL");
198
199 if avatar_payload then
200 local avatar_raw = base64_decode(avatar_payload);
201 local avatar_hash = sha1(avatar_raw, true);
202
203 local avatar_meta = st.stanza("item", { id = avatar_hash, xmlns = "http://jabber.org/protocol/pubsub" })
204 :tag("metadata", { xmlns="urn:xmpp:avatar:metadata" })
205 :tag("info", {
206 bytes = tostring(#avatar_raw),
207 id = avatar_hash,
208 type = avatar_type,
209 });
210
211 local avatar_data = st.stanza("item", { id = avatar_hash, xmlns = "http://jabber.org/protocol/pubsub" })
212 :tag("data", { xmlns="urn:xmpp:avatar:data" })
213 :text(avatar_payload);
214
215 if pep_service:publish("urn:xmpp:avatar:data", origin.full_jid, avatar_hash, avatar_data) then
216 pep_service:publish("urn:xmpp:avatar:metadata", origin.full_jid, avatar_hash, avatar_meta);
217 end
218 end
219 end
220 end
221
222 local ok, err = pep_service:publish("urn:xmpp:vcard4", origin.full_jid, "current", vcard4);
223 if ok then
224 origin.send(st.reply(stanza));
225 elseif err == "forbidden" then
226 origin.send(st.error_reply(stanza, "auth", "forbidden"));
227 elseif err == "internal-server-error" then
228 origin.send(st.error_reply(stanza, "wait", "internal-server-error"));
229 else
230 origin.send(st.error_reply(stanza, "modify", "undefined-condition", err));
231 end
232
233 return true;
234 end);
235
113 local function inject_xep153(event) 236 local function inject_xep153(event)
114 local origin, stanza = event.origin, event.stanza; 237 local origin, stanza = event.origin, event.stanza;
115 local username = origin.username; 238 local username = origin.username;
116 if not username then return end 239 if not username then return end
117 local pep = mod_pep.get_pep_service(username); 240 local pep = mod_pep.get_pep_service(username);