Render converse-chat-content
declaratively
This commit is contained in:
parent
18e48be5c4
commit
790caf9f5a
@ -280,7 +280,7 @@ describe("Chatboxes", function () {
|
||||
keyCode: 13 // Enter
|
||||
};
|
||||
view.onKeyDown(ev);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
view.onKeyUp(ev);
|
||||
expect(counter.textContent).toBe('200');
|
||||
|
||||
|
@ -27,7 +27,7 @@ describe("A Chat Message", function () {
|
||||
preventDefault: function preventDefault () {},
|
||||
keyCode: 13 // Enter
|
||||
});
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
expect(view.querySelectorAll('.chat-msg').length).toBe(1);
|
||||
expect(view.querySelector('.chat-msg__text').textContent)
|
||||
.toBe('But soft, what light through yonder airlock breaks?');
|
||||
@ -44,14 +44,15 @@ describe("A Chat Message", function () {
|
||||
await u.waitUntil(() => u.hasClass('correcting', view.querySelector('.chat-msg')), 500);
|
||||
|
||||
spyOn(_converse.connection, 'send');
|
||||
textarea.value = 'But soft, what light through yonder window breaks?';
|
||||
let new_text = 'But soft, what light through yonder window breaks?';
|
||||
textarea.value = new_text;
|
||||
view.onKeyDown({
|
||||
target: textarea,
|
||||
preventDefault: function preventDefault () {},
|
||||
keyCode: 13 // Enter
|
||||
});
|
||||
expect(_converse.connection.send).toHaveBeenCalled();
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelector('.chat-msg__text').textContent.replace(/<!---->/g, '') === new_text);
|
||||
|
||||
const msg = _converse.connection.send.calls.all()[0].args[0];
|
||||
expect(msg.toLocaleString())
|
||||
@ -97,13 +98,15 @@ describe("A Chat Message", function () {
|
||||
expect(view.querySelectorAll('.chat-msg').length).toBe(1);
|
||||
await u.waitUntil(() => (u.hasClass('correcting', view.querySelector('.chat-msg')) === false), 500);
|
||||
|
||||
textarea.value = 'It is the east, and Juliet is the one.';
|
||||
new_text = 'It is the east, and Juliet is the one.';
|
||||
textarea.value = new_text;
|
||||
view.onKeyDown({
|
||||
target: textarea,
|
||||
preventDefault: function preventDefault () {},
|
||||
keyCode: 13 // Enter
|
||||
});
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => Array.from(view.querySelectorAll('.chat-msg__text'))
|
||||
.filter(m => m.textContent.replace(/<!---->/g, '') === new_text).length);
|
||||
expect(view.querySelectorAll('.chat-msg').length).toBe(2);
|
||||
|
||||
textarea.value = 'Arise, fair sun, and kill the envious moon';
|
||||
@ -112,18 +115,17 @@ describe("A Chat Message", function () {
|
||||
preventDefault: function preventDefault () {},
|
||||
keyCode: 13 // Enter
|
||||
});
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
expect(view.querySelectorAll('.chat-msg').length).toBe(3);
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 3);
|
||||
|
||||
view.onKeyDown({
|
||||
target: textarea,
|
||||
keyCode: 38 // Up arrow
|
||||
});
|
||||
expect(textarea.value).toBe('Arise, fair sun, and kill the envious moon');
|
||||
await u.waitUntil(() => view.model.messages.at(2).get('correcting') === true);
|
||||
expect(view.model.messages.at(0).get('correcting')).toBeFalsy();
|
||||
expect(view.model.messages.at(1).get('correcting')).toBeFalsy();
|
||||
expect(view.model.messages.at(2).get('correcting')).toBe(true);
|
||||
await u.waitUntil(() => u.hasClass('correcting', sizzle('.chat-msg:last', view.el).pop()), 500);
|
||||
await u.waitUntil(() => u.hasClass('correcting', sizzle('.chat-msg:last', view.el).pop()), 750);
|
||||
|
||||
textarea.selectionEnd = 0; // Happens by pressing up,
|
||||
// but for some reason not in tests, so we set it manually.
|
||||
@ -143,7 +145,6 @@ describe("A Chat Message", function () {
|
||||
preventDefault: function preventDefault () {},
|
||||
keyCode: 13 // Enter
|
||||
});
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => textarea.value === '');
|
||||
const messages = view.querySelectorAll('.chat-msg');
|
||||
expect(messages.length).toBe(3);
|
||||
@ -177,12 +178,12 @@ describe("A Chat Message", function () {
|
||||
preventDefault: function preventDefault () {},
|
||||
keyCode: 13 // Enter
|
||||
});
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
|
||||
expect(view.querySelectorAll('.chat-msg').length).toBe(1);
|
||||
expect(view.querySelector('.chat-msg__text').textContent)
|
||||
.toBe('But soft, what light through yonder airlock breaks?');
|
||||
expect(textarea.value).toBe('');
|
||||
await u.waitUntil(() => textarea.value === '');
|
||||
|
||||
const first_msg = view.model.messages.findWhere({'message': 'But soft, what light through yonder airlock breaks?'});
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg .chat-msg__action').length === 2);
|
||||
@ -546,14 +547,16 @@ describe("A Groupchat Message", function () {
|
||||
await u.waitUntil(() => u.hasClass('correcting', view.querySelector('.chat-msg')));
|
||||
|
||||
spyOn(_converse.connection, 'send');
|
||||
textarea.value = 'But soft, what light through yonder window breaks?';
|
||||
const new_text = 'But soft, what light through yonder window breaks?'
|
||||
textarea.value = new_text;
|
||||
view.onKeyDown({
|
||||
target: textarea,
|
||||
preventDefault: function preventDefault () {},
|
||||
keyCode: 13 // Enter
|
||||
});
|
||||
expect(_converse.connection.send).toHaveBeenCalled();
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => Array.from(view.querySelectorAll('.chat-msg__text'))
|
||||
.filter(m => m.textContent.replace(/<!---->/g, '') === new_text).length);
|
||||
|
||||
const msg = _converse.connection.send.calls.all()[0].args[0];
|
||||
expect(msg.toLocaleString())
|
||||
@ -586,7 +589,7 @@ describe("A Groupchat Message", function () {
|
||||
'to': 'romeo@montague.lit',
|
||||
'type': 'groupchat'
|
||||
}).c('body').t('Hello world').tree());
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 2);
|
||||
expect(view.querySelectorAll('.chat-msg').length).toBe(2);
|
||||
|
||||
// Test that pressing the down arrow cancels message correction
|
||||
|
@ -263,7 +263,7 @@ describe("Emojis", function () {
|
||||
.c('active', {'xmlns': 'http://jabber.org/protocol/chatstates'}).tree());
|
||||
await new Promise(resolve => _converse.on('chatBoxViewInitialized', resolve));
|
||||
const view = _converse.api.chatviews.get(sender_jid);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
await u.waitUntil(() => u.hasClass('chat-msg__text--larger', view.content.querySelector('.chat-msg__text')));
|
||||
|
||||
_converse.handleMessageStanza($msg({
|
||||
@ -273,7 +273,7 @@ describe("Emojis", function () {
|
||||
'id': _converse.connection.getUniqueId()
|
||||
}).c('body').t('😇 Hello world! 😇 😇').up()
|
||||
.c('active', {'xmlns': 'http://jabber.org/protocol/chatstates'}).tree());
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 2);
|
||||
|
||||
let sel = '.message:last-child .chat-msg__text';
|
||||
await u.waitUntil(() => u.hasClass('chat-msg__text--larger', view.content.querySelector(sel)));
|
||||
@ -287,8 +287,7 @@ describe("Emojis", function () {
|
||||
preventDefault: function preventDefault () {},
|
||||
keyCode: 13 // Enter
|
||||
});
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
expect(view.querySelectorAll('.chat-msg').length).toBe(3);
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 3);
|
||||
const last_msg_sel = 'converse-chat-message:last-child .chat-msg__text';
|
||||
await u.waitUntil(() => view.content.querySelector(last_msg_sel).textContent === '💩 😇');
|
||||
|
||||
@ -301,13 +300,15 @@ describe("Emojis", function () {
|
||||
expect(view.model.messages.at(2).get('correcting')).toBe(true);
|
||||
sel = 'converse-chat-message:last-child .chat-msg'
|
||||
await u.waitUntil(() => u.hasClass('correcting', view.querySelector(sel)), 500);
|
||||
textarea.value = textarea.value += 'This is no longer an emoji-only message';
|
||||
const edited_text = textarea.value += 'This is no longer an emoji-only message';
|
||||
textarea.value = edited_text;
|
||||
view.onKeyDown({
|
||||
target: textarea,
|
||||
preventDefault: function preventDefault () {},
|
||||
keyCode: 13 // Enter
|
||||
});
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => Array.from(view.querySelectorAll('.chat-msg__text'))
|
||||
.filter(el => el.textContent === edited_text).length);
|
||||
expect(view.model.messages.models.length).toBe(3);
|
||||
let message = view.content.querySelector(last_msg_sel);
|
||||
expect(u.hasClass('chat-msg__text--larger', message)).toBe(false);
|
||||
@ -318,7 +319,7 @@ describe("Emojis", function () {
|
||||
preventDefault: function preventDefault () {},
|
||||
keyCode: 13 // Enter
|
||||
});
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 4);
|
||||
|
||||
textarea.value = ':smile: :smiley: :imp:';
|
||||
view.onKeyDown({
|
||||
@ -326,7 +327,7 @@ describe("Emojis", function () {
|
||||
preventDefault: function preventDefault () {},
|
||||
keyCode: 13 // Enter
|
||||
});
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 5);
|
||||
|
||||
message = view.content.querySelector('.message:last-child .chat-msg__text');
|
||||
expect(u.hasClass('chat-msg__text--larger', message)).toBe(true);
|
||||
|
@ -237,7 +237,6 @@ describe("XEP-0363: HTTP File Upload", function () {
|
||||
'name': "my-juliet.jpg"
|
||||
};
|
||||
view.model.sendFiles([file]);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
|
||||
await u.waitUntil(() => _.filter(IQ_stanzas, iq => iq.querySelector('iq[to="upload.montague.tld"] request')).length);
|
||||
const iq = IQ_stanzas.pop();
|
||||
@ -270,22 +269,20 @@ describe("XEP-0363: HTTP File Upload", function () {
|
||||
</slot>
|
||||
</iq>`);
|
||||
|
||||
spyOn(XMLHttpRequest.prototype, 'send').and.callFake(function () {
|
||||
spyOn(XMLHttpRequest.prototype, 'send').and.callFake(async function () {
|
||||
const message = view.model.messages.at(0);
|
||||
expect(view.querySelector('.chat-content progress').getAttribute('value')).toBe('0');
|
||||
const el = await u.waitUntil(() => view.querySelector('.chat-content progress'));
|
||||
expect(el.getAttribute('value')).toBe('0');
|
||||
message.set('progress', 0.5);
|
||||
u.waitUntil(() => view.querySelector('.chat-content progress').getAttribute('value') === '0.5')
|
||||
.then(() => {
|
||||
await u.waitUntil(() => view.querySelector('.chat-content progress').getAttribute('value') === '0.5')
|
||||
message.set('progress', 1);
|
||||
u.waitUntil(() => view.querySelector('.chat-content progress').getAttribute('value') === '1')
|
||||
}).then(() => {
|
||||
await u.waitUntil(() => view.querySelector('.chat-content progress').getAttribute('value') === '1')
|
||||
message.save({
|
||||
'upload': _converse.SUCCESS,
|
||||
'oob_url': message.get('get'),
|
||||
'message': message.get('get')
|
||||
});
|
||||
return new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
});
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
});
|
||||
let sent_stanza;
|
||||
spyOn(_converse.connection, 'send').and.callFake(stanza => (sent_stanza = stanza));
|
||||
@ -319,8 +316,7 @@ describe("XEP-0363: HTTP File Upload", function () {
|
||||
done();
|
||||
}));
|
||||
|
||||
it("is uploaded and sent out from a groupchat", mock.initConverse(async (done, _converse) => {
|
||||
|
||||
it("is uploaded and sent out from a groupchat", mock.initConverse(['chatBoxesFetched'], {} ,async (done, _converse) => {
|
||||
const base_url = 'https://conversejs.org';
|
||||
await mock.waitUntilDiscoConfirmed(
|
||||
_converse, _converse.domain,
|
||||
@ -346,7 +342,6 @@ describe("XEP-0363: HTTP File Upload", function () {
|
||||
'name': "my-juliet.jpg"
|
||||
};
|
||||
view.model.sendFiles([file]);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
|
||||
await u.waitUntil(() => _.filter(IQ_stanzas, iq => iq.querySelector('iq[to="upload.montague.tld"] request')).length);
|
||||
const iq = IQ_stanzas.pop();
|
||||
@ -378,22 +373,20 @@ describe("XEP-0363: HTTP File Upload", function () {
|
||||
</slot>
|
||||
</iq>`);
|
||||
|
||||
spyOn(XMLHttpRequest.prototype, 'send').and.callFake(function () {
|
||||
spyOn(XMLHttpRequest.prototype, 'send').and.callFake(async function () {
|
||||
const message = view.model.messages.at(0);
|
||||
expect(view.querySelector('.chat-content progress').getAttribute('value')).toBe('0');
|
||||
const el = await u.waitUntil(() => view.querySelector('.chat-content progress'));
|
||||
expect(el.getAttribute('value')).toBe('0');
|
||||
message.set('progress', 0.5);
|
||||
u.waitUntil(() => view.querySelector('.chat-content progress').getAttribute('value') === '0.5')
|
||||
.then(() => {
|
||||
await u.waitUntil(() => view.querySelector('.chat-content progress').getAttribute('value') === '0.5')
|
||||
message.set('progress', 1);
|
||||
u.waitUntil(() => view.querySelector('.chat-content progress')?.getAttribute('value') === '1')
|
||||
}).then(() => {
|
||||
await u.waitUntil(() => view.querySelector('.chat-content progress')?.getAttribute('value') === '1')
|
||||
message.save({
|
||||
'upload': _converse.SUCCESS,
|
||||
'oob_url': message.get('get'),
|
||||
'message': message.get('get')
|
||||
});
|
||||
return new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
});
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
});
|
||||
let sent_stanza;
|
||||
spyOn(_converse.connection, 'send').and.callFake(stanza => (sent_stanza = stanza));
|
||||
@ -570,8 +563,7 @@ describe("XEP-0363: HTTP File Upload", function () {
|
||||
'name': "my-juliet.jpg"
|
||||
};
|
||||
view.model.sendFiles([file]);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => _.filter(IQ_stanzas, iq => iq.querySelector('iq[to="upload.montague.tld"] request')).length)
|
||||
await u.waitUntil(() => IQ_stanzas.filter(iq => iq.querySelector('iq[to="upload.montague.tld"] request')).length)
|
||||
const iq = IQ_stanzas.pop();
|
||||
expect(Strophe.serialize(iq)).toBe(
|
||||
`<iq from="romeo@montague.lit/orchard" `+
|
||||
@ -604,7 +596,8 @@ describe("XEP-0363: HTTP File Upload", function () {
|
||||
|
||||
spyOn(XMLHttpRequest.prototype, 'send').and.callFake(async () => {
|
||||
const message = view.model.messages.at(0);
|
||||
expect(view.querySelector('.chat-content progress').getAttribute('value')).toBe('0');
|
||||
const el = await u.waitUntil(() => view.querySelector('.chat-content progress'));
|
||||
expect(el.getAttribute('value')).toBe('0');
|
||||
message.set('progress', 0.5);
|
||||
await u.waitUntil(() => view.querySelector('.chat-content progress').getAttribute('value') === '0.5');
|
||||
message.set('progress', 1);
|
||||
|
@ -64,7 +64,7 @@ describe("Message Archive Management", function () {
|
||||
.c('count').t('16');
|
||||
_converse.connection._dataRecv(mock.createRequest(iq_result));
|
||||
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 2);
|
||||
expect(view.model.messages.length).toBe(2);
|
||||
|
||||
while (sent_IQs.length) { sent_IQs.pop(); }
|
||||
@ -379,7 +379,8 @@ describe("Message Archive Management", function () {
|
||||
.c('count').t('16');
|
||||
_converse.connection._dataRecv(mock.createRequest(iq_result));
|
||||
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => Array.from(view.querySelectorAll('.chat-msg__text'))
|
||||
.filter(el => el.textContent === "Thrice the brinded cat hath mew'd.").length, 1000);
|
||||
expect(view.model.messages.length).toBe(1);
|
||||
expect(view.model.messages.at(0).get('message')).toBe("Thrice the brinded cat hath mew'd.");
|
||||
done();
|
||||
@ -433,7 +434,7 @@ describe("Message Archive Management", function () {
|
||||
.c('count').t('16');
|
||||
_converse.connection._dataRecv(mock.createRequest(iq_result));
|
||||
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 2);
|
||||
expect(view.model.messages.length).toBe(2);
|
||||
expect(view.model.messages.at(0).get('message')).toBe("Meet me at the dance");
|
||||
expect(view.model.messages.at(1).get('message')).toBe("Thrice the brinded cat hath mew'd.");
|
||||
|
@ -91,7 +91,7 @@ describe("A XEP-0333 Chat Marker", function () {
|
||||
<stanza-id xmlns="urn:xmpp:sid:0" id="IxVDLJ0RYbWcWvqC" by="${_converse.bare_jid}"/>
|
||||
</message>`);
|
||||
_converse.connection._dataRecv(mock.createRequest(stanza));
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
expect(view.querySelectorAll('.chat-msg').length).toBe(1);
|
||||
expect(view.model.messages.length).toBe(1);
|
||||
|
||||
@ -130,9 +130,9 @@ describe("A XEP-0333 Chat Marker", function () {
|
||||
preventDefault: function preventDefault () {},
|
||||
keyCode: 13 // Enter
|
||||
});
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
expect(view.querySelectorAll('.chat-msg').length).toBe(1);
|
||||
expect(view.querySelector('.chat-msg .chat-msg__body').textContent.trim())
|
||||
expect(view.querySelector('.chat-msg .chat-msg__text').textContent.trim())
|
||||
.toBe("But soft, what light through yonder airlock breaks?");
|
||||
|
||||
const msg_obj = view.model.messages.at(0);
|
||||
|
@ -23,8 +23,8 @@ describe("A Groupchat Message", function () {
|
||||
}).c('body').t(message).tree();
|
||||
await view.model.handleMessageStanza(msg);
|
||||
await u.waitUntil(() => sizzle('.chat-msg:last .chat-msg__text', view.content).pop());
|
||||
await u.waitUntil(() => view.querySelector('.chat-msg__text').textContent.trim() === 'is tired');
|
||||
expect(view.querySelector('.chat-msg__author').textContent.includes('**Dyon van de Wege')).toBeTruthy();
|
||||
expect(view.querySelector('.chat-msg__text').textContent.trim()).toBe('is tired');
|
||||
|
||||
message = '/me is as well';
|
||||
msg = $msg({
|
||||
@ -35,8 +35,8 @@ describe("A Groupchat Message", function () {
|
||||
}).c('body').t(message).tree();
|
||||
await view.model.handleMessageStanza(msg);
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg').length === 2);
|
||||
await u.waitUntil(() => Array.from(view.querySelectorAll('.chat-msg__text')).pop().textContent.trim() === 'is as well');
|
||||
expect(sizzle('.chat-msg__author:last', view).pop().textContent.includes('**Romeo Montague')).toBeTruthy();
|
||||
expect(sizzle('.chat-msg__text:last', view).pop().textContent.trim()).toBe('is as well');
|
||||
|
||||
// Check rendering of a mention inside a me message
|
||||
const msg_text = "/me mentions romeo";
|
||||
@ -77,8 +77,8 @@ describe("A Message", function () {
|
||||
const view = _converse.chatboxviews.get(sender_jid);
|
||||
await u.waitUntil(() => view.querySelector('.chat-msg__text'));
|
||||
expect(view.querySelectorAll('.chat-msg--action').length).toBe(1);
|
||||
await u.waitUntil(() => view.querySelector('.chat-msg__text').textContent.trim() === 'is tired');
|
||||
expect(view.querySelector('.chat-msg__author').textContent.includes('**Mercutio')).toBeTruthy();
|
||||
expect(view.querySelector('.chat-msg__text').textContent).toBe('is tired');
|
||||
|
||||
message = '/me is as well';
|
||||
await mock.sendMessage(view, message);
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*global mock, converse */
|
||||
|
||||
const { Promise, Strophe, $msg, $pres } = converse.env;
|
||||
const { Strophe, $msg, $pres } = converse.env;
|
||||
const u = converse.env.utils;
|
||||
|
||||
|
||||
@ -22,7 +22,7 @@ describe("An incoming groupchat message", function () {
|
||||
type: 'groupchat'
|
||||
}).c('body').t(message).tree();
|
||||
await view.model.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
expect(u.hasClass('mentioned', view.querySelector('.chat-msg'))).toBeTruthy();
|
||||
done();
|
||||
}));
|
||||
@ -58,12 +58,12 @@ describe("An incoming groupchat message", function () {
|
||||
.c('reference', {'xmlns':'urn:xmpp:reference:0', 'begin':'11', 'end':'14', 'type':'mention', 'uri':'xmpp:romeo@montague.lit'}).up()
|
||||
.c('reference', {'xmlns':'urn:xmpp:reference:0', 'begin':'15', 'end':'23', 'type':'mention', 'uri':'xmpp:mr.robot@montague.lit'}).nodeTree;
|
||||
await view.model.handleMessageStanza(msg);
|
||||
let message = await u.waitUntil(() => view.querySelector('.chat-msg__text'));
|
||||
expect(message.classList.length).toEqual(1);
|
||||
expect(message.innerHTML.replace(/<!---->/g, '')).toBe(
|
||||
await u.waitUntil(() => view.querySelector('.chat-msg__text')?.innerHTML.replace(/<!---->/g, '') ===
|
||||
'hello <span class="mention">z3r0</span> '+
|
||||
'<span class="mention mention--self badge badge-info">tom</span> '+
|
||||
'<span class="mention">mr.robot</span>, how are you?');
|
||||
let message = view.querySelector('.chat-msg__text')
|
||||
expect(message.classList.length).toEqual(1);
|
||||
|
||||
msg = $msg({
|
||||
from: 'lounge@montague.lit/sw0rdf1sh',
|
||||
@ -113,10 +113,10 @@ describe("An incoming groupchat message", function () {
|
||||
.c('reference', {'xmlns':'urn:xmpp:reference:0', 'begin':'16', 'end':'24', 'type':'mention', 'uri':'xmpp:mr.robot@montague.lit'}).nodeTree;
|
||||
|
||||
await view.model.handleMessageStanza(msg);
|
||||
const message = await u.waitUntil(() => view.querySelector('.chat-msg__text'));
|
||||
expect(message.classList.length).toEqual(1);
|
||||
expect(message.innerHTML.replace(/<!---->/g, '')).toBe(
|
||||
await u.waitUntil(() => view.querySelector('.chat-msg__text')?.innerHTML.replace(/<!---->/g, '') ===
|
||||
'<blockquote>hello <span class="mention">z3r0</span> <span class="mention mention--self badge badge-info">tom</span> <span class="mention">mr.robot</span>, how are you?</blockquote>');
|
||||
const message = view.querySelector('.chat-msg__text');
|
||||
expect(message.classList.length).toEqual(1);
|
||||
done();
|
||||
}));
|
||||
});
|
||||
@ -316,7 +316,7 @@ describe("A sent groupchat message", function () {
|
||||
}
|
||||
spyOn(_converse.connection, 'send');
|
||||
view.onKeyDown(enter_event);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
const msg = _converse.connection.send.calls.all()[1].args[0];
|
||||
expect(msg.toLocaleString())
|
||||
.toBe(`<message from="romeo@montague.lit/orchard" id="${msg.nodeTree.getAttribute("id")}" `+
|
||||
@ -375,7 +375,7 @@ describe("A sent groupchat message", function () {
|
||||
}
|
||||
spyOn(_converse.connection, 'send');
|
||||
view.onKeyDown(enter_event);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
|
||||
const last_msg_sel = 'converse-chat-message:last-child .chat-msg__text';
|
||||
await u.waitUntil(() =>
|
||||
@ -458,7 +458,7 @@ describe("A sent groupchat message", function () {
|
||||
'keyCode': 13 // Enter
|
||||
}
|
||||
view.onKeyDown(enter_event);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
|
||||
const msg = _converse.connection.send.calls.all()[1].args[0];
|
||||
expect(msg.toLocaleString())
|
||||
|
@ -111,7 +111,7 @@ describe("A Chat Message", function () {
|
||||
.c('delay', {'xmlns': 'urn:xmpp:delay', 'stamp':'2017-12-31T22:08:25Z'})
|
||||
.tree();
|
||||
_converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg').length === 2);
|
||||
|
||||
msg = $msg({
|
||||
'xmlns': 'jabber:client',
|
||||
@ -123,7 +123,7 @@ describe("A Chat Message", function () {
|
||||
.c('delay', {'xmlns': 'urn:xmpp:delay', 'stamp':'2018-01-01T13:18:23Z'})
|
||||
.tree();
|
||||
_converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg').length === 3);
|
||||
|
||||
msg = $msg({
|
||||
'xmlns': 'jabber:client',
|
||||
@ -135,7 +135,7 @@ describe("A Chat Message", function () {
|
||||
.c('delay', {'xmlns': 'urn:xmpp:delay', 'stamp':'2018-01-01T13:18:23Z'})
|
||||
.tree();
|
||||
_converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg').length === 4);
|
||||
|
||||
msg = $msg({
|
||||
'xmlns': 'jabber:client',
|
||||
@ -147,7 +147,7 @@ describe("A Chat Message", function () {
|
||||
.c('delay', {'xmlns': 'urn:xmpp:delay', 'stamp':'2018-01-02T12:18:23Z'})
|
||||
.tree();
|
||||
_converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg').length === 5);
|
||||
|
||||
msg = $msg({
|
||||
'xmlns': 'jabber:client',
|
||||
@ -159,7 +159,7 @@ describe("A Chat Message", function () {
|
||||
.c('delay', {'xmlns': 'urn:xmpp:delay', 'stamp':'2018-01-02T22:28:23Z'})
|
||||
.tree();
|
||||
_converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg').length === 6);
|
||||
|
||||
// Insert <composing> message, to also check that
|
||||
// text messages are inserted correctly with
|
||||
@ -185,8 +185,9 @@ describe("A Chat Message", function () {
|
||||
.c('composing', {'xmlns': Strophe.NS.CHATSTATES}).up()
|
||||
.c('body').t("latest message")
|
||||
.tree();
|
||||
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg').length === 7);
|
||||
|
||||
view.clearSpinner(); //cleanup
|
||||
expect(view.content.querySelectorAll('.date-separator').length).toEqual(4);
|
||||
@ -435,7 +436,7 @@ describe("A Chat Message", function () {
|
||||
.c('delay', { xmlns:'urn:xmpp:delay', from: 'montague.lit', stamp: one_day_ago.toISOString() })
|
||||
.c('active', {'xmlns': 'http://jabber.org/protocol/chatstates'}).tree();
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg').length);
|
||||
|
||||
expect(_converse.api.trigger).toHaveBeenCalledWith('message', jasmine.any(Object));
|
||||
expect(chatbox.messages.length).toEqual(1);
|
||||
@ -446,16 +447,16 @@ describe("A Chat Message", function () {
|
||||
expect(msg_obj.get('sender')).toEqual('them');
|
||||
expect(msg_obj.get('is_delayed')).toEqual(true);
|
||||
await u.waitUntil(() => chatbox.vcard.get('fullname') === 'Juliet Capulet')
|
||||
expect(view.msgs_container.querySelector('.chat-msg .chat-msg__text').textContent).toEqual(message);
|
||||
expect(view.msgs_container.querySelector('.chat-msg__time').textContent.match(/^[0-9][0-9]:[0-9][0-9]/)).toBeTruthy();
|
||||
expect(view.msgs_container.querySelector('span.chat-msg__author').textContent.trim()).toBe('Juliet Capulet');
|
||||
expect(view.querySelector('.chat-msg .chat-msg__text').textContent).toEqual(message);
|
||||
expect(view.querySelector('.chat-msg__time').textContent.match(/^[0-9][0-9]:[0-9][0-9]/)).toBeTruthy();
|
||||
expect(view.querySelector('span.chat-msg__author').textContent.trim()).toBe('Juliet Capulet');
|
||||
|
||||
expect(view.msgs_container.querySelectorAll('.date-separator').length).toEqual(1);
|
||||
let day = view.msgs_container.querySelector('.date-separator');
|
||||
expect(view.querySelectorAll('.date-separator').length).toEqual(1);
|
||||
let day = view.querySelector('.date-separator');
|
||||
expect(day.getAttribute('class')).toEqual('message date-separator');
|
||||
expect(day.getAttribute('data-isodate')).toEqual(dayjs(one_day_ago.startOf('day')).toISOString());
|
||||
|
||||
let time = view.msgs_container.querySelector('time.separator-text');
|
||||
let time = view.querySelector('time.separator-text');
|
||||
expect(time.textContent).toEqual(dayjs(one_day_ago.startOf('day')).format("dddd MMM Do YYYY"));
|
||||
|
||||
message = 'This is a current message';
|
||||
@ -467,19 +468,19 @@ describe("A Chat Message", function () {
|
||||
}).c('body').t(message).up()
|
||||
.c('active', {'xmlns': 'http://jabber.org/protocol/chatstates'}).tree();
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg').length === 2);
|
||||
|
||||
expect(_converse.api.trigger).toHaveBeenCalledWith('message', jasmine.any(Object));
|
||||
// Check that there is a <time> element, with the required props.
|
||||
expect(view.msgs_container.querySelectorAll('time.separator-text').length).toEqual(2); // There are now two time elements
|
||||
expect(view.querySelectorAll('time.separator-text').length).toEqual(2); // There are now two time elements
|
||||
|
||||
const message_date = new Date();
|
||||
day = sizzle('.date-separator:last', view.msgs_container);
|
||||
day = sizzle('.date-separator:last', view);
|
||||
expect(day.length).toEqual(1);
|
||||
expect(day[0].getAttribute('class')).toEqual('message date-separator');
|
||||
expect(day[0].getAttribute('data-isodate')).toEqual(dayjs(message_date).startOf('day').toISOString());
|
||||
|
||||
time = sizzle('time.separator-text:last', view.msgs_container).pop();
|
||||
time = sizzle('time.separator-text:last', view).pop();
|
||||
expect(time.textContent).toEqual(dayjs(message_date).startOf('day').format("dddd MMM Do YYYY"));
|
||||
|
||||
// Normal checks for the 2nd message
|
||||
@ -489,12 +490,12 @@ describe("A Chat Message", function () {
|
||||
expect(msg_obj.get('fullname')).toBeUndefined();
|
||||
expect(msg_obj.get('sender')).toEqual('them');
|
||||
expect(msg_obj.get('is_delayed')).toEqual(false);
|
||||
const msg_txt = sizzle('.chat-msg:last .chat-msg__text', view.msgs_container).pop().textContent;
|
||||
const msg_txt = sizzle('.chat-msg:last .chat-msg__text', view).pop().textContent;
|
||||
expect(msg_txt).toEqual(message);
|
||||
|
||||
expect(view.msgs_container.querySelector('converse-chat-message:last-child .chat-msg__text').textContent).toEqual(message);
|
||||
expect(view.msgs_container.querySelector('converse-chat-message:last-child .chat-msg__time').textContent.match(/^[0-9][0-9]:[0-9][0-9]/)).toBeTruthy();
|
||||
expect(view.msgs_container.querySelector('converse-chat-message:last-child .chat-msg__author').textContent.trim()).toBe('Juliet Capulet');
|
||||
expect(view.querySelector('converse-chat-message:last-child .chat-msg__text').textContent).toEqual(message);
|
||||
expect(view.querySelector('converse-chat-message:last-child .chat-msg__time').textContent.match(/^[0-9][0-9]:[0-9][0-9]/)).toBeTruthy();
|
||||
expect(view.querySelector('converse-chat-message:last-child .chat-msg__author').textContent.trim()).toBe('Juliet Capulet');
|
||||
done();
|
||||
}));
|
||||
|
||||
@ -528,7 +529,7 @@ describe("A Chat Message", function () {
|
||||
spyOn(view.model, 'sendMessage').and.callThrough();
|
||||
mock.sendMessage(view, message);
|
||||
expect(view.model.sendMessage).toHaveBeenCalled();
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
const msg = sizzle('.chat-content .chat-msg:last .chat-msg__text', view.el).pop();
|
||||
expect(msg.textContent).toEqual(message);
|
||||
await u.waitUntil(() => msg.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -547,9 +548,8 @@ describe("A Chat Message", function () {
|
||||
const view = _converse.api.chatviews.get(contact_jid);
|
||||
let message = 'This message contains a hyperlink with forbidden query params: https://www.opkode.com/?id=0&utm_content=1&utm_medium=2&s=1';
|
||||
mock.sendMessage(view, message);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
let msg = sizzle('.chat-content .chat-msg:last .chat-msg__text', view.el).pop();
|
||||
expect(msg.textContent).toEqual(message);
|
||||
await u.waitUntil(() => msg.innerHTML.replace(/<!---->/g, '') ===
|
||||
'This message contains a hyperlink with forbidden query params: <a target="_blank" rel="noopener" href="https://www.opkode.com/?id=0">https://www.opkode.com/?id=0</a>');
|
||||
|
||||
@ -557,9 +557,9 @@ describe("A Chat Message", function () {
|
||||
_converse.api.settings.set('filter_url_query_params', 'utm_medium');
|
||||
message = 'Another message with a hyperlink with forbidden query params: https://www.opkode.com/?id=0&utm_content=1&utm_medium=2&s=1';
|
||||
mock.sendMessage(view, message);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 2);
|
||||
msg = sizzle('.chat-content .chat-msg:last .chat-msg__text', view.el).pop();
|
||||
expect(msg.textContent).toEqual(message);
|
||||
expect(msg.textContent).toEqual('Another message with a hyperlink with forbidden query params: https://www.opkode.com/?id=0&utm_content=1&s=1');
|
||||
await u.waitUntil(() => msg.innerHTML.replace(/<!---->/g, '') ===
|
||||
'Another message with a hyperlink with forbidden query params: '+
|
||||
'<a target="_blank" rel="noopener" href="https://www.opkode.com/?id=0&utm_content=1&s=1">https://www.opkode.com/?id=0&utm_content=1&s=1</a>');
|
||||
@ -577,7 +577,7 @@ describe("A Chat Message", function () {
|
||||
<body>Hey\nHave you heard the news?</body>
|
||||
</message>`);
|
||||
_converse.connection._dataRecv(mock.createRequest(stanza));
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
expect(view.content.querySelector('.chat-msg__text').innerHTML.replace(/<!---->/g, '')).toBe('Hey\nHave you heard the news?');
|
||||
stanza = u.toStanza(`
|
||||
<message from="${contact_jid}"
|
||||
@ -586,8 +586,9 @@ describe("A Chat Message", function () {
|
||||
<body>Hey\n\n\nHave you heard the news?</body>
|
||||
</message>`);
|
||||
_converse.connection._dataRecv(mock.createRequest(stanza));
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.content.querySelector('converse-chat-message:last-child .chat-msg__text').innerHTML.replace(/<!---->/g, '') === 'Hey\n\n\nHave you heard the news?');
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 2);
|
||||
const text = view.content.querySelector('converse-chat-message:last-child .chat-msg__text').innerHTML.replace(/<!---->/g, '');
|
||||
expect(text).toBe('Hey\n\u200B\nHave you heard the news?');
|
||||
stanza = u.toStanza(`
|
||||
<message from="${contact_jid}"
|
||||
type="chat"
|
||||
@ -595,7 +596,7 @@ describe("A Chat Message", function () {
|
||||
<body>Hey\nHave you heard\nthe news?</body>
|
||||
</message>`);
|
||||
_converse.connection._dataRecv(mock.createRequest(stanza));
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 3);
|
||||
expect(view.content.querySelector('converse-chat-message:last-child .chat-msg__text').innerHTML.replace(/<!---->/g, '')).toBe('Hey\nHave you heard\nthe news?');
|
||||
|
||||
stanza = u.toStanza(`
|
||||
@ -605,7 +606,7 @@ describe("A Chat Message", function () {
|
||||
<body>Hey\nHave you heard\n\n\nthe news?\nhttps://conversejs.org</body>
|
||||
</message>`);
|
||||
_converse.connection._dataRecv(mock.createRequest(stanza));
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 4);
|
||||
await u.waitUntil(() => {
|
||||
const text = view.content.querySelector('converse-chat-message:last-child .chat-msg__text').innerHTML.replace(/<!---->/g, '');
|
||||
return text === 'Hey\nHave you heard\n\u200B\nthe news?\n<a target="_blank" rel="noopener" href="https://conversejs.org/">https://conversejs.org</a>';
|
||||
@ -1067,7 +1068,7 @@ describe("A Chat Message", function () {
|
||||
|
||||
await _converse.handleMessageStanza(msg);
|
||||
const view = await u.waitUntil(() => _converse.api.chatviews.get(sender_jid));
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg').length);
|
||||
expect(_converse.api.trigger).toHaveBeenCalledWith('message', jasmine.any(Object));
|
||||
|
||||
// Check that the chatbox and its view now exist
|
||||
@ -1081,7 +1082,7 @@ describe("A Chat Message", function () {
|
||||
expect(_converse.api.vcard.get).toHaveBeenCalled();
|
||||
await u.waitUntil(() => chatbox.vcard.get('fullname') === mock.cur_names[0])
|
||||
author_el = view.querySelector('.chat-msg__author');
|
||||
expect( _.includes(author_el.textContent.trim(), 'Mercutio')).toBeTruthy();
|
||||
expect(author_el.textContent.trim().includes('Mercutio')).toBeTruthy();
|
||||
done();
|
||||
}));
|
||||
});
|
||||
@ -1119,7 +1120,7 @@ describe("A Chat Message", function () {
|
||||
_converse.allow_non_roster_messaging = true;
|
||||
await _converse.handleMessageStanza(msg);
|
||||
view = _converse.chatboxviews.get(sender_jid);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg').length);
|
||||
expect(_converse.api.trigger).toHaveBeenCalledWith('message', jasmine.any(Object));
|
||||
// Check that the chatbox and its view now exist
|
||||
chatbox = await _converse.api.chats.get(sender_jid);
|
||||
@ -1170,7 +1171,7 @@ describe("A Chat Message", function () {
|
||||
let msg_text = 'This message will not be sent, due to an error';
|
||||
const view = _converse.api.chatviews.get(sender_jid);
|
||||
const message = await view.model.sendMessage(msg_text);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg').length);
|
||||
let msg_txt = sizzle('.chat-msg:last .chat-msg__text', view.content).pop().textContent;
|
||||
expect(msg_txt).toEqual(msg_text);
|
||||
|
||||
@ -1253,18 +1254,14 @@ describe("A Chat Message", function () {
|
||||
.t('Something else went wrong as well');
|
||||
_converse.connection._dataRecv(mock.createRequest(stanza));
|
||||
await u.waitUntil(() => view.model.messages.length > 2);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
expect(view.content.querySelectorAll('.chat-msg__error').length).toEqual(3);
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__error').length === 3);
|
||||
|
||||
// Ensure messages with error are not editable
|
||||
document.querySelectorAll('.chat-msg__actions').forEach(elem => {
|
||||
expect(elem.querySelector('.chat-msg__action-edit')).toBe(null)
|
||||
// Ensure messages with error are not editable or retractable
|
||||
await u.waitUntil(() => !view.model.messages.models.reduce((acc, m) => acc || m.get('editable'), false), 1000);
|
||||
view.querySelectorAll('.chat-msg').forEach(el => {
|
||||
expect(el.querySelector('.chat-msg__action-edit')).toBe(null)
|
||||
expect(el.querySelector('.chat-msg__action-retract')).toBe(null)
|
||||
})
|
||||
view.model.messages.forEach(message => {
|
||||
const isEditable = message.get('editable');
|
||||
isEditable && expect(isEditable).toBe(false);
|
||||
})
|
||||
|
||||
done();
|
||||
}));
|
||||
|
||||
@ -1302,7 +1299,7 @@ describe("A Chat Message", function () {
|
||||
const view = _converse.chatboxviews.get(contact_jid);
|
||||
const msg_text = 'This message will show!';
|
||||
await view.model.sendMessage(msg_text);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
expect(view.content.querySelectorAll('.chat-error').length).toEqual(0);
|
||||
done();
|
||||
}));
|
||||
|
23
spec/muc.js
23
spec/muc.js
@ -664,7 +664,7 @@ describe("Groupchats", function () {
|
||||
<body>This is a message</body>
|
||||
</message>`);
|
||||
_converse.connection._dataRecv(mock.createRequest(stanza));
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
expect(sizzle('.chat-msg__subject', view).length).toBe(1);
|
||||
expect(sizzle('.chat-msg__subject', view).pop().textContent.trim()).toBe('This is a message subject');
|
||||
expect(sizzle('.chat-msg__text').length).toBe(1);
|
||||
@ -695,7 +695,7 @@ describe("Groupchats", function () {
|
||||
<body>This is a message</body>
|
||||
</message>`);
|
||||
_converse.connection._dataRecv(mock.createRequest(stanza));
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
expect(sizzle('.chat-msg__subject', view).length).toBe(1);
|
||||
expect(sizzle('.chat-msg__subject', view).pop().textContent.trim()).toBe('This is a message subject');
|
||||
expect(sizzle('.chat-msg__text').length).toBe(1);
|
||||
@ -1009,7 +1009,7 @@ describe("Groupchats", function () {
|
||||
'type': 'groupchat'
|
||||
}).c('body').t('hello world').tree();
|
||||
_converse.connection._dataRecv(mock.createRequest(msg));
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
|
||||
// Add another entrant, otherwise the above message will be
|
||||
// collapsed if "newguy" leaves immediately again
|
||||
@ -2112,7 +2112,7 @@ describe("Groupchats", function () {
|
||||
preventDefault: function preventDefault () {},
|
||||
keyCode: 13
|
||||
});
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
|
||||
expect(_converse.api.trigger).toHaveBeenCalledWith('messageSend', jasmine.any(_converse.Message));
|
||||
expect(view.content.querySelectorAll('.chat-msg').length).toBe(1);
|
||||
@ -2170,7 +2170,7 @@ describe("Groupchats", function () {
|
||||
type: 'groupchat',
|
||||
id: u.getUniqueId(),
|
||||
}).c('body').t(message).tree());
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 21);
|
||||
// Now check that the message appears inside the chatbox in the DOM
|
||||
const msg_txt = sizzle('.chat-msg:last .chat-msg__text', view.content).pop().textContent;
|
||||
expect(msg_txt).toEqual(message);
|
||||
@ -2858,8 +2858,8 @@ describe("Groupchats", function () {
|
||||
'role': 'participant'
|
||||
});
|
||||
_converse.connection._dataRecv(mock.createRequest(presence));
|
||||
const csntext = await u.waitUntil(() => view.querySelector('.chat-content__notifications').textContent);
|
||||
expect(csntext.trim()).toEqual("romeo and annoyingGuy have entered the groupchat");
|
||||
await u.waitUntil(() => view.querySelector('.chat-content__notifications').textContent.trim() ===
|
||||
"romeo and annoyingGuy have entered the groupchat");
|
||||
|
||||
presence = $pres({
|
||||
'from': 'lounge@montague.lit/annoyingGuy',
|
||||
@ -2906,6 +2906,7 @@ describe("Groupchats", function () {
|
||||
Array.from(view.querySelectorAll('.chat-info__message')).pop()?.textContent.trim() ===
|
||||
"annoyingGuy is no longer a member of this groupchat"
|
||||
);
|
||||
expect(1).toBe(1);
|
||||
done();
|
||||
}));
|
||||
|
||||
@ -3614,8 +3615,8 @@ describe("Groupchats", function () {
|
||||
'role': 'participant'
|
||||
});
|
||||
_converse.connection._dataRecv(mock.createRequest(presence));
|
||||
const csntext = await u.waitUntil(() => view.querySelector('.chat-content__notifications').textContent);
|
||||
expect(csntext.trim()).toEqual("romeo and trustworthyguy have entered the groupchat");
|
||||
await u.waitUntil(() => view.querySelector('.chat-content__notifications').textContent.trim() ===
|
||||
"romeo and trustworthyguy have entered the groupchat");
|
||||
|
||||
const textarea = view.querySelector('.chat-textarea')
|
||||
textarea.value = '/op';
|
||||
@ -3753,8 +3754,8 @@ describe("Groupchats", function () {
|
||||
'role': 'participant'
|
||||
});
|
||||
_converse.connection._dataRecv(mock.createRequest(presence));
|
||||
const csntext = await u.waitUntil(() => view.querySelector('.chat-content__notifications').textContent);
|
||||
expect(csntext.trim()).toEqual("romeo and annoyingGuy have entered the groupchat");
|
||||
await u.waitUntil(() => view.querySelector('.chat-content__notifications').textContent.trim() ===
|
||||
"romeo and annoyingGuy have entered the groupchat");
|
||||
|
||||
const textarea = view.querySelector('.chat-textarea')
|
||||
textarea.value = '/mute';
|
||||
|
@ -174,8 +174,8 @@ describe("A Groupchat Message", function () {
|
||||
.c('active', {'xmlns': "http://jabber.org/protocol/chatstates"})
|
||||
.tree();
|
||||
await view.model.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
expect(view.querySelector('.chat-msg')).not.toBe(null);
|
||||
const el = await u.waitUntil(() => view.querySelector('.chat-msg__text'));
|
||||
expect(el.textContent).toBe(message);
|
||||
done();
|
||||
}));
|
||||
|
||||
@ -399,10 +399,9 @@ describe("A Groupchat Message", function () {
|
||||
type: 'groupchat'
|
||||
}).c('body').t('Another message!').tree();
|
||||
await view.model.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg').length === 2);
|
||||
expect(view.model.messages.last().occupant.get('affiliation')).toBe('member');
|
||||
expect(view.model.messages.last().occupant.get('role')).toBe('participant');
|
||||
expect(view.querySelectorAll('.chat-msg').length).toBe(2);
|
||||
expect(sizzle('.chat-msg', view.el).pop().classList.value.trim()).toBe('message chat-msg groupchat chat-msg--with-avatar participant member');
|
||||
|
||||
presence = $pres({
|
||||
@ -436,7 +435,7 @@ describe("A Groupchat Message", function () {
|
||||
type: 'groupchat'
|
||||
}).c('body').t('Message from someone not in the MUC right now').tree();
|
||||
await view.model.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg').length === 4);
|
||||
expect(view.model.messages.last().occupant).toBeUndefined();
|
||||
// Check that there's a new "add" event handler, for when the occupant appears.
|
||||
expect(view.model.occupants._events.add.length).toBe(add_events+1);
|
||||
|
@ -790,7 +790,7 @@ describe("Message Retractions", function () {
|
||||
expect(view.model.messages.length).toBe(1);
|
||||
expect(view.model.messages.at(0).get('editable')).toBe(true);
|
||||
|
||||
const retract_button = await u.waitUntil(() => view.msgs_container.querySelector('.chat-msg__content .chat-msg__action-retract'));
|
||||
const retract_button = await u.waitUntil(() => view.querySelector('.chat-msg__content .chat-msg__action-retract'));
|
||||
retract_button.click();
|
||||
await u.waitUntil(() => u.isVisible(document.querySelector('#converse-modals .modal')));
|
||||
const submit_button = document.querySelector('#converse-modals .modal button[type="submit"]');
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*global mock, converse */
|
||||
|
||||
const { u, Promise, $msg } = converse.env;
|
||||
const { u, $msg } = converse.env;
|
||||
|
||||
describe("An incoming chat Message", function () {
|
||||
|
||||
@ -79,7 +79,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = "This *message _contains_* styling hints! \`Here's *some* code\`";
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
msg_el = view.querySelector('converse-chat-message-body');
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -93,7 +93,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = "Here's a ~strikethrough section~";
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 2);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -103,7 +103,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = "~Check out this site: https://conversejs.org~"
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 3);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -116,7 +116,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = `*${base_url}/logo/conversejs-filled.svg*`;
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 4);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -128,7 +128,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = `~ Hello! :poop: ~`;
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 5);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -138,7 +138,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = "This *is not a styling hint \n * _But this is_!";
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 6);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -148,7 +148,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = `(There are three blocks in this body marked by parens,)\n (but there is no *formatting)\n (as spans* may not escape blocks.)\n ~strikethrough~`;
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 7);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -161,7 +161,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = `__ hello world _`;
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 8);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -171,7 +171,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = `Go to ~https://conversejs.org~now _please_`;
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 9);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -180,7 +180,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = `Go to _https://converse_js.org_ _please_`;
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 10);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -204,7 +204,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = `Here's a code block: \n\`\`\`\nInside the code-block, <code>hello</code> we don't enable *styling hints* like ~these~\n\`\`\``;
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -216,7 +216,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = "```\nignored\n(println \"Hello, world!\")\n```\nThis should show up as monospace, preformatted text ^";
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 2);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -229,7 +229,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = "```ignored\n (println \"Hello, world!\")\n ```\n\n This should not show up as monospace, *preformatted* text ^";
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 3);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -252,7 +252,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = `> This is quoted text\n>This is also quoted\nThis is not quoted`;
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 1);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -261,7 +261,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = `> This is *quoted* text\n>This is \`also _quoted_\`\nThis is not quoted`;
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 2);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -272,7 +272,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = `> > This is doubly quoted text`;
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 3);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') === "<blockquote><blockquote>This is doubly quoted text</blockquote></blockquote>");
|
||||
@ -280,7 +280,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = `>> This is doubly quoted text`;
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 4);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') === "<blockquote><blockquote>This is doubly quoted text</blockquote></blockquote>");
|
||||
@ -288,7 +288,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = ">```\n>ignored\n> <span></span> (println \"Hello, world!\")\n>```\n> This should show up as monospace, preformatted text ^";
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 5);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -302,7 +302,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = '> ```\n> (println "Hello, world!")\n\nThe entire blockquote is a preformatted text block, but this line is plaintext!';
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 6);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -312,7 +312,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = '> Also, icons.js is loaded from /dist, instead of dist.\nhttps://conversejs.org/docs/html/configuration.html#assets-path'
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 7);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -322,7 +322,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = '> Where is it located?\ngeo:37.786971,-122.399677';
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 8);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -333,7 +333,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = '> What do you think of it?\n :poop:';
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 9);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -342,7 +342,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = '> What do you think of it?\n~hello~';
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 10);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
@ -351,7 +351,7 @@ describe("An incoming chat Message", function () {
|
||||
msg_text = 'hello world > this is not a quote';
|
||||
msg = mock.createChatMessage(_converse, contact_jid, msg_text)
|
||||
await _converse.handleMessageStanza(msg);
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 11);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') === 'hello world > this is not a quote');
|
||||
@ -379,7 +379,7 @@ describe("An incoming chat Message", function () {
|
||||
}).nodeTree;
|
||||
await _converse.handleMessageStanza(msg);
|
||||
|
||||
await new Promise(resolve => view.model.messages.once('rendered', resolve));
|
||||
await u.waitUntil(() => view.querySelectorAll('.chat-msg__text').length === 12);
|
||||
msg_el = Array.from(view.querySelectorAll('converse-chat-message-body')).pop();
|
||||
expect(msg_el.innerText).toBe(msg_text);
|
||||
await u.waitUntil(() => msg_el.innerHTML.replace(/<!---->/g, '') ===
|
||||
|
@ -9,18 +9,29 @@ export default class ChatContent extends CustomElement {
|
||||
|
||||
static get properties () {
|
||||
return {
|
||||
chatview: { type: Object},
|
||||
messages: { type: Array},
|
||||
notifications: { type: String }
|
||||
chatview: { type: Object}
|
||||
}
|
||||
}
|
||||
|
||||
connectedCallback () {
|
||||
super.connectedCallback();
|
||||
const model = this.chatview.model;
|
||||
this.listenTo(model.messages, 'add', this.requestUpdate);
|
||||
this.listenTo(model.messages, 'change', this.requestUpdate);
|
||||
this.listenTo(model.messages, 'remove', this.requestUpdate);
|
||||
this.listenTo(model.messages, 'reset', this.requestUpdate);
|
||||
this.listenTo(model.notifications, 'change', this.requestUpdate);
|
||||
if (model.occupants) {
|
||||
this.listenTo(model.occupants, 'change', this.requestUpdate);
|
||||
}
|
||||
}
|
||||
|
||||
render () {
|
||||
const notifications = xss.filterXSS(this.notifications, {'whiteList': {}});
|
||||
const notifications = xss.filterXSS(this.chatview.getNotifications(), {'whiteList': {}});
|
||||
return html`
|
||||
<converse-message-history
|
||||
.chatview=${this.chatview}
|
||||
.messages=${this.messages}>
|
||||
.messages=${[...this.chatview.model.messages.models]}>
|
||||
</converse-message-history>
|
||||
<div class="chat-content__notifications">${unsafeHTML(notifications)}</div>
|
||||
`;
|
||||
|
@ -90,19 +90,6 @@ export default class Message extends CustomElement {
|
||||
vcard && this.listenTo(vcard, 'change', () => this.requestUpdate());
|
||||
}
|
||||
|
||||
updated () {
|
||||
// XXX: This is ugly but tests rely on this event.
|
||||
// For "normal" chat messages the event is fired in
|
||||
// src/templates/directives/body.js
|
||||
if (
|
||||
this.show_spinner ||
|
||||
(this.model.get('file') && !this.model.get('oob_url')) ||
|
||||
(['error', 'info'].includes(this.message_type))
|
||||
) {
|
||||
this.model.collection?.trigger('rendered', this.model);
|
||||
}
|
||||
}
|
||||
|
||||
renderInfoMessage () {
|
||||
const isodate = dayjs(this.model.get('time')).toISOString();
|
||||
const i18n_retry = __('Retry');
|
||||
|
@ -89,7 +89,8 @@ const MessageMixin = {
|
||||
*/
|
||||
mayBeRetracted () {
|
||||
const is_own_message = this.get('sender') === 'me';
|
||||
return is_own_message && ['all', 'own'].includes(api.settings.get('allow_message_retraction'));
|
||||
const not_canceled = this.get('error_type') !== 'cancel';
|
||||
return is_own_message && not_canceled && ['all', 'own'].includes(api.settings.get('allow_message_retraction'));
|
||||
},
|
||||
|
||||
safeDestroy () {
|
||||
|
@ -61,10 +61,7 @@ export default class ChatView extends BaseChatView {
|
||||
|
||||
// Need to be registered after render has been called.
|
||||
this.listenTo(this.model.messages, 'add', this.onMessageAdded);
|
||||
this.listenTo(this.model.messages, 'remove', this.renderChatHistory);
|
||||
this.listenTo(this.model.messages, 'rendered', this.maybeScrollDown);
|
||||
this.listenTo(this.model.messages, 'reset', this.renderChatHistory);
|
||||
this.listenTo(this.model.notifications, 'change', this.renderNotifications);
|
||||
this.listenTo(this.model, 'change:show_help_messages', this.renderHelpMessages);
|
||||
|
||||
await this.model.messages.fetched;
|
||||
@ -79,13 +76,15 @@ export default class ChatView extends BaseChatView {
|
||||
}
|
||||
|
||||
render () {
|
||||
const result = tpl_chatbox(Object.assign(this.model.toJSON(), { 'markScrolled': ev => this.markScrolled(ev) }));
|
||||
const result = tpl_chatbox(Object.assign(
|
||||
this.model.toJSON(), {
|
||||
'markScrolled': ev => this.markScrolled(ev),
|
||||
'chatview': this
|
||||
})
|
||||
);
|
||||
render(result, this);
|
||||
this.content = this.querySelector('.chat-content');
|
||||
this.notifications = this.querySelector('.chat-content__notifications');
|
||||
this.msgs_container = this.querySelector('.chat-content__messages');
|
||||
this.help_container = this.querySelector('.chat-content__help');
|
||||
this.renderChatContent();
|
||||
this.renderMessageForm();
|
||||
this.renderHeading();
|
||||
return this;
|
||||
|
@ -51,17 +51,13 @@ class HeadlinesView extends BaseChatView {
|
||||
this.setAttribute('id', this.model.get('box_id'));
|
||||
const result = tpl_chatbox(
|
||||
Object.assign(this.model.toJSON(), {
|
||||
info_close: '',
|
||||
label_personal_message: '',
|
||||
chatview: this,
|
||||
show_send_button: false,
|
||||
show_toolbar: false,
|
||||
unread_msgs: ''
|
||||
})
|
||||
);
|
||||
render(result, this);
|
||||
this.content = this.querySelector('.chat-content');
|
||||
this.msgs_container = this.querySelector('.chat-content__messages');
|
||||
this.renderChatContent();
|
||||
this.renderHeading();
|
||||
return this;
|
||||
}
|
||||
|
@ -108,20 +108,14 @@ export default class MUCView extends BaseChatView {
|
||||
// Need to be registered after render has been called.
|
||||
this.listenTo(this.model, 'change:show_help_messages', this.renderHelpMessages);
|
||||
this.listenTo(this.model.messages, 'add', this.onMessageAdded);
|
||||
this.listenTo(this.model.messages, 'change', this.renderChatHistory);
|
||||
this.listenTo(this.model.messages, 'remove', this.renderChatHistory);
|
||||
this.listenTo(this.model.messages, 'reset', this.renderChatHistory);
|
||||
this.listenTo(this.model.notifications, 'change', this.renderNotifications);
|
||||
|
||||
this.model.occupants.forEach(o => this.onOccupantAdded(o));
|
||||
this.listenTo(this.model.occupants, 'add', this.onOccupantAdded);
|
||||
this.listenTo(this.model.occupants, 'change', this.renderChatHistory);
|
||||
this.listenTo(this.model.occupants, 'change:affiliation', this.onOccupantAffiliationChanged);
|
||||
this.listenTo(this.model.occupants, 'change:role', this.onOccupantRoleChanged);
|
||||
this.listenTo(this.model.occupants, 'change:show', this.showJoinOrLeaveNotification);
|
||||
this.listenTo(this.model.occupants, 'remove', this.onOccupantRemoved);
|
||||
|
||||
this.renderChatContent();
|
||||
// Register later due to await
|
||||
const user_settings = await _converse.api.user.settings.getModel();
|
||||
this.listenTo(user_settings, 'change:mucs_with_hidden_subject', this.renderHeading);
|
||||
@ -143,6 +137,7 @@ export default class MUCView extends BaseChatView {
|
||||
render(
|
||||
tpl_chatroom({
|
||||
sidebar_hidden,
|
||||
'chatview': this,
|
||||
'model': this.model,
|
||||
'occupants': this.model.occupants,
|
||||
'show_sidebar':
|
||||
@ -157,7 +152,6 @@ export default class MUCView extends BaseChatView {
|
||||
|
||||
this.notifications = this.querySelector('.chat-content__notifications');
|
||||
this.content = this.querySelector('.chat-content');
|
||||
this.msgs_container = this.querySelector('.chat-content__messages');
|
||||
this.help_container = this.querySelector('.chat-content__help');
|
||||
|
||||
this.renderBottomPanel();
|
||||
|
@ -15,16 +15,6 @@ export default class BaseChatView extends ElementView {
|
||||
initDebounced () {
|
||||
this.markScrolled = debounce(this._markScrolled, 100);
|
||||
this.debouncedScrollDown = debounce(this.scrollDown, 100);
|
||||
|
||||
// For tests that use Jasmine.Clock we want to turn of
|
||||
// debouncing, since setTimeout breaks.
|
||||
if (api.settings.get('debounced_content_rendering')) {
|
||||
this.renderChatHistory = debounce(() => this.renderChatContent(false), 100);
|
||||
this.renderNotifications = debounce(() => this.renderChatContent(true), 100);
|
||||
} else {
|
||||
this.renderChatHistory = () => this.renderChatContent(false);
|
||||
this.renderNotifications = () => this.renderChatContent(true);
|
||||
}
|
||||
}
|
||||
|
||||
async renderHeading () {
|
||||
@ -32,20 +22,6 @@ export default class BaseChatView extends ElementView {
|
||||
render(tpl, this.querySelector('.chat-head-chatbox'));
|
||||
}
|
||||
|
||||
renderChatContent (msgs_by_ref = false) {
|
||||
if (!this.tpl_chat_content) {
|
||||
this.tpl_chat_content = o => {
|
||||
return html`
|
||||
<converse-chat-content .chatview=${this} .messages=${o.messages} notifications=${o.notifications}>
|
||||
</converse-chat-content>
|
||||
`;
|
||||
};
|
||||
}
|
||||
const msg_models = this.model.messages.models;
|
||||
const messages = msgs_by_ref ? msg_models : Array.from(msg_models);
|
||||
render(this.tpl_chat_content({ messages, 'notifications': this.getNotifications() }), this.msgs_container);
|
||||
}
|
||||
|
||||
renderHelpMessages () {
|
||||
render(
|
||||
html`
|
||||
@ -183,7 +159,8 @@ export default class BaseChatView extends ElementView {
|
||||
maintainScrollTop () {
|
||||
const pos = this.model.get('scrollTop');
|
||||
if (pos) {
|
||||
this.msgs_container.scrollTop = pos;
|
||||
const msgs_container = this.querySelector('.chat-content__messages');
|
||||
msgs_container.scrollTop = pos;
|
||||
} else {
|
||||
this.scrollDown();
|
||||
}
|
||||
@ -312,8 +289,6 @@ export default class BaseChatView extends ElementView {
|
||||
}
|
||||
|
||||
onMessageAdded (message) {
|
||||
this.renderChatHistory();
|
||||
|
||||
if (u.isNewMessage(message)) {
|
||||
if (message.get('sender') === 'me') {
|
||||
// We remove the "scrolled" flag so that the chat area
|
||||
@ -403,13 +378,14 @@ export default class BaseChatView extends ElementView {
|
||||
_markScrolled (ev) {
|
||||
let scrolled = true;
|
||||
let scrollTop = null;
|
||||
const msgs_container = this.querySelector('.chat-content__messages');
|
||||
const is_at_bottom =
|
||||
this.msgs_container.scrollTop + this.msgs_container.clientHeight >= this.msgs_container.scrollHeight - 62; // sigh...
|
||||
msgs_container.scrollTop + msgs_container.clientHeight >= msgs_container.scrollHeight - 62; // sigh...
|
||||
|
||||
if (is_at_bottom) {
|
||||
scrolled = false;
|
||||
this.onScrolledDown();
|
||||
} else if (this.msgs_container.scrollTop === 0) {
|
||||
} else if (msgs_container.scrollTop === 0) {
|
||||
/**
|
||||
* Triggered once the chat's message area has been scrolled to the top
|
||||
* @event _converse#chatBoxScrolledUp
|
||||
@ -439,11 +415,12 @@ export default class BaseChatView extends ElementView {
|
||||
'scrollTop': null
|
||||
});
|
||||
}
|
||||
if (this.msgs_container.scrollTo) {
|
||||
const behavior = this.msgs_container.scrollTop ? 'smooth' : 'auto';
|
||||
this.msgs_container.scrollTo({ 'top': this.msgs_container.scrollHeight, behavior });
|
||||
const msgs_container = this.querySelector('.chat-content__messages');
|
||||
if (msgs_container.scrollTo) {
|
||||
const behavior = msgs_container.scrollTop ? 'smooth' : 'auto';
|
||||
msgs_container.scrollTo({ 'top': msgs_container.scrollHeight, behavior });
|
||||
} else {
|
||||
this.msgs_container.scrollTop = this.msgs_container.scrollHeight;
|
||||
msgs_container.scrollTop = msgs_container.scrollHeight;
|
||||
}
|
||||
this.onScrolledDown();
|
||||
}
|
||||
@ -524,14 +501,16 @@ export default class BaseChatView extends ElementView {
|
||||
if (api.settings.get('view_mode') === 'overlayed') {
|
||||
// XXX: Chrome flexbug workaround. The .chat-content area
|
||||
// doesn't resize when the textarea is resized to its original size.
|
||||
this.msgs_container.parentElement.style.display = 'none';
|
||||
const msgs_container = this.querySelector('.chat-content__messages');
|
||||
msgs_container.parentElement.style.display = 'none';
|
||||
}
|
||||
textarea.removeAttribute('disabled');
|
||||
u.removeClass('disabled', textarea);
|
||||
|
||||
if (api.settings.get('view_mode') === 'overlayed') {
|
||||
// XXX: Chrome flexbug workaround.
|
||||
this.msgs_container.parentElement.style.display = '';
|
||||
const msgs_container = this.querySelector('.chat-content__messages');
|
||||
msgs_container.parentElement.style.display = '';
|
||||
}
|
||||
// Suppress events, otherwise superfluous CSN gets set
|
||||
// immediately after the message, causing rate-limiting issues.
|
||||
|
@ -6,7 +6,11 @@ export default (o) => html`
|
||||
<div class="chat-head chat-head-chatbox row no-gutters"></div>
|
||||
<div class="chat-body">
|
||||
<div class="chat-content ${ o.show_send_button ? 'chat-content-sendbutton' : '' }" aria-live="polite">
|
||||
<div class="chat-content__messages" @scroll=${o.markScrolled}></div>
|
||||
<converse-chat-content
|
||||
class="chat-content__messages"
|
||||
.chatview=${o.chatview}
|
||||
@scroll=${o.markScrolled}></converse-chat-content>
|
||||
|
||||
<div class="chat-content__help"></div>
|
||||
</div>
|
||||
<div class="bottom-panel">
|
||||
|
@ -7,7 +7,11 @@ export default (o) => html`
|
||||
<div class="chat-body chatroom-body row no-gutters">
|
||||
<div class="chat-area col">
|
||||
<div class="chat-content ${ o.show_send_button ? 'chat-content-sendbutton' : '' }" aria-live="polite">
|
||||
<div class="chat-content__messages" @scroll=${o.markScrolled}></div>
|
||||
<converse-chat-content
|
||||
class="chat-content__messages"
|
||||
.chatview=${o.chatview}
|
||||
@scroll=${o.markScrolled}></converse-chat-content>
|
||||
|
||||
<div class="chat-content__help"></div>
|
||||
</div>
|
||||
<div class="bottom-panel"></div>
|
||||
|
Loading…
Reference in New Issue
Block a user