Skip to content

Commit

Permalink
composebox_typeahead: Add user groups to PM recipient typeahead.
Browse files Browse the repository at this point in the history
When a user group is selected, we add PM pills for each user in the
group instead of creating a PM pill for the user group.

We also prevent the current user or previous recipients from being
inserted as well.

Fixes #9971.
  • Loading branch information
synicalsyntax committed Jul 23, 2018
1 parent fbdc21a commit 6cd743d
Show file tree
Hide file tree
Showing 3 changed files with 96 additions and 40 deletions.
31 changes: 29 additions & 2 deletions frontend_tests/node_tests/composebox_typeahead.js
@@ -1,4 +1,5 @@
set_global('i18n', global.stub_i18n);
zrequire('dict');
zrequire('compose_state');
zrequire('ui_util');
zrequire('pm_conversations');
Expand All @@ -20,6 +21,9 @@ set_global('md5', function (s) {
var ct = composebox_typeahead;
var noop = function () {};

set_global('blueslip', {});
blueslip.error = noop;

var emoji_stadium = {
emoji_name: 'stadium',
emoji_url: 'TBD',
Expand Down Expand Up @@ -157,7 +161,7 @@ var hamletcharacters = {
name: "hamletcharacters",
id: 1,
description: "Characters of Hamlet",
members: [],
members: [100, 104],
};

var backend = {
Expand Down Expand Up @@ -469,7 +473,7 @@ run_test('initialize', () => {
$('#private_message_recipient').typeahead = function (options) {
// This should match the users added at the beginning of this test file.
var actual_value = options.source();
var expected_value = [hamlet, othello, cordelia, lear];
var expected_value = [hamlet, othello, cordelia, lear, hamletcharacters, backend];
assert.deepEqual(actual_value, expected_value);

// Even though the items passed to .highlighter() are the full
Expand Down Expand Up @@ -563,6 +567,29 @@ run_test('initialize', () => {
actual_value = options.updater(othello, click_event);
assert.equal(appended_name, 'Othello, the Moor of Venice');

var appended_names = [];
people.get_person_from_user_id = function (user_id) {
var users = {100: hamlet, 104: lear};
return users[user_id];
};
people.my_current_email = function () {
return 'hamlet@zulip.com';
};
compose_pm_pill.set_from_typeahead = function (item) {
appended_names.push(item.full_name);
};

var cleared = false;
function fake_clear() {
cleared = true;
}
compose_pm_pill.widget = {clear_text: fake_clear};

options.query = 'hamletchar';
options.updater(hamletcharacters, event);
assert.deepEqual(appended_names, ['King Lear']);
assert(cleared);

pm_recipient_typeahead_called = true;
};

Expand Down
77 changes: 39 additions & 38 deletions static/js/composebox_typeahead.js
Expand Up @@ -101,6 +101,14 @@ function query_matches_user_group_or_stream(query, user_group_or_stream) {
return query_matches_source_attrs(query, user_group_or_stream, ["name", "description"], " ");
}

function query_matches_person_or_user_group(query, item) {
if (user_groups.is_user_group(item)) {
return query_matches_user_group_or_stream(query, item);
}

return query_matches_person(query, item);
}

// Case-insensitive
function query_matches_emoji(query, emoji) {
// replaces spaces with underscores
Expand Down Expand Up @@ -424,13 +432,7 @@ exports.content_highlighter = function (item) {
if (this.completing === 'emoji') {
return typeahead_helper.render_emoji(item);
} else if (this.completing === 'mention') {
var rendered;
if (user_groups.is_user_group(item)) {
rendered = typeahead_helper.render_user_group(item);
} else {
rendered = typeahead_helper.render_person(item);
}
return rendered;
return typeahead_helper.render_person_or_user_group(item);
} else if (this.completing === 'stream') {
return typeahead_helper.render_stream(item);
} else if (this.completing === 'syntax') {
Expand Down Expand Up @@ -506,13 +508,7 @@ exports.compose_content_matcher = function (item) {
if (this.completing === 'emoji') {
return query_matches_emoji(this.token, item);
} else if (this.completing === 'mention') {
var matches;
if (user_groups.is_user_group(item)) {
matches = query_matches_user_group_or_stream(this.token, item);
} else {
matches = query_matches_person(this.token, item);
}
return matches;
return query_matches_person_or_user_group(this.token, item);
} else if (this.completing === 'stream') {
return query_matches_user_group_or_stream(this.token, item);
} else if (this.completing === 'syntax') {
Expand All @@ -524,23 +520,7 @@ exports.compose_matches_sorter = function (matches) {
if (this.completing === 'emoji') {
return typeahead_helper.sort_emojis(matches, this.token);
} else if (this.completing === 'mention') {
var users = [];
var groups = [];
_.each(matches, function (match) {
if (user_groups.is_user_group(match)) {
groups.push(match);
} else {
users.push(match);
}
});

var recipients = typeahead_helper.sort_recipients(
users,
this.token,
compose_state.stream_name(),
compose_state.subject(),
groups);
return recipients;
return typeahead_helper.sort_people_and_user_groups(this.token, matches);
} else if (this.completing === 'stream') {
return typeahead_helper.sort_streams(matches, this.token);
} else if (this.completing === 'syntax') {
Expand Down Expand Up @@ -641,23 +621,44 @@ exports.initialize = function () {
});

$("#private_message_recipient").typeahead({
source: compose_pm_pill.get_typeahead_items,
source: function () {
var people = compose_pm_pill.get_typeahead_items();
var groups = user_groups.get_realm_user_groups();
return people.concat(groups);
},
items: 5,
dropup: true,
fixed: true,
highlighter: function (item) {
return typeahead_helper.render_person(item);
return typeahead_helper.render_person_or_user_group(item);
},
matcher: function (item) {
return query_matches_person(this.query, item);
return query_matches_person_or_user_group(this.query, item);
},
sorter: function (matches) {
// var current_stream = compose_state.stream_name();
return typeahead_helper.sort_recipientbox_typeahead(
this.query, matches, "");
return typeahead_helper.sort_people_and_user_groups(this.query, matches);
},
updater: function (item) {
compose_pm_pill.set_from_typeahead(item);
if (user_groups.is_user_group(item)) {
_.chain(item.members.keys())
.map(function (user_id) {
return people.get_person_from_user_id(user_id);
}).filter(function (user) {
// filter out inserted users and current user from pill insertion
var inserted_users = user_pill.get_user_ids(compose_pm_pill.widget);
var current_user = people.is_current_user(user.email);
return inserted_users.indexOf(user.user_id) === -1 && !current_user;
}).each(function (user) {
compose_pm_pill.set_from_typeahead(user);
});
// clear input pill in the event no pills were added
var pill_widget = compose_pm_pill.widget;
if (pill_widget.clear_text !== undefined) {
pill_widget.clear_text();
}
} else {
compose_pm_pill.set_from_typeahead(item);
}
},
stopAdvance: true, // Do not advance to the next field on a tab or enter
});
Expand Down
28 changes: 28 additions & 0 deletions static/js/typeahead_helper.js
Expand Up @@ -119,6 +119,14 @@ exports.render_user_group = function (user_group) {
return html;
};

exports.render_person_or_user_group = function (item) {
if (user_groups.is_user_group(item)) {
return typeahead_helper.render_user_group(item);
}

return typeahead_helper.render_person(item);
};

exports.render_stream = function (stream) {
var desc = stream.description;
var short_desc = desc.substring(0, 35);
Expand Down Expand Up @@ -364,6 +372,26 @@ exports.sort_recipientbox_typeahead = function (query, matches, current_stream)
return exports.sort_recipients(matches, query, current_stream);
};

exports.sort_people_and_user_groups = function (query, matches) {
var users = [];
var groups = [];
_.each(matches, function (match) {
if (user_groups.is_user_group(match)) {
groups.push(match);
} else {
users.push(match);
}
});

var recipients = typeahead_helper.sort_recipients(
users,
query,
compose_state.stream_name(),
compose_state.subject(),
groups);
return recipients;
};

return exports;

}());
Expand Down

0 comments on commit 6cd743d

Please sign in to comment.