Commit 5350cb10 authored by JC Brand's avatar JC Brand

Don't throw timeout errors for sent IQ#result or IQ#error stanzas

parent e82d6785
/* global mock, converse */ /* global mock, converse */
const Strophe = converse.env.Strophe;
describe("A chat room", function () { describe("A chat room", function () {
it("can be bookmarked", mock.initConverse(['rosterGroupsFetched'], {}, async function (done, _converse) { it("can be bookmarked", mock.initConverse(['rosterGroupsFetched'], {}, async function (done, _converse) {
...@@ -19,7 +22,7 @@ describe("A chat room", function () { ...@@ -19,7 +22,7 @@ describe("A chat room", function () {
spyOn(_converse.connection, 'getUniqueId').and.callThrough(); spyOn(_converse.connection, 'getUniqueId').and.callThrough();
await mock.openChatRoom(_converse, 'theplay', 'conference.shakespeare.lit', 'JC'); await mock.openChatRoom(_converse, 'theplay', 'conference.shakespeare.lit', 'JC');
var jid = 'theplay@conference.shakespeare.lit'; const jid = 'theplay@conference.shakespeare.lit';
const view = _converse.chatboxviews.get(jid); const view = _converse.chatboxviews.get(jid);
spyOn(view, 'renderBookmarkForm').and.callThrough(); spyOn(view, 'renderBookmarkForm').and.callThrough();
spyOn(view, 'closeForm').and.callThrough(); spyOn(view, 'closeForm').and.callThrough();
...@@ -78,7 +81,7 @@ describe("A chat room", function () { ...@@ -78,7 +81,7 @@ describe("A chat room", function () {
view.el.querySelector('.btn-primary').click(); view.el.querySelector('.btn-primary').click();
await u.waitUntil(() => sent_stanza); await u.waitUntil(() => sent_stanza);
expect(sent_stanza.toLocaleString()).toBe( expect(Strophe.serialize(sent_stanza)).toBe(
`<iq from="romeo@montague.lit/orchard" id="${IQ_id}" type="set" xmlns="jabber:client">`+ `<iq from="romeo@montague.lit/orchard" id="${IQ_id}" type="set" xmlns="jabber:client">`+
`<pubsub xmlns="http://jabber.org/protocol/pubsub">`+ `<pubsub xmlns="http://jabber.org/protocol/pubsub">`+
`<publish node="storage:bookmarks">`+ `<publish node="storage:bookmarks">`+
......
...@@ -418,8 +418,8 @@ describe("Message Archive Management", function () { ...@@ -418,8 +418,8 @@ describe("Message Archive Management", function () {
}); });
_converse.api.archive.query(); _converse.api.archive.query();
await u.waitUntil(() => sent_stanza); await u.waitUntil(() => sent_stanza);
const queryid = sent_stanza.nodeTree.querySelector('query').getAttribute('queryid'); const queryid = sent_stanza.querySelector('query').getAttribute('queryid');
expect(sent_stanza.toString()).toBe( expect(Strophe.serialize(sent_stanza)).toBe(
`<iq id="${IQ_id}" type="set" xmlns="jabber:client"><query queryid="${queryid}" xmlns="urn:xmpp:mam:2"/></iq>`); `<iq id="${IQ_id}" type="set" xmlns="jabber:client"><query queryid="${queryid}" xmlns="urn:xmpp:mam:2"/></iq>`);
done(); done();
})); }));
...@@ -436,8 +436,8 @@ describe("Message Archive Management", function () { ...@@ -436,8 +436,8 @@ describe("Message Archive Management", function () {
}); });
_converse.api.archive.query({'with':'juliet@capulet.lit'}); _converse.api.archive.query({'with':'juliet@capulet.lit'});
await u.waitUntil(() => sent_stanza); await u.waitUntil(() => sent_stanza);
const queryid = sent_stanza.nodeTree.querySelector('query').getAttribute('queryid'); const queryid = sent_stanza.querySelector('query').getAttribute('queryid');
expect(sent_stanza.toString()).toBe( expect(Strophe.serialize(sent_stanza)).toBe(
`<iq id="${IQ_id}" type="set" xmlns="jabber:client">`+ `<iq id="${IQ_id}" type="set" xmlns="jabber:client">`+
`<query queryid="${queryid}" xmlns="urn:xmpp:mam:2">`+ `<query queryid="${queryid}" xmlns="urn:xmpp:mam:2">`+
`<x type="submit" xmlns="jabber:x:data">`+ `<x type="submit" xmlns="jabber:x:data">`+
...@@ -564,8 +564,8 @@ describe("Message Archive Management", function () { ...@@ -564,8 +564,8 @@ describe("Message Archive Management", function () {
'end': end 'end': end
}); });
await u.waitUntil(() => sent_stanza); await u.waitUntil(() => sent_stanza);
const queryid = sent_stanza.nodeTree.querySelector('query').getAttribute('queryid'); const queryid = sent_stanza.querySelector('query').getAttribute('queryid');
expect(sent_stanza.toString()).toBe( expect(Strophe.serialize(sent_stanza)).toBe(
`<iq id="${IQ_id}" type="set" xmlns="jabber:client">`+ `<iq id="${IQ_id}" type="set" xmlns="jabber:client">`+
`<query queryid="${queryid}" xmlns="urn:xmpp:mam:2">`+ `<query queryid="${queryid}" xmlns="urn:xmpp:mam:2">`+
`<x type="submit" xmlns="jabber:x:data">`+ `<x type="submit" xmlns="jabber:x:data">`+
...@@ -613,8 +613,8 @@ describe("Message Archive Management", function () { ...@@ -613,8 +613,8 @@ describe("Message Archive Management", function () {
const start = '2010-06-07T00:00:00Z'; const start = '2010-06-07T00:00:00Z';
_converse.api.archive.query({'start': start}); _converse.api.archive.query({'start': start});
await u.waitUntil(() => sent_stanza); await u.waitUntil(() => sent_stanza);
const queryid = sent_stanza.nodeTree.querySelector('query').getAttribute('queryid'); const queryid = sent_stanza.querySelector('query').getAttribute('queryid');
expect(sent_stanza.toString()).toBe( expect(Strophe.serialize(sent_stanza)).toBe(
`<iq id="${IQ_id}" type="set" xmlns="jabber:client">`+ `<iq id="${IQ_id}" type="set" xmlns="jabber:client">`+
`<query queryid="${queryid}" xmlns="urn:xmpp:mam:2">`+ `<query queryid="${queryid}" xmlns="urn:xmpp:mam:2">`+
`<x type="submit" xmlns="jabber:x:data">`+ `<x type="submit" xmlns="jabber:x:data">`+
...@@ -644,8 +644,8 @@ describe("Message Archive Management", function () { ...@@ -644,8 +644,8 @@ describe("Message Archive Management", function () {
const start = '2010-06-07T00:00:00Z'; const start = '2010-06-07T00:00:00Z';
_converse.api.archive.query({'start': start, 'max':10}); _converse.api.archive.query({'start': start, 'max':10});
await u.waitUntil(() => sent_stanza); await u.waitUntil(() => sent_stanza);
const queryid = sent_stanza.nodeTree.querySelector('query').getAttribute('queryid'); const queryid = sent_stanza.querySelector('query').getAttribute('queryid');
expect(sent_stanza.toString()).toBe( expect(Strophe.serialize(sent_stanza)).toBe(
`<iq id="${IQ_id}" type="set" xmlns="jabber:client">`+ `<iq id="${IQ_id}" type="set" xmlns="jabber:client">`+
`<query queryid="${queryid}" xmlns="urn:xmpp:mam:2">`+ `<query queryid="${queryid}" xmlns="urn:xmpp:mam:2">`+
`<x type="submit" xmlns="jabber:x:data">`+ `<x type="submit" xmlns="jabber:x:data">`+
...@@ -682,8 +682,8 @@ describe("Message Archive Management", function () { ...@@ -682,8 +682,8 @@ describe("Message Archive Management", function () {
'max':10 'max':10
}); });
await u.waitUntil(() => sent_stanza); await u.waitUntil(() => sent_stanza);
const queryid = sent_stanza.nodeTree.querySelector('query').getAttribute('queryid'); const queryid = sent_stanza.querySelector('query').getAttribute('queryid');
expect(sent_stanza.toString()).toBe( expect(Strophe.serialize(sent_stanza)).toBe(
`<iq id="${IQ_id}" type="set" xmlns="jabber:client">`+ `<iq id="${IQ_id}" type="set" xmlns="jabber:client">`+
`<query queryid="${queryid}" xmlns="urn:xmpp:mam:2">`+ `<query queryid="${queryid}" xmlns="urn:xmpp:mam:2">`+
`<x type="submit" xmlns="jabber:x:data">`+ `<x type="submit" xmlns="jabber:x:data">`+
...@@ -715,8 +715,8 @@ describe("Message Archive Management", function () { ...@@ -715,8 +715,8 @@ describe("Message Archive Management", function () {
}); });
_converse.api.archive.query({'before': '', 'max':10}); _converse.api.archive.query({'before': '', 'max':10});
await u.waitUntil(() => sent_stanza); await u.waitUntil(() => sent_stanza);
const queryid = sent_stanza.nodeTree.querySelector('query').getAttribute('queryid'); const queryid = sent_stanza.querySelector('query').getAttribute('queryid');
expect(sent_stanza.toString()).toBe( expect(Strophe.serialize(sent_stanza)).toBe(
`<iq id="${IQ_id}" type="set" xmlns="jabber:client">`+ `<iq id="${IQ_id}" type="set" xmlns="jabber:client">`+
`<query queryid="${queryid}" xmlns="urn:xmpp:mam:2">`+ `<query queryid="${queryid}" xmlns="urn:xmpp:mam:2">`+
`<x type="submit" xmlns="jabber:x:data">`+ `<x type="submit" xmlns="jabber:x:data">`+
...@@ -752,8 +752,8 @@ describe("Message Archive Management", function () { ...@@ -752,8 +752,8 @@ describe("Message Archive Management", function () {
rsm.start = '2010-06-07T00:00:00Z'; rsm.start = '2010-06-07T00:00:00Z';
_converse.api.archive.query(rsm); _converse.api.archive.query(rsm);
await u.waitUntil(() => sent_stanza); await u.waitUntil(() => sent_stanza);
const queryid = sent_stanza.nodeTree.querySelector('query').getAttribute('queryid'); const queryid = sent_stanza.querySelector('query').getAttribute('queryid');
expect(sent_stanza.toString()).toBe( expect(Strophe.serialize(sent_stanza)).toBe(
`<iq id="${IQ_id}" type="set" xmlns="jabber:client">`+ `<iq id="${IQ_id}" type="set" xmlns="jabber:client">`+
`<query queryid="${queryid}" xmlns="urn:xmpp:mam:2">`+ `<query queryid="${queryid}" xmlns="urn:xmpp:mam:2">`+
`<x type="submit" xmlns="jabber:x:data">`+ `<x type="submit" xmlns="jabber:x:data">`+
...@@ -787,7 +787,7 @@ describe("Message Archive Management", function () { ...@@ -787,7 +787,7 @@ describe("Message Archive Management", function () {
}); });
const promise = _converse.api.archive.query({'with': 'romeo@capulet.lit', 'max':'10'}); const promise = _converse.api.archive.query({'with': 'romeo@capulet.lit', 'max':'10'});
await u.waitUntil(() => sent_stanza); await u.waitUntil(() => sent_stanza);
const queryid = sent_stanza.nodeTree.querySelector('query').getAttribute('queryid'); const queryid = sent_stanza.querySelector('query').getAttribute('queryid');
/* <message id='aeb213' to='juliet@capulet.lit/chamber'> /* <message id='aeb213' to='juliet@capulet.lit/chamber'>
* <result xmlns='urn:xmpp:mam:2' queryid='f27' id='28482-98726-73623'> * <result xmlns='urn:xmpp:mam:2' queryid='f27' id='28482-98726-73623'>
...@@ -953,9 +953,9 @@ describe("Chatboxes", function () { ...@@ -953,9 +953,9 @@ describe("Chatboxes", function () {
IQ_id = sendIQ.bind(this)(iq, callback, errback); IQ_id = sendIQ.bind(this)(iq, callback, errback);
}); });
await u.waitUntil(() => sent_stanza); await u.waitUntil(() => sent_stanza);
const stanza_el = sent_stanza.root().nodeTree; const stanza_el = sent_stanza;
const queryid = stanza_el.querySelector('query').getAttribute('queryid'); const queryid = stanza_el.querySelector('query').getAttribute('queryid');
expect(sent_stanza.toString()).toBe( expect(Strophe.serialize(sent_stanza)).toBe(
`<iq id="${stanza_el.getAttribute('id')}" type="set" xmlns="jabber:client">`+ `<iq id="${stanza_el.getAttribute('id')}" type="set" xmlns="jabber:client">`+
`<query queryid="${queryid}" xmlns="urn:xmpp:mam:2">`+ `<query queryid="${queryid}" xmlns="urn:xmpp:mam:2">`+
`<x type="submit" xmlns="jabber:x:data">`+ `<x type="submit" xmlns="jabber:x:data">`+
......
...@@ -1496,7 +1496,7 @@ describe("Groupchats", function () { ...@@ -1496,7 +1496,7 @@ describe("Groupchats", function () {
* <query xmlns='http://jabber.org/protocol/muc#owner'/> * <query xmlns='http://jabber.org/protocol/muc#owner'/>
* </iq> * </iq>
*/ */
expect(sent_IQ.toLocaleString()).toBe( expect(Strophe.serialize(sent_IQ)).toBe(
`<iq id="`+IQ_id+`" to="coven@chat.shakespeare.lit" type="get" xmlns="jabber:client">`+ `<iq id="`+IQ_id+`" to="coven@chat.shakespeare.lit" type="get" xmlns="jabber:client">`+
`<query xmlns="http://jabber.org/protocol/muc#owner"/>`+ `<query xmlns="http://jabber.org/protocol/muc#owner"/>`+
`</iq>`); `</iq>`);
...@@ -1645,11 +1645,10 @@ describe("Groupchats", function () { ...@@ -1645,11 +1645,10 @@ describe("Groupchats", function () {
view.el.querySelector('.chatroom-form input[type="submit"]').click(); view.el.querySelector('.chatroom-form input[type="submit"]').click();
const sent_stanza = sent_IQ.nodeTree; expect(sent_IQ.querySelector('field[var="muc#roomconfig_membersonly"] value').textContent.trim()).toBe('1');
expect(sent_stanza.querySelector('field[var="muc#roomconfig_membersonly"] value').textContent.trim()).toBe('1'); expect(sent_IQ.querySelector('field[var="muc#roomconfig_moderatedroom"] value').textContent.trim()).toBe('1');
expect(sent_stanza.querySelector('field[var="muc#roomconfig_moderatedroom"] value').textContent.trim()).toBe('1'); expect(sent_IQ.querySelector('field[var="muc#roomconfig_allowpm"] value').textContent.trim()).toBe('moderators');
expect(sent_stanza.querySelector('field[var="muc#roomconfig_allowpm"] value').textContent.trim()).toBe('moderators'); expect(sent_IQ.querySelector('field[var="muc#roomconfig_presencebroadcast"] value').textContent.trim()).toBe('moderator');
expect(sent_stanza.querySelector('field[var="muc#roomconfig_presencebroadcast"] value').textContent.trim()).toBe('moderator');
done(); done();
})); }));
...@@ -3433,7 +3432,7 @@ describe("Groupchats", function () { ...@@ -3433,7 +3432,7 @@ describe("Groupchats", function () {
expect(view.validateRoleOrAffiliationChangeArgs.calls.count()).toBe(3); expect(view.validateRoleOrAffiliationChangeArgs.calls.count()).toBe(3);
expect(view.model.setAffiliation).toHaveBeenCalled(); expect(view.model.setAffiliation).toHaveBeenCalled();
// Check that the member list now gets updated // Check that the member list now gets updated
expect(sent_IQ.toLocaleString()).toBe( expect(Strophe.serialize(sent_IQ)).toBe(
`<iq id="${IQ_id}" to="lounge@montague.lit" type="set" xmlns="jabber:client">`+ `<iq id="${IQ_id}" to="lounge@montague.lit" type="set" xmlns="jabber:client">`+
`<query xmlns="http://jabber.org/protocol/muc#admin">`+ `<query xmlns="http://jabber.org/protocol/muc#admin">`+
`<item affiliation="owner" jid="annoyingguy@montague.lit">`+ `<item affiliation="owner" jid="annoyingguy@montague.lit">`+
...@@ -3513,7 +3512,7 @@ describe("Groupchats", function () { ...@@ -3513,7 +3512,7 @@ describe("Groupchats", function () {
expect(view.validateRoleOrAffiliationChangeArgs.calls.count()).toBe(2); expect(view.validateRoleOrAffiliationChangeArgs.calls.count()).toBe(2);
expect(view.model.setAffiliation).toHaveBeenCalled(); expect(view.model.setAffiliation).toHaveBeenCalled();
// Check that the member list now gets updated // Check that the member list now gets updated
expect(sent_IQ.toLocaleString()).toBe( expect(Strophe.serialize(sent_IQ)).toBe(
`<iq id="${IQ_id}" to="lounge@montague.lit" type="set" xmlns="jabber:client">`+ `<iq id="${IQ_id}" to="lounge@montague.lit" type="set" xmlns="jabber:client">`+
`<query xmlns="http://jabber.org/protocol/muc#admin">`+ `<query xmlns="http://jabber.org/protocol/muc#admin">`+
`<item affiliation="outcast" jid="annoyingguy@montague.lit">`+ `<item affiliation="outcast" jid="annoyingguy@montague.lit">`+
...@@ -3612,7 +3611,7 @@ describe("Groupchats", function () { ...@@ -3612,7 +3611,7 @@ describe("Groupchats", function () {
expect(view.validateRoleOrAffiliationChangeArgs.calls.count()).toBe(2); expect(view.validateRoleOrAffiliationChangeArgs.calls.count()).toBe(2);
expect(view.model.setRole).toHaveBeenCalled(); expect(view.model.setRole).toHaveBeenCalled();
expect(sent_IQ.toLocaleString()).toBe( expect(Strophe.serialize(sent_IQ)).toBe(
`<iq id="${IQ_id}" to="lounge@montague.lit" type="set" xmlns="jabber:client">`+ `<iq id="${IQ_id}" to="lounge@montague.lit" type="set" xmlns="jabber:client">`+
`<query xmlns="http://jabber.org/protocol/muc#admin">`+ `<query xmlns="http://jabber.org/protocol/muc#admin">`+
`<item nick="annoying guy" role="none">`+ `<item nick="annoying guy" role="none">`+
...@@ -3717,7 +3716,7 @@ describe("Groupchats", function () { ...@@ -3717,7 +3716,7 @@ describe("Groupchats", function () {
expect(view.validateRoleOrAffiliationChangeArgs.calls.count()).toBe(2); expect(view.validateRoleOrAffiliationChangeArgs.calls.count()).toBe(2);
expect(view.model.setRole).toHaveBeenCalled(); expect(view.model.setRole).toHaveBeenCalled();
expect(sent_IQ.toLocaleString()).toBe( expect(Strophe.serialize(sent_IQ)).toBe(
`<iq id="${IQ_id}" to="lounge@montague.lit" type="set" xmlns="jabber:client">`+ `<iq id="${IQ_id}" to="lounge@montague.lit" type="set" xmlns="jabber:client">`+
`<query xmlns="http://jabber.org/protocol/muc#admin">`+ `<query xmlns="http://jabber.org/protocol/muc#admin">`+
`<item nick="trustworthyguy" role="moderator">`+ `<item nick="trustworthyguy" role="moderator">`+
...@@ -3761,7 +3760,7 @@ describe("Groupchats", function () { ...@@ -3761,7 +3760,7 @@ describe("Groupchats", function () {
expect(view.validateRoleOrAffiliationChangeArgs.calls.count()).toBe(3); expect(view.validateRoleOrAffiliationChangeArgs.calls.count()).toBe(3);
expect(view.model.setRole).toHaveBeenCalled(); expect(view.model.setRole).toHaveBeenCalled();
expect(sent_IQ.toLocaleString()).toBe( expect(Strophe.serialize(sent_IQ)).toBe(
`<iq id="${IQ_id}" to="lounge@montague.lit" type="set" xmlns="jabber:client">`+ `<iq id="${IQ_id}" to="lounge@montague.lit" type="set" xmlns="jabber:client">`+
`<query xmlns="http://jabber.org/protocol/muc#admin">`+ `<query xmlns="http://jabber.org/protocol/muc#admin">`+
`<item nick="trustworthyguy" role="participant">`+ `<item nick="trustworthyguy" role="participant">`+
...@@ -3857,7 +3856,7 @@ describe("Groupchats", function () { ...@@ -3857,7 +3856,7 @@ describe("Groupchats", function () {
expect(view.validateRoleOrAffiliationChangeArgs.calls.count()).toBe(2); expect(view.validateRoleOrAffiliationChangeArgs.calls.count()).toBe(2);
expect(view.model.setRole).toHaveBeenCalled(); expect(view.model.setRole).toHaveBeenCalled();
expect(sent_IQ.toLocaleString()).toBe( expect(Strophe.serialize(sent_IQ)).toBe(
`<iq id="${IQ_id}" to="lounge@montague.lit" type="set" xmlns="jabber:client">`+ `<iq id="${IQ_id}" to="lounge@montague.lit" type="set" xmlns="jabber:client">`+
`<query xmlns="http://jabber.org/protocol/muc#admin">`+ `<query xmlns="http://jabber.org/protocol/muc#admin">`+
`<item nick="annoyingGuy" role="visitor">`+ `<item nick="annoyingGuy" role="visitor">`+
...@@ -3898,7 +3897,7 @@ describe("Groupchats", function () { ...@@ -3898,7 +3897,7 @@ describe("Groupchats", function () {
expect(view.validateRoleOrAffiliationChangeArgs.calls.count()).toBe(3); expect(view.validateRoleOrAffiliationChangeArgs.calls.count()).toBe(3);
expect(view.model.setRole).toHaveBeenCalled(); expect(view.model.setRole).toHaveBeenCalled();
expect(sent_IQ.toLocaleString()).toBe( expect(Strophe.serialize(sent_IQ)).toBe(
`<iq id="${IQ_id}" to="lounge@montague.lit" type="set" xmlns="jabber:client">`+ `<iq id="${IQ_id}" to="lounge@montague.lit" type="set" xmlns="jabber:client">`+
`<query xmlns="http://jabber.org/protocol/muc#admin">`+ `<query xmlns="http://jabber.org/protocol/muc#admin">`+
`<item nick="annoyingGuy" role="participant">`+ `<item nick="annoyingGuy" role="participant">`+
......
/*global mock */ /*global mock, converse */
// See: https://xmpp.org/rfcs/rfc3921.html // See: https://xmpp.org/rfcs/rfc3921.html
const Strophe = converse.env.Strophe;
describe("The Protocol", function () { describe("The Protocol", function () {
describe("Integration of Roster Items and Presence Subscriptions", function () { describe("Integration of Roster Items and Presence Subscriptions", function () {
...@@ -103,7 +105,7 @@ describe("The Protocol", function () { ...@@ -103,7 +105,7 @@ describe("The Protocol", function () {
*/ */
await mock.waitForRoster(_converse, 'all', 0); await mock.waitForRoster(_converse, 'all', 0);
expect(_converse.roster.sendContactAddIQ).toHaveBeenCalled(); expect(_converse.roster.sendContactAddIQ).toHaveBeenCalled();
expect(sent_stanza.toLocaleString()).toBe( expect(Strophe.serialize(sent_stanza)).toBe(
`<iq id="${IQ_id}" type="set" xmlns="jabber:client">`+ `<iq id="${IQ_id}" type="set" xmlns="jabber:client">`+
`<query xmlns="jabber:iq:roster">`+ `<query xmlns="jabber:iq:roster">`+
`<item jid="contact@example.org"/>`+ `<item jid="contact@example.org"/>`+
...@@ -430,7 +432,7 @@ describe("The Protocol", function () { ...@@ -430,7 +432,7 @@ describe("The Protocol", function () {
/* _converse.js will then also automatically remove the /* _converse.js will then also automatically remove the
* contact from the user's roster. * contact from the user's roster.
*/ */
expect(sent_IQ.toLocaleString()).toBe( expect(Strophe.serialize(sent_IQ)).toBe(
`<iq type="set" xmlns="jabber:client">`+ `<iq type="set" xmlns="jabber:client">`+
`<query xmlns="jabber:iq:roster">`+ `<query xmlns="jabber:iq:roster">`+
`<item jid="contact@example.org" subscription="remove"/>`+ `<item jid="contact@example.org" subscription="remove"/>`+
......
/*global mock */ /*global mock, converse */
const $iq = converse.env.$iq; const $iq = converse.env.$iq;
const $pres = converse.env.$pres; const $pres = converse.env.$pres;
...@@ -651,7 +651,7 @@ describe("The Contacts Roster", function () { ...@@ -651,7 +651,7 @@ describe("The Contacts Roster", function () {
await u.waitUntil(() => (sizzle(".pending-contact-name:contains('"+name+"')", _converse.rosterview.el).length === 0), 1000); await u.waitUntil(() => (sizzle(".pending-contact-name:contains('"+name+"')", _converse.rosterview.el).length === 0), 1000);
expect(window.confirm).toHaveBeenCalled(); expect(window.confirm).toHaveBeenCalled();
expect(contact.removeFromRoster).toHaveBeenCalled(); expect(contact.removeFromRoster).toHaveBeenCalled();
expect(sent_IQ.toLocaleString()).toBe( expect(Strophe.serialize(sent_IQ)).toBe(
`<iq type="set" xmlns="jabber:client">`+ `<iq type="set" xmlns="jabber:client">`+
`<query xmlns="jabber:iq:roster">`+ `<query xmlns="jabber:iq:roster">`+
`<item jid="lord.capulet@montague.lit" subscription="remove"/>`+ `<item jid="lord.capulet@montague.lit" subscription="remove"/>`+
...@@ -829,7 +829,7 @@ describe("The Contacts Roster", function () { ...@@ -829,7 +829,7 @@ describe("The Contacts Roster", function () {
}); });
sizzle(`.remove-xmpp-contact[title="Click to remove ${name} as a contact"]`, _converse.rosterview.el).pop().click(); sizzle(`.remove-xmpp-contact[title="Click to remove ${name} as a contact"]`, _converse.rosterview.el).pop().click();
expect(window.confirm).toHaveBeenCalled(); expect(window.confirm).toHaveBeenCalled();
expect(sent_IQ.toLocaleString()).toBe( expect(Strophe.serialize(sent_IQ)).toBe(
`<iq type="set" xmlns="jabber:client">`+ `<iq type="set" xmlns="jabber:client">`+
`<query xmlns="jabber:iq:roster"><item jid="mercutio@montague.lit" subscription="remove"/></query>`+ `<query xmlns="jabber:iq:roster"><item jid="mercutio@montague.lit" subscription="remove"/></query>`+
`</iq>`); `</iq>`);
......
...@@ -209,6 +209,10 @@ export const _converse = { ...@@ -209,6 +209,10 @@ export const _converse = {
OPENED: 'opened', OPENED: 'opened',
PREBIND: 'prebind', PREBIND: 'prebind',
/**
* @constant
* @type { integer }
*/
STANZA_TIMEOUT: 10000, STANZA_TIMEOUT: 10000,
SUCCESS: 'success', SUCCESS: 'success',
...@@ -463,10 +467,10 @@ export const api = _converse.api = { ...@@ -463,10 +467,10 @@ export const api = _converse.api = {
* A hook is a special kind of event which allows you to intercept a data * A hook is a special kind of event which allows you to intercept a data
* structure in order to modify it, before passing it back. * structure in order to modify it, before passing it back.
* @async * @async
* @method _converse.api.hook
* @param {string} name - The hook name * @param {string} name - The hook name
* @param {...any} context - The context to which the hook applies (could be for example, a {@link _converse.ChatBox)). * @param {...any} context - The context to which the hook applies (could be for example, a {@link _converse.ChatBox)).
* @param {...any} data - The data structure to be intercepted and modified by the hook listeners. * @param {...any} data - The data structure to be intercepted and modified by the hook listeners.
* @returns {Promise<any>} - A promise that resolves with the modified data structure.
*/ */
hook (name, context, data) { hook (name, context, data) {
const events = _converse._events[name] || []; const events = _converse._events[name] || [];
...@@ -516,6 +520,7 @@ export const api = _converse.api = { ...@@ -516,6 +520,7 @@ export const api = _converse.api = {
* initialized. It's used together with the `auto_login` configuration flag * initialized. It's used together with the `auto_login` configuration flag
* to determine whether Converse should try to log the user in if it * to determine whether Converse should try to log the user in if it
* fails to restore a previous auth'd session. * fails to restore a previous auth'd session.
* @returns {void}
*/ */
async login (jid, password, automatic=false) { async login (jid, password, automatic=false) {
jid = jid || _converse.jid; jid = jid || _converse.jid;
...@@ -879,6 +884,8 @@ export const api = _converse.api = { ...@@ -879,6 +884,8 @@ export const api = _converse.api = {
/** /**
* Allows you to send XML stanzas. * Allows you to send XML stanzas.
* @method _converse.api.send * @method _converse.api.send
* @param {XMLElement} stanza
* @return {void}
* @example * @example
* const msg = converse.env.$msg({ * const msg = converse.env.$msg({
* 'from': 'juliet@example.com/balcony', * 'from': 'juliet@example.com/balcony',
...@@ -905,29 +912,37 @@ export const api = _converse.api = { ...@@ -905,29 +912,37 @@ export const api = _converse.api = {
}, },
/** /**
* Send an IQ stanza and receive a promise * Send an IQ stanza
* @method _converse.api.sendIQ * @method _converse.api.sendIQ
* @param { XMLElement } stanza * @param {XMLElement} stanza
* @param { Integer } timeout * @param {Integer} [timeout=_converse.STANZA_TIMEOUT]
* @param { Boolean } reject - Whether an error IQ should cause the promise * @param {Boolean} [reject=true] - Whether an error IQ should cause the promise
* to be rejected. If `false`, the promise will resolve instead of being rejected. * to be rejected. If `false`, the promise will resolve instead of being rejected.
* @returns {Promise} A promise which resolves when we receive a `result` stanza * @returns {Promise} A promise which resolves (or potentially rejected) once we
* or is rejected when we receive an `error` stanza. * receive a `result` or `error` stanza or once a timeout is reached.
* If the IQ stanza being sent is of type `result` or `error`, there's
* nothing to wait for, so an already resolved promise is returned.
*/ */
sendIQ (stanza, timeout, reject=true) { sendIQ (stanza, timeout=_converse.STANZA_TIMEOUT, reject=true) {
timeout = timeout || _converse.STANZA_TIMEOUT;
let promise; let promise;
if (reject) { stanza = stanza?.nodeTree ?? stanza;
promise = new Promise((resolve, reject) => _converse.connection.sendIQ(stanza, resolve, reject, timeout)); if (['get', 'set'].includes(stanza.getAttribute('type'))) {
promise.catch(e => { timeout = timeout || _converse.STANZA_TIMEOUT;
if (e === null) { if (reject) {
throw new TimeoutError( promise = new Promise((resolve, reject) => _converse.connection.sendIQ(stanza, resolve, reject, timeout));
`Timeout error after ${timeout}ms for the following IQ stanza: ${Strophe.serialize(stanza)}` promise.catch(e => {
); if (e === null) {
} throw new TimeoutError(
}); `Timeout error after ${timeout}ms for the following IQ stanza: ${Strophe.serialize(stanza)}`
);
}
});
} else {
promise = new Promise(resolve => _converse.connection.sendIQ(stanza, resolve, resolve, timeout));
}
} else { } else {
promise = new Promise(resolve => _converse.connection.sendIQ(stanza, resolve, resolve, timeout)); _converse.connection.sendIQ(stanza);
promise = new Promise.resolve();
} }
api.trigger('send', stanza); api.trigger('send', stanza);
return promise; return promise;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment