[FIX] Fix REST spotlight to allow searches with # and @ (#10410)

[FIX] REST spotlight API wasn't allowing searches with # and @
pull/10532/head
Marcos Spessatto Defendi 7 years ago committed by Rodrigo Nascimento
parent 2d123a8be7
commit fe663cf674
  1. 1
      packages/rocketchat-api/package.js
  2. 16
      packages/rocketchat-api/server/v1/misc.js
  3. 27
      packages/rocketchat-api/server/v1/spotlight.js
  4. 7
      packages/rocketchat-ui-sidenav/client/toolbar.js
  5. 10
      server/publications/spotlight.js
  6. 103
      tests/end-to-end/api/00-miscellaneous.js
  7. 40
      tests/end-to-end/api/11-spotlight.js

@ -44,5 +44,4 @@ Package.onUse(function(api) {
api.addFiles('server/v1/settings.js', 'server');
api.addFiles('server/v1/stats.js', 'server');
api.addFiles('server/v1/users.js', 'server');
api.addFiles('server/v1/spotlight.js', 'server');
});

@ -146,6 +146,22 @@ RocketChat.API.v1.addRoute('shield.svg', { authRequired: false }, {
}
});
RocketChat.API.v1.addRoute('spotlight', { authRequired: true }, {
get() {
check(this.queryParams, {
query: String
});
const { query } = this.queryParams;
const result = Meteor.runAsUser(this.userId, () =>
Meteor.call('spotlight', query)
);
return RocketChat.API.v1.success(result);
}
});
RocketChat.API.v1.addRoute('directory', { authRequired: true }, {
get() {
const { offset, count } = this.getPaginationItems();

@ -1,27 +0,0 @@
/**
This API returns the result of a query of rooms
and users, using Meteor's Spotlight method.
Method: GET
Route: api/v1/spotlight
Query params:
- query: The term to be searched.
*/
RocketChat.API.v1.addRoute('spotlight', { authRequired: true }, {
get() {
check(this.queryParams, {
query: String
});
const { query } = this.queryParams;
const result = Meteor.runAsUser(this.userId, () =>
Meteor.call('spotlight', query, null, {
rooms: true,
users: true
})
);
return RocketChat.API.v1.success(result);
}
});

@ -149,14 +149,15 @@ Template.toolbar.helpers({
query._id = query.rid;
delete query.rid;
}
if (filterText[0] === '#') {
const searchForChannels = filterText[0] === '#';
const searchForDMs = filterText[0] === '@';
if (searchForChannels) {
filterText = filterText.slice(1);
type.users = false;
query.t = 'c';
}
if (filterText[0] === '@') {
if (searchForDMs) {
filterText = filterText.slice(1);
type.rooms = false;
query.t = 'd';

@ -13,6 +13,16 @@ function fetchRooms(userId, rooms) {
Meteor.methods({
spotlight(text, usernames, type = {users: true, rooms: true}, rid) {
const searchForChannels = text[0] === '#';
const searchForDMs = text[0] === '@';
if (searchForChannels) {
type.users = false;
text = text.slice(1);
}
if (searchForDMs) {
type.rooms = false;
text = text.slice(1);
}
const regex = new RegExp(s.trim(s.escapeRegExp(text)), 'i');
const result = {
users: [],

@ -2,8 +2,8 @@
/* globals expect */
/* eslint no-unused-vars: 0 */
import {getCredentials, api, login, request, credentials} from '../../data/api-data.js';
import {adminEmail, adminUsername, adminPassword, password} from '../../data/user.js';
import { getCredentials, api, login, request, credentials } from '../../data/api-data.js';
import { adminEmail, adminUsername, adminPassword, password } from '../../data/user.js';
import supertest from 'supertest';
describe('miscellaneous', function() {
@ -73,7 +73,6 @@ describe('miscellaneous', function() {
.end(done);
});
describe('/directory', () => {
let user;
let testChannel;
@ -82,7 +81,7 @@ describe('miscellaneous', function() {
const email = `${ username }@rocket.chat`;
request.post(api('users.create'))
.set(credentials)
.send({email, name: username, username, password})
.send({ email, name: username, username, password })
.end((err, res) => {
user = res.body.user;
done();
@ -165,6 +164,102 @@ describe('miscellaneous', function() {
})
.end(done);
});
});
describe('[/spotlight]', () => {
let user;
before((done) => {
const username = `user.test.${ Date.now() }`;
const email = `${ username }@rocket.chat`;
request.post(api('users.create'))
.set(credentials)
.send({ email, name: username, username, password })
.end((err, res) => {
user = res.body.user;
done();
});
});
let userCredentials;
let testChannel;
before((done) => {
request.post(api('login'))
.send({
user: user.username,
password
})
.expect('Content-Type', 'application/json')
.expect(200)
.expect((res) => {
userCredentials = {};
userCredentials['X-Auth-Token'] = res.body.data.authToken;
userCredentials['X-User-Id'] = res.body.data.userId;
})
.end(done);
});
after(done => {
request.post(api('users.delete')).set(credentials).send({
userId: user._id
}).end(done);
user = undefined;
});
it('create an channel', (done) => {
request.post(api('channels.create'))
.set(userCredentials)
.send({
name: `channel.test.${ Date.now() }`
})
.end((err, res) => {
testChannel = res.body.channel;
done();
});
});
it('should fail when does not have query param', (done) => {
request.get(api('spotlight'))
.set(credentials)
.expect('Content-Type', 'application/json')
.expect(400)
.expect((res) => {
expect(res.body).to.have.property('success', false);
expect(res.body).to.have.property('error');
})
.end(done);
});
it('should return object inside users array when search by a valid user', (done) => {
request.get(api('spotlight'))
.query({
query: `@${ adminUsername }`
})
.set(credentials)
.expect('Content-Type', 'application/json')
.expect(200)
.expect((res) => {
expect(res.body).to.have.property('success', true);
expect(res.body).to.have.property('users').and.to.be.an('array');
expect(res.body.users[0]).to.have.property('_id');
expect(res.body.users[0]).to.have.property('name');
expect(res.body.users[0]).to.have.property('username');
expect(res.body.users[0]).to.have.property('status');
expect(res.body).to.have.property('rooms').and.to.be.an('array');
})
.end(done);
});
it('must return the object inside the room array when searching for a valid room and that user is not a member of it', (done) => {
request.get(api('spotlight'))
.query({
query: `#${ testChannel.name }`
})
.set(credentials)
.expect('Content-Type', 'application/json')
.expect(200)
.expect((res) => {
expect(res.body).to.have.property('success', true);
expect(res.body).to.have.property('users').and.to.be.an('array');
expect(res.body).to.have.property('rooms').and.to.be.an('array');
expect(res.body.rooms[0]).to.have.property('_id');
expect(res.body.rooms[0]).to.have.property('name');
expect(res.body.rooms[0]).to.have.property('t');
})
.end(done);
});
});
});

@ -1,40 +0,0 @@
/* eslint-env mocha */
/* globals expect */
import {getCredentials, api, request, credentials } from '../../data/api-data.js';
describe('[Spotlight]', function() {
this.retries(0);
before(done => getCredentials(done));
describe('[/spotlight]', () => {
it('should fail when does not have query param', (done) => {
request.get(api('spotlight'))
.set(credentials)
.expect('Content-Type', 'application/json')
.expect(400)
.expect((res) => {
expect(res.body).to.have.property('success', false);
expect(res.body).to.have.property('error');
})
.end(done);
});
it('should return objects for a valid query param', (done) => {
request.get(api('spotlight'))
.query({
query: 'foobar'
})
.set(credentials)
.expect('Content-Type', 'application/json')
.expect(200)
.expect((res) => {
expect(res.body).to.have.property('success', true);
expect(res.body).to.have.property('users').that.have.lengthOf(0);
expect(res.body).to.have.property('rooms').that.have.lengthOf(0);
})
.end(done);
});
});
});
Loading…
Cancel
Save