Fix more tests

This commit is contained in:
JC Brand 2021-01-29 14:15:27 +01:00
parent 22b6b4b502
commit f33fa1e9fc
14 changed files with 179 additions and 265 deletions

View File

@ -25,48 +25,49 @@ module.exports = function(config) {
{ pattern: "node_modules/sinon/pkg/sinon.js", type: 'module' },
{ pattern: "spec/mock.js", type: 'module' },
// { pattern: "spec/user-details-modal.js", type: 'module' },
// { pattern: "spec/spoilers.js", type: 'module' },
// { pattern: "spec/emojis.js", type: 'module' },
// { pattern: "spec/muclist.js", type: 'module' },
// { pattern: "spec/converse.js", type: 'module' },
// { pattern: "spec/bookmarks.js", type: 'module' },
// { pattern: "spec/headline.js", type: 'module' },
// { pattern: "spec/disco.js", type: 'module' },
// { pattern: "spec/protocol.js", type: 'module' },
// { pattern: "spec/presence.js", type: 'module' },
// { pattern: "spec/eventemitter.js", type: 'module' },
// { pattern: "spec/smacks.js", type: 'module' },
// { pattern: "spec/ping.js", type: 'module' },
// { pattern: "spec/push.js", type: 'module' },
// { pattern: "spec/xmppstatus.js", type: 'module' },
// { pattern: "spec/mam.js", type: 'module' },
// { pattern: "spec/omemo.js", type: 'module' },
// { pattern: "spec/controlbox.js", type: 'module' },
// { pattern: "spec/roster.js", type: 'module' },
{ pattern: "spec/user-details-modal.js", type: 'module' },
{ pattern: "spec/spoilers.js", type: 'module' },
{ pattern: "spec/emojis.js", type: 'module' },
{ pattern: "spec/muclist.js", type: 'module' },
{ pattern: "spec/utils.js", type: 'module' },
{ pattern: "spec/converse.js", type: 'module' },
{ pattern: "spec/bookmarks.js", type: 'module' },
{ pattern: "spec/headline.js", type: 'module' },
{ pattern: "spec/disco.js", type: 'module' },
{ pattern: "spec/protocol.js", type: 'module' },
{ pattern: "spec/presence.js", type: 'module' },
{ pattern: "spec/eventemitter.js", type: 'module' },
{ pattern: "spec/smacks.js", type: 'module' },
{ pattern: "spec/ping.js", type: 'module' },
{ pattern: "spec/push.js", type: 'module' },
{ pattern: "spec/xmppstatus.js", type: 'module' },
{ pattern: "spec/mam.js", type: 'module' },
{ pattern: "spec/omemo.js", type: 'module' },
{ pattern: "spec/controlbox.js", type: 'module' },
{ pattern: "spec/roster.js", type: 'module' },
{ pattern: "spec/chatbox.js", type: 'module' },
// { pattern: "spec/messages.js", type: 'module' },
// { pattern: "spec/corrections.js", type: 'module' },
// { pattern: "spec/styling.js", type: 'module' },
// { pattern: "spec/receipts.js", type: 'module' },
// { pattern: "spec/markers.js", type: 'module' },
// { pattern: "spec/rai.js", type: 'module' },
// { pattern: "spec/muc_messages.js", type: 'module' },
// { pattern: "spec/muc-mentions.js", type: 'module' },
// { pattern: "spec/me-messages.js", type: 'module' },
// { pattern: "spec/mentions.js", type: 'module' },
// { pattern: "spec/retractions.js", type: 'module' },
// { pattern: "spec/muc.js", type: 'module' },
// { pattern: "spec/modtools.js", type: 'module' },
// { pattern: "spec/room_registration.js", type: 'module' },
// { pattern: "spec/autocomplete.js", type: 'module' },
// { pattern: "spec/minchats.js", type: 'module' },
// { pattern: "spec/notification.js", type: 'module' },
// { pattern: "spec/login.js", type: 'module' },
// { pattern: "spec/register.js", type: 'module' },
// { pattern: "spec/hats.js", type: 'module' },
// { pattern: "spec/http-file-upload.js", type: 'module' },
// { pattern: "spec/xss.js", type: 'module' }
{ pattern: "spec/messages.js", type: 'module' },
{ pattern: "spec/corrections.js", type: 'module' },
{ pattern: "spec/styling.js", type: 'module' },
{ pattern: "spec/receipts.js", type: 'module' },
{ pattern: "spec/markers.js", type: 'module' },
{ pattern: "spec/rai.js", type: 'module' },
{ pattern: "spec/muc_messages.js", type: 'module' },
{ pattern: "spec/muc-mentions.js", type: 'module' },
{ pattern: "spec/me-messages.js", type: 'module' },
{ pattern: "spec/mentions.js", type: 'module' },
{ pattern: "spec/retractions.js", type: 'module' },
{ pattern: "spec/muc.js", type: 'module' },
{ pattern: "spec/modtools.js", type: 'module' },
{ pattern: "spec/room_registration.js", type: 'module' },
{ pattern: "spec/autocomplete.js", type: 'module' },
{ pattern: "spec/minchats.js", type: 'module' },
{ pattern: "spec/notification.js", type: 'module' },
{ pattern: "spec/login.js", type: 'module' },
{ pattern: "spec/register.js", type: 'module' },
{ pattern: "spec/hats.js", type: 'module' },
{ pattern: "spec/http-file-upload.js", type: 'module' },
{ pattern: "spec/xss.js", type: 'module' }
],
proxies: {

View File

@ -8,9 +8,8 @@ const u = converse.env.utils;
describe("The nickname autocomplete feature", function () {
it("shows all autocompletion options when the user presses @",
mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {},
async function (done, _converse) {
mock.initConverse(['chatBoxesFetched'], {},
async function (done, _converse) {
await mock.openAndEnterChatRoom(_converse, 'lounge@montague.lit', 'tom');
const view = _converse.chatboxviews.get('lounge@montague.lit');
@ -62,9 +61,8 @@ describe("The nickname autocomplete feature", function () {
}));
it("shows all autocompletion options when the user presses @ right after a new line",
mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {},
async function (done, _converse) {
mock.initConverse(['chatBoxesFetched'], {},
async function (done, _converse) {
await mock.openAndEnterChatRoom(_converse, 'lounge@montague.lit', 'tom');
const view = _converse.chatboxviews.get('lounge@montague.lit');
@ -118,8 +116,8 @@ describe("The nickname autocomplete feature", function () {
it("shows all autocompletion options when the user presses @ right after an allowed character",
mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {'opening_mention_characters':['(']},
async function (done, _converse) {
['chatBoxesFetched'], {'opening_mention_characters':['(']},
async function (done, _converse) {
await mock.openAndEnterChatRoom(_converse, 'lounge@montague.lit', 'tom');
const view = _converse.chatboxviews.get('lounge@montague.lit');
@ -172,7 +170,7 @@ describe("The nickname autocomplete feature", function () {
}));
it("should order by query index position and length", mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {}, async function (done, _converse) {
['chatBoxesFetched'], {}, async function (done, _converse) {
await mock.openAndEnterChatRoom(_converse, 'lounge@montague.lit', 'tom');
const view = _converse.chatboxviews.get('lounge@montague.lit');
@ -219,9 +217,7 @@ describe("The nickname autocomplete feature", function () {
}));
it("autocompletes when the user presses tab",
mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {},
async function (done, _converse) {
mock.initConverse(['chatBoxesFetched'], {}, async function (done, _converse) {
await mock.openAndEnterChatRoom(_converse, 'lounge@montague.lit', 'romeo');
const view = _converse.chatboxviews.get('lounge@montague.lit');
@ -331,9 +327,7 @@ describe("The nickname autocomplete feature", function () {
}));
it("autocompletes when the user presses backspace",
mock.initConverse(
['rosterContactsFetched'], {},
async function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
await mock.openAndEnterChatRoom(_converse, 'lounge@montague.lit', 'romeo');
const view = _converse.chatboxviews.get('lounge@montague.lit');

View File

@ -394,10 +394,10 @@ describe("Chatboxes", function () {
await u.waitUntil(() => rosterview.querySelectorAll('.roster-group').length);
await mock.openChatBoxFor(_converse, contact_jid);
const view = _converse.chatboxviews.get(contact_jid);
view.model.minimize();
_converse.minimize.minimize(view.model);
expect(view.model.get('chat_state')).toBe('inactive');
spyOn(_converse.connection, 'send');
view.model.maximize();
_converse.minimize.maximize(view.model);
await u.waitUntil(() => view.model.get('chat_state') === 'active', 1000);
expect(_converse.connection.send).toHaveBeenCalled();
const calls = _.filter(_converse.connection.send.calls.all(), function (call) {
@ -750,7 +750,7 @@ describe("Chatboxes", function () {
await mock.openChatBoxFor(_converse, contact_jid);
const view = _converse.chatboxviews.get(contact_jid);
spyOn(_converse.connection, 'send');
view.minimize();
_converse.minimize.minimize(view.model);
expect(view.model.get('chat_state')).toBe('inactive');
expect(_converse.connection.send).toHaveBeenCalled();
var stanza = _converse.connection.send.calls.argsFor(0)[0].tree();
@ -1125,8 +1125,7 @@ describe("Chatboxes", function () {
await u.waitUntil(() => rosterview.querySelectorAll('.roster-group').length, 500);
await mock.openChatBoxFor(_converse, sender_jid);
const chatbox = _converse.chatboxes.get(sender_jid);
var chatboxview = _converse.chatboxviews.get(sender_jid);
chatboxview.minimize();
_converse.minimize.minimize(chatbox);
msg = mock.createChatMessage(_converse, sender_jid, 'This message will be unread');
await _converse.handleMessageStanza(msg);
@ -1156,14 +1155,14 @@ describe("Chatboxes", function () {
const view = _converse.chatboxviews.get(sender_jid);
const selector = 'a.open-chat:contains("' + chatbox.get('nickname') + '") .msgs-indicator';
const select_msgs_indicator = () => sizzle(selector, rosterview.el).pop();
view.minimize();
_converse.minimize.minimize(view.model);
_converse.handleMessageStanza(msgFactory());
await u.waitUntil(() => chatbox.messages.length);
expect(select_msgs_indicator().textContent).toBe('1');
_converse.handleMessageStanza(msgFactory());
await u.waitUntil(() => chatbox.messages.length > 1);
expect(select_msgs_indicator().textContent).toBe('2');
view.model.maximize();
_converse.minimize.minimize(view.model);
u.waitUntil(() => typeof select_msgs_indicator() === 'undefined');
done();
}));

View File

@ -1,4 +1,4 @@
/*global mock, converse, _ */
/*global mock, converse */
const $msg = converse.env.$msg;
const u = converse.env.utils;
@ -9,25 +9,19 @@ const sizzle = converse.env.sizzle;
describe("The Controlbox", function () {
it("can be opened by clicking a DOM element with class 'toggle-controlbox'",
mock.initConverse(
['rosterContactsFetched'], {},
function (done, _converse) {
mock.initConverse([], {}, function (done, _converse) {
// This spec will only pass if the controlbox is not currently
// open yet.
let el = document.querySelector("div#controlbox");
expect(_.isElement(el)).toBe(true);
expect(u.isVisible(el)).toBe(false);
spyOn(_converse.controlboxtoggle, 'onClick').and.callThrough();
spyOn(_converse.controlboxtoggle, 'showControlBox').and.callThrough();
const toggle = document.querySelector('converse-controlbox-toggle');
spyOn(toggle, 'onClick').and.callThrough();
spyOn(toggle, 'showControlBox').and.callThrough();
spyOn(_converse.api, "trigger").and.callThrough();
// Redelegate so that the spies are now registered as the event handlers (specifically for 'onClick')
_converse.controlboxtoggle.delegateEvents();
toggle.delegateEvents();
document.querySelector('.toggle-controlbox').click();
expect(_converse.controlboxtoggle.onClick).toHaveBeenCalled();
expect(_converse.controlboxtoggle.showControlBox).toHaveBeenCalled();
expect(toggle.onClick).toHaveBeenCalled();
expect(toggle.showControlBox).toHaveBeenCalled();
expect(_converse.api.trigger).toHaveBeenCalledWith('controlBoxOpened', jasmine.any(Object));
el = document.querySelector("div#controlbox");
const el = document.querySelector("#controlbox");
expect(u.isVisible(el)).toBe(true);
done();
}));
@ -37,18 +31,17 @@ describe("The Controlbox", function () {
mock.initConverse(['chatBoxesFetched'], {}, async function (done, _converse) {
await mock.openControlBox(_converse);
const controlview = _converse.chatboxviews.get('controlbox');
const view = _converse.chatboxviews.get('controlbox');
spyOn(controlview, 'close').and.callThrough();
spyOn(view, 'close').and.callThrough();
spyOn(_converse.api, "trigger").and.callThrough();
// We need to rebind all events otherwise our spy won't be called
controlview.delegateEvents();
view.delegateEvents();
controlview.querySelector('.close-chatbox-button').click();
expect(controlview.close).toHaveBeenCalled();
await new Promise(resolve => _converse.api.listen.once('chatBoxClosed', resolve));
expect(_converse.api.trigger).toHaveBeenCalledWith('chatBoxClosed', jasmine.any(Object));
view.querySelector('.close-chatbox-button').click();
expect(view.close).toHaveBeenCalled();
expect(_converse.api.trigger).toHaveBeenCalledWith('controlBoxClosed', jasmine.any(Object));
done();
}));
@ -56,12 +49,10 @@ describe("The Controlbox", function () {
describe("The \"Contacts\" section", function () {
it("can be used to add contact and it checks for case-sensivity",
mock.initConverse(
['rosterContactsFetched'], {},
async function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
spyOn(_converse.api, "trigger").and.callThrough();
spyOn(_converse.rosterview, 'update').and.callThrough();
await mock.waitForRoster(_converse, 'all', 0);
await mock.openControlBox(_converse);
// Adding two contacts one with Capital initials and one with small initials of same JID (Case sensitive check)
_converse.roster.create({
@ -76,17 +67,15 @@ describe("The Controlbox", function () {
ask: 'subscribe',
fullname: mock.pend_names[0]
});
await u.waitUntil(() => _.filter(_converse.rosterview.querySelectorAll('.roster-group li'), u.isVisible).length, 700);
const rosterview = document.querySelector('converse-roster');
await u.waitUntil(() => Array.from(rosterview.querySelectorAll('.roster-group li')).filter(u.isVisible).length, 700);
// Checking that only one entry is created because both JID is same (Case sensitive check)
expect(_.filter(_converse.rosterview.querySelectorAll('li'), u.isVisible).length).toBe(1);
expect(_converse.rosterview.update).toHaveBeenCalled();
expect(Array.from(rosterview.querySelectorAll('li')).filter(u.isVisible).length).toBe(1);
done();
}));
it("shows the number of unread mentions received",
mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {},
async function (done, _converse) {
mock.initConverse(['chatBoxesFetched'], {}, async function (done, _converse) {
await mock.waitForRoster(_converse, 'all');
await mock.openControlBox(_converse);
@ -97,8 +86,10 @@ describe("The Controlbox", function () {
const chatview = _converse.chatboxviews.get(sender_jid);
chatview.model.set({'minimized': true});
expect(_converse.chatboxviews.el.querySelector('.restore-chat .message-count') === null).toBeTruthy();
expect(_converse.rosterview.querySelector('.msgs-indicator') === null).toBeTruthy();
const el = document.querySelector('converse-chats');
expect(el.querySelector('.restore-chat .message-count') === null).toBeTruthy();
const rosterview = document.querySelector('converse-roster');
expect(rosterview.querySelector('.msgs-indicator') === null).toBeTruthy();
let msg = $msg({
from: sender_jid,
@ -108,10 +99,10 @@ describe("The Controlbox", function () {
}).c('body').t('hello').up()
.c('active', {'xmlns': 'http://jabber.org/protocol/chatstates'}).tree();
_converse.handleMessageStanza(msg);
await u.waitUntil(() => _converse.rosterview.querySelectorAll(".msgs-indicator").length);
await u.waitUntil(() => rosterview.querySelectorAll(".msgs-indicator").length);
spyOn(chatview.model, 'handleUnreadMessage').and.callThrough();
await u.waitUntil(() => _converse.chatboxviews.el.querySelector('.restore-chat .message-count')?.textContent === '1');
expect(_converse.rosterview.querySelector('.msgs-indicator').textContent).toBe('1');
await u.waitUntil(() => el.querySelector('.restore-chat .message-count')?.textContent === '1');
expect(rosterview.querySelector('.msgs-indicator').textContent).toBe('1');
msg = $msg({
from: sender_jid,
@ -122,11 +113,11 @@ describe("The Controlbox", function () {
.c('active', {'xmlns': 'http://jabber.org/protocol/chatstates'}).tree();
_converse.handleMessageStanza(msg);
await u.waitUntil(() => chatview.model.handleUnreadMessage.calls.count());
await u.waitUntil(() => _converse.chatboxviews.el.querySelector('.restore-chat .message-count')?.textContent === '2');
expect(_converse.rosterview.querySelector('.msgs-indicator').textContent).toBe('2');
await u.waitUntil(() => el.querySelector('.restore-chat .message-count')?.textContent === '2');
expect(rosterview.querySelector('.msgs-indicator').textContent).toBe('2');
chatview.model.set({'minimized': false});
expect(_converse.chatboxviews.el.querySelector('.restore-chat .message-count')).toBe(null);
await u.waitUntil(() => _converse.rosterview.querySelector('.msgs-indicator') === null);
await u.waitUntil(() => rosterview.querySelector('.msgs-indicator') === null);
done();
}));
});
@ -134,28 +125,22 @@ describe("The Controlbox", function () {
describe("The Status Widget", function () {
it("shows the user's chat status, which is online by default",
mock.initConverse(
['rosterContactsFetched'], {},
function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
mock.openControlBox(_converse);
var view = _converse.xmppstatusview;
const view = await u.waitUntil(() => document.querySelector('converse-user-profile'));
expect(u.hasClass('online', view.querySelector('.xmpp-status span:first-child'))).toBe(true);
expect(view.querySelector('.xmpp-status span.online').textContent.trim()).toBe('I am online');
done();
}));
it("can be used to set the current user's chat status",
mock.initConverse(
['rosterContactsFetched'], {},
async function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
await mock.openControlBox(_converse);
var cbview = _converse.chatboxviews.get('controlbox');
cbview.querySelector('.change-status').click()
const modal = _converse.api.modal.get('modal-status-change');
await u.waitUntil(() => u.isVisible(modal.el), 1000);
const view = _converse.xmppstatusview;
modal.el.querySelector('label[for="radio-busy"]').click(); // Change status to "dnd"
modal.el.querySelector('[type="submit"]').click();
const sent_stanzas = _converse.connection.sent_stanzas;
@ -166,6 +151,7 @@ describe("The Controlbox", function () {
`<priority>0</priority>`+
`<c hash="sha-1" node="https://conversejs.org" ver="PxXfr6uz8ClMWIga0OB/MhKNH/M=" xmlns="http://jabber.org/protocol/caps"/>`+
`</presence>`);
const view = await u.waitUntil(() => document.querySelector('converse-user-profile'));
const first_child = view.querySelector('.xmpp-status span:first-child');
expect(u.hasClass('online', first_child)).toBe(false);
expect(u.hasClass('dnd', first_child)).toBe(true);
@ -174,9 +160,7 @@ describe("The Controlbox", function () {
}));
it("can be used to set a custom status message",
mock.initConverse(
['rosterContactsFetched'], {},
async function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
await mock.openControlBox(_converse);
const cbview = _converse.chatboxviews.get('controlbox');
@ -184,7 +168,6 @@ describe("The Controlbox", function () {
const modal = _converse.api.modal.get('modal-status-change');
await u.waitUntil(() => u.isVisible(modal.el), 1000);
const view = _converse.xmppstatusview;
const msg = 'I am happy';
modal.el.querySelector('input[name="status_message"]').value = msg;
modal.el.querySelector('[type="submit"]').click();
@ -197,6 +180,7 @@ describe("The Controlbox", function () {
`<c hash="sha-1" node="https://conversejs.org" ver="PxXfr6uz8ClMWIga0OB/MhKNH/M=" xmlns="http://jabber.org/protocol/caps"/>`+
`</presence>`);
const view = await u.waitUntil(() => document.querySelector('converse-user-profile'));
const first_child = view.querySelector('.xmpp-status span:first-child');
expect(u.hasClass('online', first_child)).toBe(true);
expect(view.querySelector('.xmpp-status span:first-child').textContent.trim()).toBe(msg);
@ -208,9 +192,7 @@ describe("The Controlbox", function () {
describe("The 'Add Contact' widget", function () {
it("opens up an add modal when you click on it",
mock.initConverse(
['rosterContactsFetched'], {},
async function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
await mock.waitForRoster(_converse, 'all');
await mock.openControlBox(_converse);
@ -242,9 +224,7 @@ describe("The 'Add Contact' widget", function () {
}));
it("can be configured to not provide search suggestions",
mock.initConverse(
['rosterContactsFetched'], {'autocomplete_add_contact': false},
async function (done, _converse) {
mock.initConverse([], {'autocomplete_add_contact': false}, async function (done, _converse) {
await mock.waitForRoster(_converse, 'all', 0);
mock.openControlBox(_converse);
@ -274,9 +254,7 @@ describe("The 'Add Contact' widget", function () {
it("integrates with xhr_user_search_url to search for contacts",
mock.initConverse(
['rosterContactsFetched'],
{ 'xhr_user_search_url': 'http://example.org/?' },
mock.initConverse([], { 'xhr_user_search_url': 'http://example.org/?' },
async function (done, _converse) {
await mock.waitForRoster(_converse, 'all', 0);
@ -330,8 +308,7 @@ describe("The 'Add Contact' widget", function () {
}));
it("can be configured to not provide search suggestions for XHR search results",
mock.initConverse(
['rosterContactsFetched'],
mock.initConverse([],
{ 'autocomplete_add_contact': false,
'xhr_user_search_url': 'http://example.org/?' },
async function (done, _converse) {

View File

@ -1,14 +1,11 @@
/*global mock */
/*global mock, converse */
const u = converse.env.utils;
describe("A XEP-0317 MUC Hat", function () {
it("can be included in a presence stanza",
mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {},
async function (done, _converse) {
mock.initConverse(['chatBoxesFetched'], {}, async function (done, _converse) {
const muc_jid = 'lounge@montague.lit';
await mock.openAndEnterChatRoom(_converse, muc_jid, 'romeo');
const view = _converse.chatboxviews.get(muc_jid);

View File

@ -9,10 +9,7 @@ describe("XEP-0363: HTTP File Upload", function () {
describe("Discovering support", function () {
it("is done automatically",
mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {},
async function (done, _converse) {
it("is done automatically", mock.initConverse(['chatBoxesFetched'], {}, async function (done, _converse) {
const IQ_stanzas = _converse.connection.IQ_stanzas;
await mock.waitUntilDiscoConfirmed(_converse, _converse.bare_jid, [], []);
let selector = 'iq[to="montague.lit"] query[xmlns="http://jabber.org/protocol/disco#info"]';
@ -162,10 +159,7 @@ describe("XEP-0363: HTTP File Upload", function () {
done();
}));
it("does not appear in MUC chats", mock.initConverse(
['rosterContactsFetched'], {},
async (done, _converse) => {
it("does not appear in MUC chats", mock.initConverse([], {}, async (done, _converse) => {
await mock.openAndEnterChatRoom(_converse, 'lounge@montague.lit', 'romeo');
mock.waitUntilDiscoConfirmed(
_converse, _converse.domain,
@ -203,10 +197,7 @@ describe("XEP-0363: HTTP File Upload", function () {
done();
}));
it("appears in MUC chats", mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {},
async (done, _converse) => {
it("appears in MUC chats", mock.initConverse(['chatBoxesFetched'], {}, async (done, _converse) => {
await mock.waitUntilDiscoConfirmed(
_converse, _converse.domain,
[{'category': 'server', 'type':'IM'}],
@ -215,7 +206,7 @@ describe("XEP-0363: HTTP File Upload", function () {
await mock.waitUntilDiscoConfirmed(_converse, _converse.domain, [], [], ['upload.montague.lit'], 'items');
await mock.waitUntilDiscoConfirmed(_converse, 'upload.montague.lit', [], [Strophe.NS.HTTPUPLOAD], []);
await mock.openAndEnterChatRoom(_converse, 'lounge@montague.lit', 'romeo');
await u.waitUntil(() => _converse.chatboxviews.get('lounge@montague.lit').el.querySelector('.fileupload'));
await u.waitUntil(() => _converse.chatboxviews.get('lounge@montague.lit').querySelector('.fileupload'));
const view = _converse.chatboxviews.get('lounge@montague.lit');
expect(view.querySelector('.chat-toolbar .fileupload')).not.toBe(null);
done();
@ -223,9 +214,7 @@ describe("XEP-0363: HTTP File Upload", function () {
describe("when clicked and a file chosen", function () {
it("is uploaded and sent out", mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {} ,async (done, _converse) => {
it("is uploaded and sent out", mock.initConverse(['chatBoxesFetched'], {} ,async (done, _converse) => {
const base_url = 'https://conversejs.org';
await mock.waitUntilDiscoConfirmed(
_converse, _converse.domain,
@ -560,10 +549,7 @@ describe("XEP-0363: HTTP File Upload", function () {
describe("While a file is being uploaded", function () {
it("shows a progress bar", mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {},
async function (done, _converse) {
it("shows a progress bar", mock.initConverse(['chatBoxesFetched'], {}, async function (done, _converse) {
await mock.waitUntilDiscoConfirmed(
_converse, _converse.domain,
[{'category': 'server', 'type':'IM'}],

View File

@ -148,7 +148,6 @@ describe("A Chatbox", function () {
spyOn(_converse.minimize, 'trimChats');
await mock.waitForRoster(_converse, 'current');
await mock.openControlBox(_converse);
expect(_converse.minimize.trimChats.calls.count()).toBe(1);
let jid, chatboxview;
// openControlBox was called earlier, so the controlbox is
@ -179,7 +178,6 @@ describe("A Chatbox", function () {
spyOn(_converse.minimize, 'maximize').and.callThrough();
const minimized_chats = document.querySelector("converse-minimized-chats")
minimized_chats.querySelector("a.restore-chat").click();
expect(_converse.minimize.maximize).toHaveBeenCalled();
expect(_converse.minimize.trimChats.calls.count()).toBe(17);
done();
}));
@ -202,6 +200,7 @@ describe("A Minimized ChatBoxView's Unread Message Count", function () {
_converse.handleMessageStanza(msgFactory());
await u.waitUntil(() => chatbox.messages.length);
const view = _converse.chatboxviews.get(sender_jid);
expect(view.model.get('num_unread')).toBe(1);
_converse.minimize.minimize(view.model);
const unread_count = selectUnreadMsgCount();
expect(u.isVisible(unread_count)).toBeTruthy();

View File

@ -148,9 +148,7 @@ window.addEventListener('converse-loaded', () => {
const model = await _converse.api.controlbox.open('controlbox');
await u.waitUntil(() => model.get('connected'));
await mock.openControlBox(_converse);
const view = await _converse.chatboxviews.get('controlbox');
const roomspanel = view.roomspanel;
roomspanel.el.querySelector('.show-add-muc-modal').click();
document.querySelector('converse-rooms-list .show-add-muc-modal').click();
mock.closeControlBox(_converse);
const modal = _converse.api.modal.get('add-chatroom-modal');
await u.waitUntil(() => u.isVisible(modal.el), 1500)

View File

@ -21,9 +21,7 @@ async function openModtools (_converse, view) {
describe("The groupchat moderator tool", function () {
it("allows you to set affiliations and roles",
mock.initConverse(
['rosterContactsFetched'], {},
async function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
spyOn(_converse.ChatRoomView.prototype, 'showModeratorToolsModal').and.callThrough();
const muc_jid = 'lounge@montague.lit';
@ -142,9 +140,7 @@ describe("The groupchat moderator tool", function () {
}));
it("allows you to filter affiliation search results",
mock.initConverse(
['rosterContactsFetched'], {},
async function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
spyOn(_converse.ChatRoomView.prototype, 'showModeratorToolsModal').and.callThrough();
const muc_jid = 'lounge@montague.lit';
@ -198,9 +194,7 @@ describe("The groupchat moderator tool", function () {
}));
it("allows you to filter role search results",
mock.initConverse(
['rosterContactsFetched'], {},
async function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
spyOn(_converse.ChatRoomView.prototype, 'showModeratorToolsModal').and.callThrough();
const muc_jid = 'lounge@montague.lit';
@ -309,9 +303,7 @@ describe("The groupchat moderator tool", function () {
}));
it("shows an error message if a particular affiliation list may not be retrieved",
mock.initConverse(
['rosterContactsFetched'], {},
async function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
spyOn(_converse.ChatRoomView.prototype, 'showModeratorToolsModal').and.callThrough();
const muc_jid = 'lounge@montague.lit';
@ -361,9 +353,7 @@ describe("The groupchat moderator tool", function () {
}));
it("shows an error message if a particular affiliation may not be set",
mock.initConverse(
['rosterContactsFetched'], {},
async function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
spyOn(_converse.ChatRoomView.prototype, 'showModeratorToolsModal').and.callThrough();
const muc_jid = 'lounge@montague.lit';
@ -428,9 +418,7 @@ describe("The groupchat moderator tool", function () {
it("doesn't allow admins to make more admins",
mock.initConverse(
['rosterContactsFetched'], {},
async function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
spyOn(_converse.ChatRoomView.prototype, 'showModeratorToolsModal').and.callThrough();
const muc_jid = 'lounge@montague.lit';
@ -465,9 +453,7 @@ describe("The groupchat moderator tool", function () {
}));
it("lets the assignable affiliations and roles be configured via modtools_disable_assign",
mock.initConverse(
['rosterContactsFetched'], {},
async function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
spyOn(_converse.ChatRoomView.prototype, 'showModeratorToolsModal').and.callThrough();
const muc_jid = 'lounge@montague.lit';

View File

@ -13,7 +13,7 @@ describe("Groupchats", function () {
describe("The \"rooms\" API", function () {
fit("has a method 'close' which closes rooms by JID or all rooms when called with no arguments",
it("has a method 'close' which closes rooms by JID or all rooms when called with no arguments",
mock.initConverse([], {}, async function (done, _converse) {
await mock.openAndEnterChatRoom(_converse, 'lounge@montague.lit', 'romeo');
@ -51,7 +51,8 @@ describe("Groupchats", function () {
mock.initConverse([], {}, async function (done, _converse) {
await mock.waitForRoster(_converse, 'current');
await u.waitUntil(() => _converse.rosterview.querySelectorAll('.roster-group .group-toggle').length, 300);
const rosterview = document.querySelector('converse-roster');
await u.waitUntil(() => rosterview.querySelectorAll('.roster-group .group-toggle').length, 300);
let muc_jid = 'chillout@montague.lit';
await mock.openAndEnterChatRoom(_converse, muc_jid, 'romeo');
let room = await _converse.api.rooms.get(muc_jid);
@ -103,7 +104,8 @@ describe("Groupchats", function () {
let chatroomview, IQ_id;
await mock.openControlBox(_converse);
await mock.waitForRoster(_converse, 'current');
await u.waitUntil(() => _converse.rosterview.querySelectorAll('.roster-group .group-toggle').length);
const rosterview = document.querySelector('converse-roster');
await u.waitUntil(() => rosterview.querySelectorAll('.roster-group .group-toggle').length);
let room = await _converse.api.rooms.open(jid);
// Test on groupchat that's not yet open
@ -196,7 +198,7 @@ describe("Groupchats", function () {
expect(_converse.connection.sendIQ).toHaveBeenCalled();
const IQ_stanzas = _converse.connection.IQ_stanzas;
const iq = IQ_stanzas.filter(s => s.querySelector(`query[xmlns="${Strophe.NS.MUC_OWNER}"]`)).pop();
const iq = await u.waitUntil(() => IQ_stanzas.filter(s => s.querySelector(`query[xmlns="${Strophe.NS.MUC_OWNER}"]`)).pop());
expect(Strophe.serialize(iq)).toBe(
`<iq id="${iq.getAttribute('id')}" to="room@conference.example.org" type="get" xmlns="jabber:client">`+
`<query xmlns="http://jabber.org/protocol/muc#owner"/></iq>`);
@ -378,14 +380,14 @@ describe("Groupchats", function () {
'time': '2021-02-02T12:00:00Z'
});
expect(view.model.session.get('connection_status')).toBe(converse.ROOMSTATUS.NICKNAME_REQUIRED);
await u.waitUntil(() => view.el.querySelectorAll('converse-chat-message').length === 1);
await u.waitUntil(() => view.querySelectorAll('converse-chat-message').length === 1);
const sel = 'converse-message-history converse-chat-message .chat-msg__text';
await u.waitUntil(() => view.el.querySelector(sel)?.textContent.trim());
expect(view.el.querySelector(sel).textContent.trim()).toBe('Hello world')
await u.waitUntil(() => view.querySelector(sel)?.textContent.trim());
expect(view.querySelector(sel).textContent.trim()).toBe('Hello world')
view.el.querySelector('[name="nick"]').value = nick;
view.el.querySelector('.muc-nickname-form input[type="submit"]').click();
view.querySelector('[name="nick"]').value = nick;
view.querySelector('.muc-nickname-form input[type="submit"]').click();
_converse.connection.IQ_stanzas = [];
await mock.getRoomFeatures(_converse, muc_jid);
await u.waitUntil(() => view.model.session.get('connection_status') === converse.ROOMSTATUS.CONNECTING);
@ -1432,6 +1434,7 @@ describe("Groupchats", function () {
}));
it("can be configured if you're its owner", mock.initConverse(['chatBoxesFetched'], {}, async function (done, _converse) {
let sent_IQ, IQ_id;
const sendIQ = _converse.connection.sendIQ;
spyOn(_converse.connection, 'sendIQ').and.callFake(function (iq, callback, errback) {
@ -2722,7 +2725,7 @@ describe("Groupchats", function () {
_converse.connection._dataRecv(mock.createRequest(presence));
expect(u.isVisible(view.querySelector('.chat-area'))).toBeFalsy();
await u.waitUntil(() => !u.isVisible(view.querySelector('.chat-area')));
expect(u.isVisible(view.querySelector('.occupants'))).toBeFalsy();
const chat_body = view.querySelector('.chatroom-body');
expect(chat_body.querySelectorAll('.disconnect-msg').length).toBe(3);
@ -2775,7 +2778,7 @@ describe("Groupchats", function () {
_converse.connection._dataRecv(mock.createRequest(presence));
const view = _converse.chatboxviews.get('lounge@montague.lit');
expect(u.isVisible(view.querySelector('.chat-area'))).toBeFalsy();
await u.waitUntil(() => !u.isVisible(view.querySelector('.chat-area')));
expect(u.isVisible(view.querySelector('.occupants'))).toBeFalsy();
const chat_body = view.querySelector('.chatroom-body');
expect(chat_body.querySelectorAll('.disconnect-msg').length).toBe(2);
@ -2815,7 +2818,6 @@ describe("Groupchats", function () {
// only on the right.
expect(_.isEqual(new_attrs.sort(), old_attrs.sort())).toEqual(true);
}
_converse.rosterview.render();
done();
}));
@ -4552,7 +4554,7 @@ describe("Groupchats", function () {
await mock.waitForRoster(_converse, 'current', 0);
const roomspanel = _converse.chatboxviews.get('controlbox').querySelector('converse-rooms-list');
roomspanel.el.querySelector('.show-add-muc-modal').click();
roomspanel.querySelector('.show-add-muc-modal').click();
mock.closeControlBox(_converse);
const modal = _converse.api.modal.get('add-chatroom-modal');
await u.waitUntil(() => u.isVisible(modal.el), 1000)
@ -4577,7 +4579,7 @@ describe("Groupchats", function () {
await u.waitUntil(() => sizzle('.chatroom', _converse.el).filter(u.isVisible).length === 1);
roomspanel.model.set('muc_domain', 'muc.example.org');
roomspanel.el.querySelector('.show-add-muc-modal').click();
roomspanel.querySelector('.show-add-muc-modal').click();
label_name = modal.el.querySelector('label[for="chatroom"]');
expect(label_name.textContent.trim()).toBe('Groupchat address:');
name_input = modal.el.querySelector('input[name="chatroom"]');
@ -4591,7 +4593,7 @@ describe("Groupchats", function () {
await mock.openControlBox(_converse);
await mock.waitForRoster(_converse, 'current', 0);
const roomspanel = _converse.chatboxviews.get('controlbox').querySelector('converse-rooms-list');
roomspanel.el.querySelector('.show-add-muc-modal').click();
roomspanel.querySelector('.show-add-muc-modal').click();
mock.closeControlBox(_converse);
const modal = _converse.api.modal.get('add-chatroom-modal');
await u.waitUntil(() => u.isVisible(modal.el), 1000)
@ -4612,7 +4614,7 @@ describe("Groupchats", function () {
await mock.openControlBox(_converse);
await mock.waitForRoster(_converse, 'current', 0);
const roomspanel = _converse.chatboxviews.get('controlbox').querySelector('converse-rooms-list');
roomspanel.el.querySelector('.show-add-muc-modal').click();
roomspanel.querySelector('.show-add-muc-modal').click();
mock.closeControlBox(_converse);
const modal = _converse.api.modal.get('add-chatroom-modal');
await u.waitUntil(() => u.isVisible(modal.el), 1000)
@ -4629,7 +4631,7 @@ describe("Groupchats", function () {
await mock.openControlBox(_converse);
await mock.waitForRoster(_converse, 'current', 0);
const roomspanel = _converse.chatboxviews.get('controlbox').querySelector('converse-rooms-list');
roomspanel.el.querySelector('.show-add-muc-modal').click();
roomspanel.querySelector('.show-add-muc-modal').click();
mock.closeControlBox(_converse);
const modal = _converse.api.modal.get('add-chatroom-modal');
await u.waitUntil(() => u.isVisible(modal.el), 1000)
@ -4645,7 +4647,7 @@ describe("Groupchats", function () {
await mock.openControlBox(_converse);
const roomspanel = _converse.chatboxviews.get('controlbox').querySelector('converse-rooms-list');
roomspanel.el.querySelector('.show-add-muc-modal').click();
roomspanel.querySelector('.show-add-muc-modal').click();
const modal = _converse.api.modal.get('add-chatroom-modal');
await u.waitUntil(() => u.isVisible(modal.el), 1000)
expect(modal.el.querySelector('.modal-title').textContent.trim()).toBe('Enter a new Groupchat');
@ -4665,7 +4667,7 @@ describe("Groupchats", function () {
expect(_.includes(_converse.chatboxes.models.map(m => m.get('id')), 'lounge@muc.example.org')).toBe(true);
// However, you can still open MUCs with different domains
roomspanel.el.querySelector('.show-add-muc-modal').click();
roomspanel.querySelector('.show-add-muc-modal').click();
await u.waitUntil(() => u.isVisible(modal.el), 1000);
name_input = modal.el.querySelector('input[name="chatroom"]');
name_input.value = 'lounge@conference.example.org';
@ -4684,7 +4686,7 @@ describe("Groupchats", function () {
await mock.openControlBox(_converse);
const roomspanel = _converse.chatboxviews.get('controlbox').querySelector('converse-rooms-list');
roomspanel.el.querySelector('.show-add-muc-modal').click();
roomspanel.querySelector('.show-add-muc-modal').click();
const modal = _converse.api.modal.get('add-chatroom-modal');
await u.waitUntil(() => u.isVisible(modal.el), 1000)
expect(modal.el.querySelector('.modal-title').textContent.trim()).toBe('Enter a new Groupchat');
@ -4703,7 +4705,7 @@ describe("Groupchats", function () {
expect(_.includes(_converse.chatboxes.models.map(m => m.get('id')), 'lounge@muc.example.org')).toBe(true);
// However, you can still open MUCs with different domains
roomspanel.el.querySelector('.show-add-muc-modal').click();
roomspanel.querySelector('.show-add-muc-modal').click();
await u.waitUntil(() => u.isVisible(modal.el), 1000);
name_input = modal.el.querySelector('input[name="chatroom"]');
name_input.value = 'lounge@conference';
@ -4724,7 +4726,7 @@ describe("Groupchats", function () {
await mock.openControlBox(_converse);
const roomspanel = _converse.chatboxviews.get('controlbox').querySelector('converse-rooms-list');
roomspanel.el.querySelector('.show-list-muc-modal').click();
roomspanel.querySelector('.show-list-muc-modal').click();
mock.closeControlBox(_converse);
const modal = _converse.api.modal.get('muc-list-modal');
await u.waitUntil(() => u.isVisible(modal.el), 1000);
@ -4801,7 +4803,7 @@ describe("Groupchats", function () {
await mock.openControlBox(_converse);
const roomspanel = _converse.chatboxviews.get('controlbox').querySelector('converse-rooms-list');
roomspanel.el.querySelector('.show-list-muc-modal').click();
roomspanel.querySelector('.show-list-muc-modal').click();
mock.closeControlBox(_converse);
const modal = _converse.api.modal.get('muc-list-modal');
await u.waitUntil(() => u.isVisible(modal.el), 1000);
@ -4818,7 +4820,7 @@ describe("Groupchats", function () {
await mock.openControlBox(_converse);
const roomspanel = _converse.chatboxviews.get('controlbox').querySelector('converse-rooms-list');
roomspanel.el.querySelector('.show-list-muc-modal').click();
roomspanel.querySelector('.show-list-muc-modal').click();
mock.closeControlBox(_converse);
const modal = _converse.api.modal.get('muc-list-modal');
await u.waitUntil(() => u.isVisible(modal.el), 1000);
@ -4868,15 +4870,15 @@ describe("Groupchats", function () {
await mock.openControlBox(_converse);
const roomspanel = _converse.chatboxviews.get('controlbox').querySelector('converse-rooms-list');
expect(roomspanel.el.querySelectorAll('.available-room').length).toBe(0);
expect(roomspanel.querySelectorAll('.available-room').length).toBe(0);
const muc_jid = 'kitchen@conference.shakespeare.lit';
const message = 'fires: Your attention is required';
await mock.openAndEnterChatRoom(_converse, muc_jid, 'fires');
const view = _converse.api.chatviews.get(muc_jid);
await u.waitUntil(() => roomspanel.el.querySelectorAll('.available-room').length);
expect(roomspanel.el.querySelectorAll('.available-room').length).toBe(1);
expect(roomspanel.el.querySelectorAll('.msgs-indicator').length).toBe(0);
await u.waitUntil(() => roomspanel.querySelectorAll('.available-room').length);
expect(roomspanel.querySelectorAll('.available-room').length).toBe(1);
expect(roomspanel.querySelectorAll('.msgs-indicator').length).toBe(0);
view.model.set({'minimized': true});
@ -4888,9 +4890,9 @@ describe("Groupchats", function () {
type: 'groupchat'
}).c('body').t(message).tree());
await u.waitUntil(() => view.model.messages.length);
expect(roomspanel.el.querySelectorAll('.available-room').length).toBe(1);
expect(roomspanel.el.querySelectorAll('.msgs-indicator').length).toBe(1);
expect(roomspanel.el.querySelector('.msgs-indicator').textContent.trim()).toBe('1');
expect(roomspanel.querySelectorAll('.available-room').length).toBe(1);
expect(roomspanel.querySelectorAll('.msgs-indicator').length).toBe(1);
expect(roomspanel.querySelector('.msgs-indicator').textContent.trim()).toBe('1');
await view.model.handleMessageStanza($msg({
'from': muc_jid+'/'+nick,
@ -4899,12 +4901,12 @@ describe("Groupchats", function () {
'type': 'groupchat'
}).c('body').t(message).tree());
await u.waitUntil(() => view.model.messages.length > 1);
expect(roomspanel.el.querySelectorAll('.available-room').length).toBe(1);
expect(roomspanel.el.querySelectorAll('.msgs-indicator').length).toBe(1);
expect(roomspanel.el.querySelector('.msgs-indicator').textContent.trim()).toBe('2');
expect(roomspanel.querySelectorAll('.available-room').length).toBe(1);
expect(roomspanel.querySelectorAll('.msgs-indicator').length).toBe(1);
expect(roomspanel.querySelector('.msgs-indicator').textContent.trim()).toBe('2');
view.model.set({'minimized': false});
expect(roomspanel.el.querySelectorAll('.available-room').length).toBe(1);
expect(roomspanel.el.querySelectorAll('.msgs-indicator').length).toBe(0);
expect(roomspanel.querySelectorAll('.available-room').length).toBe(1);
expect(roomspanel.querySelectorAll('.msgs-indicator').length).toBe(0);
done();
}));
});
@ -4953,7 +4955,7 @@ describe("Groupchats", function () {
_converse.connection._dataRecv(mock.createRequest(presence));
const occupant = view.model.occupants.findWhere({'jid': _converse.bare_jid});
expect(occupant.get('role')).toBe('visitor');
await u.waitUntil(() => occupant.get('role') === 'visitor');
spyOn(_converse.connection, 'send');
view.model.setChatState(_converse.INACTIVE);
@ -5260,7 +5262,7 @@ describe("Groupchats", function () {
</presence>`);
_converse.connection._dataRecv(mock.createRequest(stanza));
expect(view.querySelector('.chat-textarea')).toBe(null);
await u.waitUntil(() => view.querySelector('.chat-textarea') === null);
let bottom_panel = view.querySelector('.muc-bottom-panel');
expect(bottom_panel.textContent.trim()).toBe("You're not allowed to send messages in this room");
@ -5295,8 +5297,7 @@ describe("Groupchats", function () {
</x>
</presence>`);
_converse.connection._dataRecv(mock.createRequest(stanza));
bottom_panel = view.querySelector('.muc-bottom-panel');
expect(bottom_panel).toBe(null);
await u.waitUntil(() => view.querySelector('.muc-bottom-panel') === null);
textarea = view.querySelector('.chat-textarea');
expect(textarea === null).toBe(false);

View File

@ -390,6 +390,8 @@ describe("A Groupchat Message", function () {
.c('status').attrs({code:'210'}).nodeTree;
_converse.connection._dataRecv(mock.createRequest(presence));
await u.waitUntil(() => view.model.messages.length === 4);
msg = $msg({
from: 'lounge@montague.lit/romeo',
id: u.getUniqueId(),

View File

@ -12,7 +12,7 @@ describe("Notifications", function () {
describe("an HTML5 Notification", function () {
it("is shown when a new private message is received",
mock.initConverse(['rosterContactsFetched'], {}, async (done, _converse) => {
mock.initConverse([], {}, async (done, _converse) => {
await mock.waitForRoster(_converse, 'current');
const stub = jasmine.createSpyObj('MyNotification', ['onclick', 'close']);
@ -34,7 +34,7 @@ describe("Notifications", function () {
}));
it("is shown when you are mentioned in a groupchat",
mock.initConverse(['rosterContactsFetched'], {}, async (done, _converse) => {
mock.initConverse([], {}, async (done, _converse) => {
await mock.waitForRoster(_converse, 'current');
await mock.openAndEnterChatRoom(_converse, 'lounge@montague.lit', 'romeo');
@ -78,11 +78,12 @@ describe("Notifications", function () {
done();
}));
it("is shown for headline messages",
mock.initConverse(['rosterContactsFetched'], {}, async (done, _converse) => {
it("is shown for headline messages", mock.initConverse([], {}, async (done, _converse) => {
const stub = jasmine.createSpyObj('MyNotification', ['onclick', 'close']);
spyOn(window, 'Notification').and.returnValue(stub);
await mock.waitForRoster(_converse, 'current', 0);
const stanza = $msg({
'type': 'headline',
'from': 'notify.example.com',
@ -95,7 +96,7 @@ describe("Notifications", function () {
.c('url').t('imap://romeo@example.com/INBOX;UIDVALIDITY=385759043/;UID=18');
_converse.connection._dataRecv(mock.createRequest(stanza));
await u.waitUntil(() => _converse.chatboxviews.keys().length);
await u.waitUntil(() => _converse.chatboxviews.keys().length === 2);
const view = _converse.chatboxviews.get('notify.example.com');
await new Promise(resolve => view.model.messages.once('rendered', resolve));
expect(_converse.chatboxviews.keys().includes('notify.example.com')).toBeTruthy();
@ -124,7 +125,7 @@ describe("Notifications", function () {
}));
it("is shown when a user changes their chat state (if show_chat_state_notifications is true)",
mock.initConverse(['rosterContactsFetched'], {show_chat_state_notifications: true},
mock.initConverse([], {show_chat_state_notifications: true},
async (done, _converse) => {
await mock.waitForRoster(_converse, 'current', 3);
@ -152,9 +153,7 @@ describe("Notifications", function () {
describe("When play_sounds is set to true", function () {
describe("A notification sound", function () {
it("is played when the current user is mentioned in a groupchat",
mock.initConverse(['rosterContactsFetched'], {}, async (done, _converse) => {
it("is played when the current user is mentioned in a groupchat", mock.initConverse([], {}, async (done, _converse) => {
mock.createContacts(_converse, 'current');
await mock.openAndEnterChatRoom(_converse, 'lounge@montague.lit', 'romeo');
_converse.play_sounds = true;
@ -208,9 +207,7 @@ describe("Notifications", function () {
describe("A Favicon Message Counter", function () {
it("is incremented when the message is received and the window is not focused",
mock.initConverse(
['rosterContactsFetched'], {'show_tab_notifications': false},
async function (done, _converse) {
mock.initConverse([], {'show_tab_notifications': false}, async function (done, _converse) {
await mock.waitForRoster(_converse, 'current');
await mock.openControlBox(_converse);
@ -264,9 +261,7 @@ describe("Notifications", function () {
}));
it("is not incremented when the message is received and the window is focused",
mock.initConverse(
['rosterContactsFetched'], {},
async function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
await mock.waitForRoster(_converse, 'current');
await mock.openControlBox(_converse);
@ -295,15 +290,11 @@ describe("Notifications", function () {
}));
it("is incremented from zero when chatbox was closed after viewing previously received messages and the window is not focused now",
mock.initConverse(
['rosterContactsFetched'], {},
async function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
await mock.waitForRoster(_converse, 'current');
const favico = jasmine.createSpyObj('favico', ['badge']);
spyOn(converse.env, 'Favico').and.returnValue(favico);
const message = 'This message will always increment the message counter from zero';
const sender_jid = mock.cur_names[0].replace(/ /g,'.').toLowerCase() + '@montague.lit';
const msgFactory = function () {

View File

@ -11,8 +11,7 @@ describe("Chatrooms", function () {
describe("The /register commmand", function () {
it("allows you to register your nickname in a room",
mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {'auto_register_muc_nickname': true},
mock.initConverse(['chatBoxesFetched'], {'auto_register_muc_nickname': true},
async function (done, _converse) {
const muc_jid = 'coven@chat.shakespeare.lit';
@ -68,8 +67,7 @@ describe("Chatrooms", function () {
describe("The auto_register_muc_nickname option", function () {
it("allows you to automatically register your nickname when joining a room",
mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {'auto_register_muc_nickname': true},
mock.initConverse(['chatBoxesFetched'], {'auto_register_muc_nickname': true},
async function (done, _converse) {
const muc_jid = 'coven@chat.shakespeare.lit';

View File

@ -7,11 +7,7 @@ const u = converse.env.utils;
describe("XSS", function () {
describe("A Chat Message", function () {
it("will escape IMG payload XSS attempts",
mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {},
async function (done, _converse) {
it("will escape IMG payload XSS attempts", mock.initConverse(['chatBoxesFetched'], {}, async function (done, _converse) {
spyOn(window, 'alert').and.callThrough();
await mock.waitForRoster(_converse, 'current');
await mock.openControlBox(_converse);
@ -67,11 +63,7 @@ describe("XSS", function () {
done();
}));
it("will escape SVG payload XSS attempts",
mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {},
async function (done, _converse) {
it("will escape SVG payload XSS attempts", mock.initConverse(['chatBoxesFetched'], {}, async function (done, _converse) {
spyOn(window, 'alert').and.callThrough();
await mock.waitForRoster(_converse, 'current');
await mock.openControlBox(_converse);
@ -127,9 +119,7 @@ describe("XSS", function () {
}));
it("will have properly escaped URLs",
mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {},
async function (done, _converse) {
mock.initConverse(['chatBoxesFetched'], {}, async function (done, _converse) {
await mock.waitForRoster(_converse, 'current');
await mock.openControlBox(_converse);
@ -185,9 +175,7 @@ describe("XSS", function () {
}));
it("will avoid malformed and unsafe urls urls from rendering as anchors",
mock.initConverse(
['rosterContactsFetched', 'chatBoxesFetched'], {},
async function (done, _converse) {
mock.initConverse(['chatBoxesFetched'], {}, async function (done, _converse) {
await mock.waitForRoster(_converse, 'current');
await mock.openControlBox(_converse);
@ -270,8 +258,7 @@ describe("XSS", function () {
describe("A Groupchat", function () {
it("escapes occupant nicknames when rendering them, to avoid JS-injection attacks",
mock.initConverse(['rosterContactsFetched'], {},
async function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
await mock.openAndEnterChatRoom(_converse, 'lounge@montague.lit', 'romeo');
/* <presence xmlns="jabber:client" to="jc@chat.example.org/converse.js-17184538"
@ -294,17 +281,15 @@ describe("XSS", function () {
_converse.connection._dataRecv(mock.createRequest(presence));
const view = _converse.chatboxviews.get('lounge@montague.lit');
await u.waitUntil(() => view.querySelectorAll('li .occupant-nick').length, 500);
const occupants = view.querySelector('.occupant-list').querySelectorAll('li .occupant-nick');
await u.waitUntil(() => view.querySelectorAll('.occupant-list .occupant-nick').length === 2);
const occupants = view.querySelectorAll('.occupant-list li .occupant-nick');
expect(occupants.length).toBe(2);
expect(occupants[0].textContent.trim()).toBe("&lt;img src=&quot;x&quot; onerror=&quot;alert(123)&quot;/&gt;");
done();
}));
it("escapes the subject before rendering it, to avoid JS-injection attacks",
mock.initConverse(
['rosterContactsFetched'], {},
async function (done, _converse) {
mock.initConverse([], {}, async function (done, _converse) {
await mock.openAndEnterChatRoom(_converse, 'jdev@conference.jabber.org', 'jc');
spyOn(window, 'alert');