Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion app/api/server/v1/chat.js
Original file line number Diff line number Diff line change
Expand Up @@ -128,7 +128,7 @@ API.v1.addRoute('chat.pinMessage', { authRequired: true }, {

API.v1.addRoute('chat.postMessage', { authRequired: true }, {
post() {
const messageReturn = processWebhookMessage(this.bodyParams, this.user, undefined, true)[0];
const messageReturn = processWebhookMessage(this.bodyParams, this.user)[0];

if (!messageReturn) {
return API.v1.failure('unknown-error');
Expand Down
2 changes: 1 addition & 1 deletion app/integrations/server/api/api.js
Original file line number Diff line number Diff line change
Expand Up @@ -247,7 +247,7 @@ function executeIntegrationRest() {
this.bodyParams.bot = { i: this.integration._id };

try {
const message = processWebhookMessage(this.bodyParams, this.user, defaultValues);
const message = processWebhookMessage(this.bodyParams, this.user, defaultValues, this.integration);
if (_.isEmpty(message)) {
return API.v1.failure('unknown-error');
}
Expand Down
2 changes: 1 addition & 1 deletion app/integrations/server/lib/triggerHandler.js
Original file line number Diff line number Diff line change
Expand Up @@ -205,7 +205,7 @@ integrations.triggerHandler = new class RocketChatIntegrationHandler {
message.channel = `#${ tmpRoom._id }`;
}

message = processWebhookMessage(message, user, defaultValues);
message = processWebhookMessage(message, user, defaultValues, trigger);
return message;
}

Expand Down
31 changes: 22 additions & 9 deletions app/lib/server/functions/processWebhookMessage.js
Original file line number Diff line number Diff line change
@@ -1,14 +1,21 @@
import { Meteor } from 'meteor/meteor';
import _ from 'underscore';
import s from 'underscore.string';
import mem from 'mem';

import { getRoomByNameOrIdWithOptionToJoin } from './getRoomByNameOrIdWithOptionToJoin';
import { sendMessage } from './sendMessage';
import { validateRoomMessagePermissions } from '../../../authorization/server/functions/canSendMessage';
import { Subscriptions } from '../../../models';
import { getDirectMessageByIdWithOptionToJoin, getDirectMessageByNameOrIdWithOptionToJoin } from './getDirectMessageByNameOrIdWithOptionToJoin';

export const processWebhookMessage = function(messageObj, user, defaultValues = { channel: '', alias: '', avatar: '', emoji: '' }, mustBeJoined = false) {
// show deprecation warning only once per hour for each integration
const showDeprecation = mem(({ integration, channels, username }, error) => {
console.warn(`Warning: The integration "${ integration }" failed to send a message to "${ [].concat(channels).join(',') }" because user "${ username }" doesn't have permission or is not a member of the channel.`);
console.warn('This behavior is deprecated and starting from version v4.0.0 the following error will be thrown and the message will not be sent.');
console.error(error);
}, { maxAge: 360000, cacheKey: (integration) => JSON.stringify(integration) });

export const processWebhookMessage = function(messageObj, user, defaultValues = { channel: '', alias: '', avatar: '', emoji: '' }, integration = null) {
const sentData = [];
const channels = [].concat(messageObj.channel || messageObj.roomId || defaultValues.channel);

Expand Down Expand Up @@ -44,12 +51,7 @@ export const processWebhookMessage = function(messageObj, user, defaultValues =
throw new Meteor.Error('invalid-channel');
}

if (mustBeJoined && !Subscriptions.findOneByRoomIdAndUserId(room._id, user._id, { fields: { _id: 1 } })) {
// throw new Meteor.Error('invalid-room', 'Invalid room provided to send a message to, must be joined.');
throw new Meteor.Error('invalid-channel'); // Throwing the generic one so people can't "brute force" find rooms
}

if (messageObj.attachments && !_.isArray(messageObj.attachments)) {
if (messageObj.attachments && !Array.isArray(messageObj.attachments)) {
console.log('Attachments should be Array, ignoring value'.red, messageObj.attachments);
messageObj.attachments = undefined;
}
Expand Down Expand Up @@ -84,7 +86,18 @@ export const processWebhookMessage = function(messageObj, user, defaultValues =
}
}

validateRoomMessagePermissions(room, { uid: user._id, ...user });
try {
validateRoomMessagePermissions(room, { uid: user._id, ...user });
} catch (error) {
if (!integration) {
throw error;
}
showDeprecation({
integration: integration.name,
channels: integration.channel,
username: integration.username,
}, error);
}

const messageReturn = sendMessage(user, message, room);
sentData.push({ channel, message: messageReturn });
Expand Down