xmpp.chapril.org-conversejs/src/converse-vcard.js

182 lines
7.1 KiB
JavaScript
Raw Normal View History

// Converse.js
// http://conversejs.org
//
// Copyright (c) 2013-2018, the Converse.js developers
// Licensed under the Mozilla Public License (MPLv2)
(function (root, factory) {
2018-05-24 21:09:33 +02:00
define(["converse-core", "crypto", "templates/vcard.html"], factory);
}(this, function (converse, CryptoJS, tpl_vcard) {
"use strict";
const { Backbone, Promise, Strophe, SHA1, _, $iq, $build, b64_sha1, moment, sizzle } = converse.env;
const u = converse.env.utils;
converse.plugins.add('converse-vcard', {
initialize () {
/* The initialize function gets called as soon as the plugin is
* loaded by converse.js's plugin machinery.
*/
const { _converse } = this;
_converse.VCard = Backbone.Model.extend({
defaults: {
'image': _converse.DEFAULT_IMAGE,
'image_type': _converse.DEFAULT_IMAGE_TYPE
},
set (key, val, options) {
// Override Backbone.Model.prototype.set to make sure that the
// default `image` and `image_type` values are maintained.
let attrs;
if (typeof key === 'object') {
attrs = key;
options = val;
} else {
(attrs = {})[key] = val;
}
if (_.has(attrs, 'image') && !attrs['image']) {
attrs['image'] = _converse.DEFAULT_IMAGE;
attrs['image_type'] = _converse.DEFAULT_IMAGE_TYPE;
return Backbone.Model.prototype.set.call(this, attrs, options);
} else {
return Backbone.Model.prototype.set.apply(this, arguments);
}
}
});
_converse.VCards = Backbone.Collection.extend({
model: _converse.VCard,
initialize () {
this.on('add', (vcard) => _converse.api.vcard.update(vcard));
}
});
function onVCardData (jid, iq, callback) {
const vcard = iq.querySelector('vCard');
let result = {};
if (!_.isNull(vcard)) {
result = {
'stanza': iq,
'fullname': _.get(vcard.querySelector('FN'), 'textContent'),
'nickname': _.get(vcard.querySelector('NICKNAME'), 'textContent'),
'image': _.get(vcard.querySelector('PHOTO BINVAL'), 'textContent'),
'image_type': _.get(vcard.querySelector('PHOTO TYPE'), 'textContent'),
'url': _.get(vcard.querySelector('URL'), 'textContent'),
'role': _.get(vcard.querySelector('ROLE'), 'textContent'),
'email': _.get(vcard.querySelector('EMAIL USERID'), 'textContent'),
'vcard_updated': moment().format(),
'vcard_error': undefined
};
}
if (result.image) {
const word_array_from_b64 = CryptoJS.enc.Base64.parse(result['image']);
2018-05-17 11:25:05 +02:00
result['image_hash'] = CryptoJS.SHA1(word_array_from_b64).toString()
}
if (callback) {
callback(result);
}
}
function onVCardError (jid, iq, errback) {
if (errback) {
errback({
'stanza': iq,
'jid': jid,
'vcard_error': moment().format()
});
}
}
function createStanza (type, jid, vcard_el) {
const iq = $iq(jid ? {'type': type, 'to': jid} : {'type': type});
if (!vcard_el) {
iq.c("vCard", {'xmlns': Strophe.NS.VCARD});
} else {
iq.cnode(vcard_el);
}
return iq;
}
function setVCard (jid, data) {
if (!jid) {
throw Error("No jid provided for the VCard data");
}
const vcard_el = Strophe.xmlHtmlNode(tpl_vcard(data)).firstElementChild;
return _converse.api.sendIQ(createStanza("set", jid, vcard_el));
}
function getVCard (_converse, jid) {
/* Request the VCard of another user. Returns a promise.
*
* Parameters:
* (String) jid - The Jabber ID of the user whose VCard
* is being requested.
*/
const to = Strophe.getBareJidFromJid(jid) === _converse.bare_jid ? null : jid;
return new Promise((resolve, reject) => {
_converse.connection.sendIQ(
createStanza("get", to),
_.partial(onVCardData, jid, _, resolve),
_.partial(onVCardError, jid, _, resolve),
_converse.IQ_TIMEOUT
);
});
}
/* Event handlers */
_converse.initVCardCollection = function () {
_converse.vcards = new _converse.VCards();
const id = b64_sha1(`converse.vcards`);
_converse.vcards.browserStorage = new Backbone.BrowserStorage[_converse.config.get('storage')](id);
_converse.vcards.fetch();
}
_converse.api.listen.on('sessionInitialized', _converse.initVCardCollection);
_converse.on('addClientFeatures', () => {
_converse.api.disco.own.features.add(Strophe.NS.VCARD);
});
_.extend(_converse.api, {
'vcard': {
'set' (jid, data) {
return setVCard(jid, data);
},
'get' (model, force) {
if (_.isString(model)) {
return getVCard(_converse, model);
} else if (force ||
!model.get('vcard_updated') ||
!moment(model.get('vcard_error')).isSame(new Date(), "day")) {
const jid = model.get('jid');
if (!jid) {
throw new Error("No JID to get vcard for!");
}
return getVCard(_converse, jid);
} else {
2018-05-01 14:51:18 +02:00
return Promise.resolve({});
}
2018-05-01 14:51:18 +02:00
},
'update' (model, force) {
return new Promise((resolve, reject) => {
this.get(model, force).then((vcard) => {
delete vcard['stanza']
model.save(vcard);
resolve();
});
});
}
}
});
}
});
}));