Commit 25d9880f authored by JC Brand's avatar JC Brand

Add config setting `allow_non_roster_messaging`

- Add a test case.
- Don't allow passing of `attrs` to `chats.open`. Not sure yet of the
  implications of this.
parent 246edf8a
...@@ -5,6 +5,7 @@ ...@@ -5,6 +5,7 @@
be prioritized above other auth mechanisms. [jcbrand] be prioritized above other auth mechanisms. [jcbrand]
- #755: create composer.json to add this project in packagist.org [fabiomontefuscolo] - #755: create composer.json to add this project in packagist.org [fabiomontefuscolo]
- #758: Bugfix. Render all resize drag handles for ChatRoomView. [LeoYReyes] - #758: Bugfix. Render all resize drag handles for ChatRoomView. [LeoYReyes]
- #762 Allow chatting with users not in your roster. [Ape, jcbrand]
- Bugfix. Cancel button shown while registration form is being fetched wasn't working - Bugfix. Cancel button shown while registration form is being fetched wasn't working
properly. [jcbrand] properly. [jcbrand]
- Bugfix. Login form wasn't rendered after logging out (when `auto_reconnect` is `true`). [jcbrand] - Bugfix. Login form wasn't rendered after logging out (when `auto_reconnect` is `true`). [jcbrand]
......
...@@ -173,6 +173,18 @@ Allows users to be invited to join MUC chat rooms. An "Invite" widget will ...@@ -173,6 +173,18 @@ Allows users to be invited to join MUC chat rooms. An "Invite" widget will
appear in the sidebar of the chat room where you can type in the JID of a user appear in the sidebar of the chat room where you can type in the JID of a user
to invite into the chat room. to invite into the chat room.
allow_non_roster_messaging
--------------------------
* Default: ``false``
Determines whether you'll receive messages from users that are not in your
roster. The XMPP specification allows for this (similar to email).
Setting this to `true` increases your chances of receiving spam (when using a
federated server), while setting it to `false` means that people not on your
roster can't contact you unless one (or both) of you subscribe to one another's
presence (i.e. adding as a roster contact).
allow_otr allow_otr
--------- ---------
......
...@@ -465,7 +465,7 @@ ...@@ -465,7 +465,7 @@
test_utils.openContactsPanel(converse); test_utils.openContactsPanel(converse);
spyOn(converse, 'emit'); spyOn(converse, 'emit');
var message = 'converse is a received message'; var message = 'This is a received message';
var sender_jid = mock.cur_names[0].replace(/ /g,'.').toLowerCase() + '@localhost'; var sender_jid = mock.cur_names[0].replace(/ /g,'.').toLowerCase() + '@localhost';
var msg = $msg({ var msg = $msg({
from: sender_jid, from: sender_jid,
...@@ -506,6 +506,63 @@ ...@@ -506,6 +506,63 @@
}); });
})); }));
describe("who is not on the roster", function () {
it("will open a chatbox and be displayed inside it if allow_non_roster_messaging is true", mock.initConverse(function (converse) {
converse.allow_non_roster_messaging = false;
spyOn(converse, 'emit');
var message = 'This is a received message from someone not on the roster';
var sender_jid = mock.cur_names[0].replace(/ /g,'.').toLowerCase() + '@localhost';
var msg = $msg({
from: sender_jid,
to: converse.connection.jid,
type: 'chat',
id: (new Date()).getTime()
}).c('body').t(message).up()
.c('active', {'xmlns': 'http://jabber.org/protocol/chatstates'}).tree();
// We don't already have an open chatbox for this user
expect(converse.chatboxes.get(sender_jid)).not.toBeDefined();
runs(function () {
// onMessage is a handler for received XMPP messages
converse.chatboxes.onMessage(msg);
expect(converse.emit).toHaveBeenCalledWith('message', msg);
});
waits(50);
runs(function () {
var chatbox = converse.chatboxes.get(sender_jid);
expect(chatbox).not.toBeDefined();
// onMessage is a handler for received XMPP messages
converse.allow_non_roster_messaging =true;
converse.chatboxes.onMessage(msg);
expect(converse.emit).toHaveBeenCalledWith('message', msg);
});
waits(50);
runs(function () {
// Check that the chatbox and its view now exist
var chatbox = converse.chatboxes.get(sender_jid);
var chatboxview = converse.chatboxviews.get(sender_jid);
expect(chatbox).toBeDefined();
expect(chatboxview).toBeDefined();
// Check that the message was received and check the message parameters
expect(chatbox.messages.length).toEqual(1);
var msg_obj = chatbox.messages.models[0];
expect(msg_obj.get('message')).toEqual(message);
expect(msg_obj.get('fullname')).toEqual(sender_jid);
expect(msg_obj.get('sender')).toEqual('them');
expect(msg_obj.get('delayed')).toEqual(false);
// Now check that the message appears inside the chatbox in the DOM
var $chat_content = chatboxview.$el.find('.chat-content');
var msg_txt = $chat_content.find('.chat-message').find('.chat-msg-content').text();
expect(msg_txt).toEqual(message);
var sender_txt = $chat_content.find('span.chat-msg-them').text();
expect(sender_txt.match(/^[0-9][0-9]:[0-9][0-9] /)).toBeTruthy();
});
}));
});
describe("and for which then an error message is received from the server", function () { describe("and for which then an error message is received from the server", function () {
afterEach(function () { afterEach(function () {
converse_api.user.logout(); converse_api.user.logout();
...@@ -719,12 +776,6 @@ ...@@ -719,12 +776,6 @@
})); }));
}); });
describe("when sent by the current user", function () {
it("will always cause the chat area to be scrolled down", mock.initConverse(function (converse) {
// TODO
}));
});
it("is ignored if it's a malformed headline message", mock.initConverse(function (converse) { it("is ignored if it's a malformed headline message", mock.initConverse(function (converse) {
test_utils.createContacts(converse, 'current'); test_utils.createContacts(converse, 'current');
test_utils.openControlBox(); test_utils.openControlBox();
......
...@@ -106,20 +106,20 @@ ...@@ -106,20 +106,20 @@
} }
}, },
'chats': { 'chats': {
'open': function (jids, attrs) { 'open': function (jids) {
var chatbox; var chatbox;
if (typeof jids === "undefined") { if (typeof jids === "undefined") {
converse.log("chats.open: You need to provide at least one JID", "error"); converse.log("chats.open: You need to provide at least one JID", "error");
return null; return null;
} else if (typeof jids === "string") { } else if (typeof jids === "string") {
chatbox = converse.wrappedChatBox( chatbox = converse.wrappedChatBox(
converse.chatboxes.getChatBox(jids, true, attrs).trigger('show') converse.chatboxes.getChatBox(jids, true).trigger('show')
); );
return chatbox; return chatbox;
} }
return _.map(jids, function (jid) { return _.map(jids, function (jid) {
chatbox = converse.wrappedChatBox( chatbox = converse.wrappedChatBox(
converse.chatboxes.getChatBox(jid, true, attrs).trigger('show') converse.chatboxes.getChatBox(jid, true).trigger('show')
); );
return chatbox; return chatbox;
}); });
......
...@@ -208,6 +208,7 @@ ...@@ -208,6 +208,7 @@
// ---------------------------- // ----------------------------
this.default_settings = { this.default_settings = {
allow_contact_requests: true, allow_contact_requests: true,
allow_non_roster_messaging: false,
animate: true, animate: true,
authentication: 'login', // Available values are "login", "prebind", "anonymous" and "external". authentication: 'login', // Available values are "login", "prebind", "anonymous" and "external".
auto_away: 0, // Seconds after which user status is set to 'away' auto_away: 0, // Seconds after which user status is set to 'away'
...@@ -230,6 +231,7 @@ ...@@ -230,6 +231,7 @@
keepalive: false, keepalive: false,
locked_domain: undefined, locked_domain: undefined,
message_carbons: false, // Support for XEP-280 message_carbons: false, // Support for XEP-280
message_storage: 'session',
password: undefined, password: undefined,
prebind: false, // XXX: Deprecated, use "authentication" instead. prebind: false, // XXX: Deprecated, use "authentication" instead.
prebind_url: null, prebind_url: null,
...@@ -238,7 +240,6 @@ ...@@ -238,7 +240,6 @@
show_only_online_users: false, show_only_online_users: false,
sid: undefined, sid: undefined,
storage: 'session', storage: 'session',
message_storage: 'session',
strict_plugin_dependencies: false, strict_plugin_dependencies: false,
synchronize_availability: true, // Set to false to not sync with other clients or with resource name of the particular client that it should synchronize with synchronize_availability: true, // Set to false to not sync with other clients or with resource name of the particular client that it should synchronize with
websocket_url: undefined, websocket_url: undefined,
...@@ -1494,20 +1495,25 @@ ...@@ -1494,20 +1495,25 @@
* Parameters: * Parameters:
* (String) jid - The JID of the user whose chat box we want * (String) jid - The JID of the user whose chat box we want
* (Boolean) create - Should a new chat box be created if none exists? * (Boolean) create - Should a new chat box be created if none exists?
* (Object) attrs - Optional chat box atributes.
*/ */
jid = jid.toLowerCase(); jid = jid.toLowerCase();
var bare_jid = Strophe.getBareJidFromJid(jid); var bare_jid = Strophe.getBareJidFromJid(jid);
var chatbox = this.get(bare_jid); var chatbox = this.get(bare_jid);
if (!chatbox && create) { if (!chatbox && create) {
var roster_info; var roster_info = {};
var roster_item = converse.roster.get(bare_jid); var roster_item = converse.roster.get(bare_jid);
if (roster_item !== undefined) { if (! _.isUndefined(roster_item)) {
roster_info = { roster_info = {
'fullname': _.isEmpty(roster_item.get('fullname'))? jid: roster_item.get('fullname'), 'fullname': _.isEmpty(roster_item.get('fullname'))? jid: roster_item.get('fullname'),
'image_type': roster_item.get('image_type'), 'image_type': roster_item.get('image_type'),
'image': roster_item.get('image'), 'image': roster_item.get('image'),
'url': roster_item.get('url'), 'url': roster_item.get('url'),
}; };
} else if (!converse.allow_non_roster_messaging) {
converse.log('Could not get roster item for JID '+bare_jid+
' and allow_non_roster_messaging is set to false', 'error');
return;
} }
chatbox = this.create(_.extend({ chatbox = this.create(_.extend({
'id': bare_jid, 'id': bare_jid,
...@@ -1516,7 +1522,7 @@ ...@@ -1516,7 +1522,7 @@
'image_type': DEFAULT_IMAGE_TYPE, 'image_type': DEFAULT_IMAGE_TYPE,
'image': DEFAULT_IMAGE, 'image': DEFAULT_IMAGE,
'url': '', 'url': '',
}, roster_info || {}, attrs || {})); }, roster_info, attrs || {}));
} }
return chatbox; return chatbox;
} }
......
...@@ -87,7 +87,7 @@ ...@@ -87,7 +87,7 @@
auto_login: true, auto_login: true,
jid: 'dummy@localhost', jid: 'dummy@localhost',
password: 'secret', password: 'secret',
debug: true debug: false
}, settings || {})); }, settings || {}));
converse.ChatBoxViews.prototype.trimChat = function () {}; converse.ChatBoxViews.prototype.trimChat = function () {};
return func(converse); return func(converse);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment