Chore: Move client helpers (#23178)

pull/23205/head^2
Tasso Evangelista 4 years ago committed by GitHub
parent 651167594c
commit a4a2fedcc5
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
  1. 2
      app/action-links/client/lib/actionLinks.js
  2. 2
      app/apps/client/RealAppsEngineUIHost.js
  3. 3
      app/apps/client/gameCenter/gameCenter.js
  4. 7
      app/apps/client/gameCenter/invitePlayers.js
  5. 80
      app/authorization/client/hasPermission.js
  6. 82
      app/authorization/client/hasPermission.ts
  7. 6
      app/autotranslate/client/lib/autotranslate.js
  8. 2
      app/callbacks/lib/callbacks.js
  9. 7
      app/chatpal-search/client/template/result.js
  10. 2
      app/e2e/client/logger.ts
  11. 2
      app/e2e/client/rocketchat.e2e.js
  12. 3
      app/emoji-custom/client/lib/emojiCustom.js
  13. 2
      app/emoji/client/emojiParser.js
  14. 1
      app/emoji/client/index.js
  15. 27
      app/emoji/client/lib/emojiRenderer.js
  16. 12
      app/lib/client/UserDeleted.js
  17. 5
      app/lib/client/index.js
  18. 53
      app/lib/client/lib/formatDate.js
  19. 10
      app/lib/client/lib/index.js
  20. 22
      app/lib/client/lib/startup/commands.js
  21. 42
      app/lib/client/lib/userRoles.js
  22. 3
      app/livechat/client/lib/dateHandler.js
  23. 4
      app/livechat/client/lib/stream/queueManager.js
  24. 3
      app/livechat/client/views/app/dialog/closeRoom.js
  25. 8
      app/livechat/client/views/app/livechatReadOnly.js
  26. 3
      app/livechat/client/views/app/tabbar/agentEdit.js
  27. 3
      app/livechat/client/views/app/tabbar/agentInfo.js
  28. 9
      app/livechat/client/views/app/tabbar/visitorInfo.js
  29. 3
      app/livechat/client/views/app/tabbar/visitorTranscript.js
  30. 4
      app/livestream/client/views/broadcastView.js
  31. 3
      app/livestream/client/views/liveStreamTab.js
  32. 2
      app/logger/client/logger.js
  33. 2
      app/message-mark-as-unread/client/actionButton.js
  34. 2
      app/message-pin/client/actionButton.js
  35. 4
      app/message-snippet/client/page/snippetPage.js
  36. 2
      app/message-star/client/actionButton.js
  37. 4
      app/models/client/models/Roles.js
  38. 14
      app/nrr/client/nrr.js
  39. 4
      app/otr/client/rocketchat.otr.room.js
  40. 2
      app/search/client/provider/result.js
  41. 3
      app/slashcommands-status/lib/status.js
  42. 3
      app/slashcommands-topic/lib/topic.js
  43. 2
      app/threads/client/components/ThreadComponent.tsx
  44. 4
      app/threads/client/flextab/messageBoxFollow.js
  45. 5
      app/threads/client/flextab/thread.js
  46. 5
      app/threads/client/messageAction/follow.js
  47. 5
      app/threads/client/messageAction/unfollow.js
  48. 3
      app/tokenpass/client/tokenpassChannelSettings.js
  49. 8
      app/ui-cached-collection/client/models/CachedCollection.js
  50. 3
      app/ui-login/client/login/form.js
  51. 6
      app/ui-master/client/body.js
  52. 10
      app/ui-master/client/main.js
  53. 2
      app/ui-message/client/message.html
  54. 16
      app/ui-message/client/message.js
  55. 4
      app/ui-message/client/messageBox/messageBox.js
  56. 2
      app/ui-message/client/messageBox/messageBoxTyping.js
  57. 6
      app/ui-message/client/messageThread.js
  58. 6
      app/ui-message/client/popup/messagePopupConfig.js
  59. 2
      app/ui-message/client/popup/messagePopupEmoji.html
  60. 9
      app/ui-utils/client/config.js
  61. 8
      app/ui-utils/client/index.js
  62. 17
      app/ui-utils/client/lib/Layout.js
  63. 13
      app/ui-utils/client/lib/MessageAction.js
  64. 10
      app/ui-utils/client/lib/RoomHistoryManager.js
  65. 8
      app/ui-utils/client/lib/RoomManager.js
  66. 26
      app/ui-utils/client/lib/avatar.js
  67. 28
      app/ui-utils/client/lib/callMethod.js
  68. 21
      app/ui-utils/client/lib/fireGlobalEvent.js
  69. 15
      app/ui-utils/client/lib/getUidDirectMessage.js
  70. 11
      app/ui-utils/client/lib/messageContext.js
  71. 3
      app/ui-utils/client/lib/modal.js
  72. 14
      app/ui-utils/client/lib/openRoom.js
  73. 23
      app/ui-utils/client/lib/prependReplies.js
  74. 7
      app/ui-utils/client/lib/rtl.js
  75. 63
      app/ui-utils/client/lib/warnUserDeletionMayRemoveRooms.js
  76. 3
      app/ui/client/components/header/header.js
  77. 2
      app/ui/client/components/icon.js
  78. 21
      app/ui/client/lib/chatMessages.js
  79. 2
      app/ui/client/lib/fileUpload.js
  80. 2
      app/ui/client/lib/iframeCommands.js
  81. 2
      app/ui/client/lib/notification.js
  82. 5
      app/ui/client/views/app/burger.js
  83. 16
      app/ui/client/views/app/lib/getCommonRoomEvents.js
  84. 11
      app/ui/client/views/app/room.js
  85. 6
      app/utils/client/index.js
  86. 22
      app/utils/client/lib/CustomTranslations.js
  87. 7
      app/utils/client/lib/RestApiClient.js
  88. 18
      app/utils/client/lib/baseuri.js
  89. 41
      app/utils/client/lib/canDeleteMessage.js
  90. 32
      app/utils/client/lib/handleError.js
  91. 14
      app/utils/client/lib/waitUntilFind.ts
  92. 2
      app/webrtc/client/WebRTCClass.js
  93. 2
      app/webrtc/client/screenShare.js
  94. 10
      client/.eslintrc.js
  95. 2
      client/components/CreateDiscussion/CreateDiscussion.tsx
  96. 2
      client/components/Emoji.js
  97. 2
      client/components/MarkdownText.tsx
  98. 2
      client/components/Message/Body/Link.tsx
  99. 2
      client/components/modals/FileUploadModal/FilePreview.tsx
  100. 2
      client/components/modals/FileUploadModal/GenericPreview.tsx
  101. Some files were not shown because too many files have changed in this diff Show More

@ -1,6 +1,6 @@
import { Meteor } from 'meteor/meteor';
import { handleError } from '../../../utils/client';
import { handleError } from '../../../../client/lib/utils/handleError';
import { Messages, Subscriptions } from '../../../models/client';
// Action Links namespace creation.

@ -4,8 +4,8 @@ import { AppsEngineUIHost } from '@rocket.chat/apps-engine/client/AppsEngineUIHo
import { Rooms } from '../../models/client';
import { APIClient } from '../../utils/client';
import { baseURI } from '../../utils/client/lib/baseuri';
import { getUserAvatarURL } from '../../utils/lib/getUserAvatarURL';
import { baseURI } from '../../../client/lib/baseURI';
export class RealAppsEngineUIHost extends AppsEngineUIHost {
constructor() {

@ -2,8 +2,9 @@ import { Template } from 'meteor/templating';
import { ReactiveVar } from 'meteor/reactive-var';
import { modal } from '../../../ui-utils/client';
import { APIClient, t, handleError } from '../../../utils/client';
import { APIClient, t } from '../../../utils/client';
import './gameCenter.html';
import { handleError } from '../../../../client/lib/utils/handleError';
const getExternalComponents = async (instance) => {
try {

@ -10,7 +10,8 @@ import { Session } from 'meteor/session';
import { AutoComplete } from '../../../meteor-autocomplete/client';
import { roomTypes } from '../../../utils/client';
import { ChatRoom } from '../../../models/client';
import { call, modal } from '../../../ui-utils/client';
import { modal } from '../../../ui-utils/client';
import { callWithErrorHandling } from '../../../../client/lib/utils/callWithErrorHandling';
import './invitePlayers.html';
@ -77,7 +78,7 @@ Template.InvitePlayers.events({
const privateGroupName = `${ name.replace(/\s/g, '-') }-${ Random.id(10) }`;
try {
const result = await call('createPrivateGroup', privateGroupName, users);
const result = await callWithErrorHandling('createPrivateGroup', privateGroupName, users);
roomTypes.openRouteLink(result.t, result);
@ -90,7 +91,7 @@ Template.InvitePlayers.events({
return;
}
call('sendMessage', {
callWithErrorHandling('sendMessage', {
_id: Random.id(),
rid: result.rid,
msg: TAPi18n.__('Apps_Game_Center_Play_Game_Together', { name }),

@ -1,80 +0,0 @@
import { Meteor } from 'meteor/meteor';
import { Template } from 'meteor/templating';
import { ChatPermissions } from './lib/ChatPermissions';
import * as Models from '../../models';
import { AuthorizationUtils } from '../lib/AuthorizationUtils';
function atLeastOne(permissions = [], scope, userId) {
userId = userId || Meteor.userId();
const user = Models.Users.findOneById(userId, { fields: { roles: 1 } });
return permissions.some((permissionId) => {
if (user && user.roles) {
if (AuthorizationUtils.isPermissionRestrictedForRoleList(permissionId, user.roles)) {
return false;
}
}
const permission = ChatPermissions.findOne(permissionId, { fields: { roles: 1 } });
const roles = (permission && permission.roles) || [];
return roles.some((roleName) => {
const role = Models.Roles.findOne(roleName, { fields: { scope: 1 } });
const roleScope = role && role.scope;
const model = Models[roleScope];
return model && model.isUserInRole && model.isUserInRole(userId, roleName, scope);
});
});
}
function all(permissions = [], scope, userId) {
userId = userId || Meteor.userId();
const user = Models.Users.findOneById(userId, { fields: { roles: 1 } });
return permissions.every((permissionId) => {
if (user && user.roles) {
if (AuthorizationUtils.isPermissionRestrictedForRoleList(permissionId, user.roles)) {
return false;
}
}
const permission = ChatPermissions.findOne(permissionId, { fields: { roles: 1 } });
const roles = (permission && permission.roles) || [];
return roles.some((roleName) => {
const role = Models.Roles.findOne(roleName, { fields: { scope: 1 } });
const roleScope = role && role.scope;
const model = Models[roleScope];
return model && model.isUserInRole && model.isUserInRole(userId, roleName, scope);
});
});
}
function _hasPermission(permissions, scope, strategy, userId) {
userId = userId || Meteor.userId();
if (!userId) {
return false;
}
if (!Models.AuthzCachedCollection.ready.get()) {
return false;
}
permissions = [].concat(permissions);
return strategy(permissions, scope, userId);
}
Template.registerHelper('hasPermission', function(permission, scope) {
return _hasPermission(permission, scope, atLeastOne);
});
Template.registerHelper('userHasAllPermission', function(userId, permission, scope) {
return _hasPermission(permission, scope, all, userId);
});
export const hasAllPermission = (permissions, scope) => _hasPermission(permissions, scope, all);
export const hasAtLeastOnePermission = (permissions, scope) => _hasPermission(permissions, scope, atLeastOne);
export const userHasAllPermission = (permissions, scope, userId) => _hasPermission(permissions, scope, all, userId);
export const hasPermission = hasAllPermission;

@ -0,0 +1,82 @@
import { Meteor } from 'meteor/meteor';
import { ChatPermissions } from './lib/ChatPermissions';
import * as Models from '../../models/client';
import { AuthorizationUtils } from '../lib/AuthorizationUtils';
import { IUser } from '../../../definition/IUser';
import { IRole } from '../../../definition/IRole';
import { IPermission } from '../../../definition/IPermission';
const isValidScope = (scope: IRole['scope']): scope is keyof typeof Models =>
typeof scope === 'string' && scope in Models;
const createPermissionValidator = (quantifier: (predicate: (permissionId: IPermission['_id']) => boolean) => boolean) =>
(permissionIds: IPermission['_id'][], scope: IRole['scope'], userId: IUser['_id']): boolean => {
const user: IUser | null = Models.Users.findOneById(userId, { fields: { roles: 1 } });
const checkEachPermission = quantifier.bind(permissionIds);
return checkEachPermission((permissionId) => {
if (user?.roles) {
if (AuthorizationUtils.isPermissionRestrictedForRoleList(permissionId, user.roles)) {
return false;
}
}
const permission: IPermission | null = ChatPermissions.findOne(permissionId, { fields: { roles: 1 } });
const roles = permission?.roles ?? [];
return roles.some((roleName) => {
const role = Models.Roles.findOne(roleName, { fields: { scope: 1 } });
const roleScope = role?.scope;
if (!isValidScope(roleScope)) {
return false;
}
const model = Models[roleScope];
return model.isUserInRole && model.isUserInRole(userId, roleName, scope);
});
});
};
const atLeastOne = createPermissionValidator(Array.prototype.some);
const all = createPermissionValidator(Array.prototype.every);
const validatePermissions = (
permissions: IPermission['_id'] | IPermission['_id'][],
scope: IRole['scope'],
predicate: (permissionIds: IPermission['_id'][], scope: IRole['scope'], userId: IUser['_id']) => boolean,
userId?: IUser['_id'] | null,
): boolean => {
userId = userId ?? Meteor.userId();
if (!userId) {
return false;
}
if (!Models.AuthzCachedCollection.ready.get()) {
return false;
}
return predicate(([] as IPermission['_id'][]).concat(permissions), scope, userId);
};
export const hasAllPermission = (
permissions: IPermission['_id'] | IPermission['_id'][],
scope?: IRole['scope'],
): boolean => validatePermissions(permissions, scope, all);
export const hasAtLeastOnePermission = (
permissions: IPermission['_id'] | IPermission['_id'][],
scope?: IRole['scope'],
): boolean => validatePermissions(permissions, scope, atLeastOne);
export const userHasAllPermission = (
permissions: IPermission['_id'] | IPermission['_id'][],
scope?: IRole['scope'],
userId?: IUser['_id'] | null,
): boolean => validatePermissions(permissions, scope, all, userId);
export const hasPermission = hasAllPermission;

@ -5,7 +5,7 @@ import mem from 'mem';
import { Subscriptions, Messages } from '../../../models';
import { hasPermission } from '../../../authorization';
import { call } from '../../../ui-utils/client';
import { callWithErrorHandling } from '../../../../client/lib/utils/callWithErrorHandling';
let userLanguage = 'en';
let username = '';
@ -76,8 +76,8 @@ export const AutoTranslate = {
c.stop();
[this.providersMetadata, this.supportedLanguages] = await Promise.all([
call('autoTranslate.getProviderUiMetadata'),
call('autoTranslate.getSupportedLanguages', 'en'),
callWithErrorHandling('autoTranslate.getProviderUiMetadata'),
callWithErrorHandling('autoTranslate.getSupportedLanguages', 'en'),
]);
});

@ -11,7 +11,7 @@ let logger = {
};
if (Meteor.isClient) {
const { getConfig } = require('../../ui-utils/client/config');
const { getConfig } = require('../../../client/lib/utils/getConfig');
timed = [getConfig('debug'), getConfig('timed-callbacks')].includes('true');
}

@ -2,10 +2,11 @@ import { ReactiveVar } from 'meteor/reactive-var';
import { Template } from 'meteor/templating';
import { TAPi18n } from 'meteor/rocketchat:tap-i18n';
import { DateFormat } from '../../../lib';
import { roomTypes, getURL } from '../../../utils';
import { Subscriptions } from '../../../models';
import { getUserAvatarURL as getAvatarUrl } from '../../../utils/lib/getUserAvatarURL';
import { formatTime } from '../../../../client/lib/utils/formatTime';
import { formatDate } from '../../../../client/lib/utils/formatDate';
const getDMUrl = (username) => getURL(`/direct/${ username }`);
@ -116,10 +117,10 @@ Template.ChatpalSearchSingleMessage.helpers({
},
time() {
return DateFormat.formatTime(this.created);
return formatTime(this.created);
},
date() {
return DateFormat.formatDate(this.created);
return formatDate(this.created);
},
getAvatarUrl,
});

@ -1,4 +1,4 @@
import { getConfig } from '../../ui-utils/client/config';
import { getConfig } from '../../../client/lib/utils/getConfig';
let debug: boolean | undefined = undefined;

@ -25,7 +25,7 @@ import { call } from '../../ui-utils';
import './events.js';
import './tabbar';
import { log, logError } from './logger';
import { waitUntilFind } from '../../utils/client/lib/waitUntilFind';
import { waitUntilFind } from '../../../client/lib/utils/waitUntilFind';
import { imperativeModal } from '../../../client/lib/imperativeModal';
import SaveE2EPasswordModal from './SaveE2EPasswordModal';
import EnterE2EPasswordModal from './EnterE2EPasswordModal';

@ -1,5 +1,4 @@
import { Meteor } from 'meteor/meteor';
import { Blaze } from 'meteor/blaze';
import { Session } from 'meteor/session';
import { escapeRegExp } from '@rocket.chat/string-helpers';
@ -26,8 +25,6 @@ export const getEmojiUrlFromName = function(name, extension) {
return `${ path }/emoji-custom/${ encodeURIComponent(name) }.${ extension }?_dc=${ random }`;
};
Blaze.registerHelper('emojiUrlFromName', getEmojiUrlFromName);
export const deleteEmojiCustom = function(emojiData) {
delete emoji.list[`:${ emojiData.name }:`];
const arrayIndex = emoji.packages.emojiCustom.emojisByCategory.rocket.indexOf(emojiData.name);

@ -1,4 +1,4 @@
import { isIE11 } from '../../ui-utils/client/lib/isIE11';
import { isIE11 } from '../../../client/lib/utils/isIE11';
import { emoji } from '../lib/rocketchat';
/*

@ -1,4 +1,3 @@
export { EmojiPicker } from './lib/EmojiPicker';
export { renderEmoji } from './lib/emojiRenderer';
export { emoji } from '../lib/rocketchat';
export { createEmojiMessageRenderer } from './emojiParser';

@ -1,27 +0,0 @@
import { Blaze } from 'meteor/blaze';
import { Template } from 'meteor/templating';
import { HTML } from 'meteor/htmljs';
import { emoji } from '../../lib/rocketchat';
import { isSetNotNull } from '../function-isSet';
export const renderEmoji = function(_emoji) {
if (isSetNotNull(() => emoji.list[_emoji].emojiPackage)) {
const { emojiPackage } = emoji.list[_emoji];
return emoji.packages[emojiPackage].render(_emoji);
}
};
Blaze.registerHelper('renderEmoji', renderEmoji);
Template.registerHelper('renderEmoji', new Template('renderEmoji', function() {
const view = this;
const _emoji = Blaze.getData(view);
if (isSetNotNull(() => emoji.list[_emoji].emojiPackage)) {
const { emojiPackage } = emoji.list[_emoji];
return new HTML.Raw(emoji.packages[emojiPackage].render(_emoji));
}
return '';
}));

@ -1,12 +0,0 @@
import { Meteor } from 'meteor/meteor';
import { ChatMessage } from '../../models';
import { Notifications } from '../../notifications';
Meteor.startup(function() {
Notifications.onLogged('Users:Deleted', ({ userId }) =>
ChatMessage.remove({
'u._id': userId,
}),
);
});

@ -1,11 +1,6 @@
import '../lib/startup/settingsOnLoadSiteUrl';
import '../lib/MessageTypes';
import './CustomTranslations';
import './OAuthProxy';
import './UserDeleted';
import './lib/startup/commands';
import './lib/settings';
import './lib/userRoles';
import './methods/sendMessage';
import './views/customFieldsForm.html';
import './views/customFieldsForm';

@ -1,53 +0,0 @@
import moment from 'moment';
import mem from 'mem';
import { Meteor } from 'meteor/meteor';
import { Tracker } from 'meteor/tracker';
import { getUserPreference, t } from '../../../utils';
import { settings } from '../../../settings';
let lastDay = t('yesterday');
let clockMode;
let sameDay;
const dayFormat = ['h:mm A', 'H:mm'];
Meteor.startup(() => Tracker.autorun(() => {
clockMode = getUserPreference(Meteor.userId(), 'clockMode', false);
sameDay = dayFormat[clockMode - 1] || settings.get('Message_TimeFormat');
lastDay = t('yesterday');
}));
export const formatTime = (time) => {
switch (clockMode) {
case 1:
case 2:
return moment(time).format(sameDay);
default:
return moment(time).format(settings.get('Message_TimeFormat'));
}
};
export const formatDateAndTime = (time) => {
switch (clockMode) {
case 1:
return moment(time).format('MMMM D, Y h:mm A');
case 2:
return moment(time).format('MMMM D, Y H:mm');
default:
return moment(time).format(settings.get('Message_TimeAndDateFormat'));
}
};
const sameElse = function(now) {
const diff = Math.ceil(this.diff(now, 'years', true));
return diff < 0 ? 'MMM D YYYY' : 'MMM D';
};
export const timeAgo = (date) => moment(date).calendar(null, {
lastDay: `[${ lastDay }]`,
sameDay,
lastWeek: 'dddd',
sameElse,
});
export const formatDate = mem((time) => moment(time).format(settings.get('Message_DateFormat')), { maxAge: 5000 });

@ -1,12 +1,2 @@
/*
What is this file? Great question! To make Rocket.Chat more "modular"
and to make the "rocketchat:lib" package more of a core package
with the libraries, this index file contains the exported members
for the *client* pieces of code which does include the shared
library files.
*/
import * as DateFormat from './formatDate';
export { RocketChatAnnouncement } from './RocketChatAnnouncement';
export { LoginPresence } from './LoginPresence';
export { DateFormat };

@ -1,22 +0,0 @@
import { Meteor } from 'meteor/meteor';
import { Tracker } from 'meteor/tracker';
import { slashCommands, APIClient } from '../../../../utils';
// Track logins and when they login, get the commands
(() => {
let oldUserId = null;
Tracker.autorun(() => {
const newUserId = Meteor.userId();
if (oldUserId === null && newUserId) {
APIClient.v1.get('commands.list').then(function _loadedCommands(result) {
result.commands.forEach((command) => {
slashCommands.commands[command.command] = command;
});
});
}
oldUserId = Meteor.userId();
});
})();

@ -1,42 +0,0 @@
import { Meteor } from 'meteor/meteor';
import { Tracker } from 'meteor/tracker';
import { UserRoles, RoomRoles, ChatMessage } from '../../../models';
import { handleError } from '../../../utils';
import { Notifications } from '../../../notifications';
Meteor.startup(function() {
Tracker.autorun(function() {
if (Meteor.userId()) {
Meteor.call('getUserRoles', (error, results) => {
if (error) {
return handleError(error);
}
for (const record of results) {
UserRoles.upsert({ _id: record._id }, record);
}
});
Notifications.onLogged('roles-change', function(role) {
if (role.type === 'added') {
if (role.scope) {
RoomRoles.upsert({ rid: role.scope, 'u._id': role.u._id }, { $setOnInsert: { u: role.u }, $addToSet: { roles: role._id } });
} else {
UserRoles.upsert({ _id: role.u._id }, { $addToSet: { roles: role._id }, $set: { username: role.u.username } });
ChatMessage.update({ 'u._id': role.u._id }, { $addToSet: { roles: role._id } }, { multi: true });
}
} else if (role.type === 'removed') {
if (role.scope) {
RoomRoles.update({ rid: role.scope, 'u._id': role.u._id }, { $pull: { roles: role._id } });
} else {
UserRoles.update({ _id: role.u._id }, { $pull: { roles: role._id } });
ChatMessage.update({ 'u._id': role.u._id }, { $pull: { roles: role._id } }, { multi: true });
}
} else if (role.type === 'changed') {
ChatMessage.update({ roles: role._id }, { $inc: { rerender: 1 } }, { multi: true });
}
});
}
});
});

@ -1,7 +1,6 @@
import moment from 'moment';
import { handleError } from '../../../utils';
import { handleError } from '../../../../client/lib/utils/handleError';
/**
* Check if given daterange matches any of pre-defined options

@ -3,7 +3,7 @@ import { Meteor } from 'meteor/meteor';
import { APIClient } from '../../../../utils/client';
import { LivechatInquiry } from '../../collections/LivechatInquiry';
import { inquiryDataStream } from './inquiry';
import { call } from '../../../../ui-utils/client';
import { callWithErrorHandling } from '../../../../../client/lib/utils/callWithErrorHandling';
import { getUserPreference } from '../../../../utils';
import { CustomSounds } from '../../../../custom-sounds/client/lib/CustomSounds';
@ -79,7 +79,7 @@ const addGlobalListener = () => {
const subscribe = async (userId) => {
const config = await call('livechat:getRoutingConfig');
const config = await callWithErrorHandling('livechat:getRoutingConfig');
if (config && config.autoAssignAgent) {
return;
}

@ -5,9 +5,10 @@ import { TAPi18n } from 'meteor/rocketchat:tap-i18n';
import { settings } from '../../../../../settings';
import { modal } from '../../../../../ui-utils/client';
import { APIClient, handleError, t } from '../../../../../utils';
import { APIClient, t } from '../../../../../utils';
import { hasRole } from '../../../../../authorization';
import './closeRoom.html';
import { handleError } from '../../../../../../client/lib/utils/handleError';
const validateRoomComment = (comment) => {
if (!settings.get('Livechat_request_comment_when_closing_conversation')) {

@ -4,7 +4,7 @@ import { ReactiveVar } from 'meteor/reactive-var';
import { FlowRouter } from 'meteor/kadira:flow-router';
import { ChatRoom, CachedChatRoom } from '../../../../models';
import { call } from '../../../../ui-utils/client';
import { callWithErrorHandling } from '../../../../../client/lib/utils/callWithErrorHandling';
import './livechatReadOnly.html';
import { APIClient } from '../../../../utils/client';
import { inquiryDataStream } from '../../lib/stream/inquiry';
@ -42,7 +42,7 @@ Template.livechatReadOnly.events({
const inquiry = instance.inquiry.get();
const { _id } = inquiry;
await call('livechat:takeInquiry', _id, { clientAction: true });
await callWithErrorHandling('livechat:takeInquiry', _id, { clientAction: true });
instance.loadInquiry(inquiry.rid);
},
@ -52,7 +52,7 @@ Template.livechatReadOnly.events({
const room = instance.room.get();
await call('livechat:resumeOnHold', room._id, { clientAction: true });
await callWithErrorHandling('livechat:resumeOnHold', room._id, { clientAction: true });
},
});
@ -64,7 +64,7 @@ Template.livechatReadOnly.onCreated(function() {
this.preparing = new ReactiveVar(true);
this.updateInquiry = async ({ clientAction, ...inquiry }) => {
if (clientAction === 'removed' || !await call('canAccessRoom', inquiry.rid, Meteor.userId())) {
if (clientAction === 'removed' || !await callWithErrorHandling('canAccessRoom', inquiry.rid, Meteor.userId())) {
// this will force to refresh the room
// since the client wont get notified of room changes when chats are on queue (no one assigned)
// a better approach should be performed when refactoring these templates to use react

@ -6,7 +6,8 @@ import toastr from 'toastr';
import { getCustomFormTemplate } from '../customTemplates/register';
import './agentEdit.html';
import { hasPermission } from '../../../../../authorization';
import { t, handleError, APIClient } from '../../../../../utils/client';
import { t, APIClient } from '../../../../../utils/client';
import { handleError } from '../../../../../../client/lib/utils/handleError';
Template.agentEdit.helpers({
canEditDepartment() {

@ -9,8 +9,9 @@ import s from 'underscore.string';
import { getCustomFormTemplate } from '../customTemplates/register';
import './agentInfo.html';
import { modal } from '../../../../../ui-utils';
import { t, handleError, APIClient } from '../../../../../utils/client';
import { t, APIClient } from '../../../../../utils/client';
import { hasPermission } from '../../../../../authorization';
import { handleError } from '../../../../../../client/lib/utils/handleError';
const customFieldsTemplate = () => getCustomFormTemplate('livechatAgentInfoForm');

@ -11,14 +11,15 @@ import UAParser from 'ua-parser-js';
import { modal } from '../../../../../ui-utils';
import { Subscriptions } from '../../../../../models';
import { settings } from '../../../../../settings';
import { t, handleError, roomTypes } from '../../../../../utils';
import { t, roomTypes } from '../../../../../utils';
import { hasRole, hasPermission, hasAtLeastOnePermission } from '../../../../../authorization';
import './visitorInfo.html';
import { APIClient } from '../../../../../utils/client';
import { RoomManager } from '../../../../../ui-utils/client';
import { DateFormat } from '../../../../../lib/client';
import { getCustomFormTemplate } from '../customTemplates/register';
import { Markdown } from '../../../../../markdown/client';
import { handleError } from '../../../../../../client/lib/utils/handleError';
import { formatDateAndTime } from '../../../../../../client/lib/utils/formatDateAndTime';
const isSubscribedToRoom = () => {
const data = Template.currentData();
@ -213,7 +214,7 @@ Template.visitorInfo.helpers({
roomClosedDateTime() {
const { closedAt } = this;
return DateFormat.formatDateAndTime(closedAt);
return formatDateAndTime(closedAt);
},
roomClosedBy() {
@ -249,7 +250,7 @@ Template.visitorInfo.helpers({
transcriptRequestedDateTime() {
const { requestedAt } = this;
return DateFormat.formatDateAndTime(requestedAt);
return formatDateAndTime(requestedAt);
},
markdown(text) {

@ -3,7 +3,8 @@ import { ReactiveVar } from 'meteor/reactive-var';
import { Template } from 'meteor/templating';
import toastr from 'toastr';
import { t, isEmail, handleError, roomTypes } from '../../../../../utils';
import { handleError } from '../../../../../../client/lib/utils/handleError';
import { t, isEmail, roomTypes } from '../../../../../utils';
import { APIClient } from '../../../../../utils/client';
import './visitorTranscript.html';

@ -3,8 +3,8 @@ import { ReactiveVar } from 'meteor/reactive-var';
import { Session } from 'meteor/session';
import { Template } from 'meteor/templating';
import { handleError } from '../../../utils';
import { settings } from '../../../settings';
import { handleError } from '../../../../client/lib/utils/handleError';
import { settings } from '../../../settings/client';
const getMedia = () => navigator.getUserMedia || navigator.webkitGetUserMedia || navigator.mozGetUserMedia || navigator.msGetUserMedia;
const createAndConnect = (url) => {

@ -9,11 +9,12 @@ import toastr from 'toastr';
import { auth } from '../oauth.js';
import { RocketChatAnnouncement } from '../../../lib';
import { popout } from '../../../ui-utils';
import { t, handleError } from '../../../utils';
import { t } from '../../../utils';
import { settings } from '../../../settings';
import { callbacks } from '../../../callbacks';
import { hasAllPermission } from '../../../authorization';
import { Users, Rooms } from '../../../models';
import { handleError } from '../../../../client/lib/utils/handleError';
export const call = (...args) => new Promise(function(resolve, reject) {
Meteor.call(...args, function(err, result) {

@ -1,7 +1,7 @@
import { Template } from 'meteor/templating';
import _ from 'underscore';
import { getConfig } from '../../ui-utils/client/config';
import { getConfig } from '../../../client/lib/utils/getConfig';
Template.log = !!(getConfig('debug') || getConfig('debug-template'));

@ -3,9 +3,9 @@ import { FlowRouter } from 'meteor/kadira:flow-router';
import { RoomManager, MessageAction } from '../../ui-utils';
import { messageArgs } from '../../ui-utils/client/lib/messageArgs';
import { handleError } from '../../utils';
import { ChatSubscription } from '../../models';
import { roomTypes } from '../../utils/client';
import { handleError } from '../../../client/lib/utils/handleError';
Meteor.startup(() => {
MessageAction.addButton({

@ -6,11 +6,11 @@ import toastr from 'toastr';
import { RoomHistoryManager, MessageAction } from '../../ui-utils';
import { messageArgs } from '../../ui-utils/client/lib/messageArgs';
import { handleError } from '../../utils';
import { settings } from '../../settings';
import { hasAtLeastOnePermission } from '../../authorization';
import { Rooms } from '../../models/client';
import { roomTypes } from '../../utils/client';
import { handleError } from '../../../client/lib/utils/handleError';
Meteor.startup(function() {
MessageAction.addButton({

@ -3,10 +3,10 @@ import { ReactiveVar } from 'meteor/reactive-var';
import { Template } from 'meteor/templating';
import moment from 'moment';
import { DateFormat } from '../../../lib';
import { settings } from '../../../settings';
import { Markdown } from '../../../markdown/client';
import { APIClient } from '../../../utils/client';
import { formatTime } from '../../../../client/lib/utils/formatTime';
Template.snippetPage.helpers({
snippet() {
@ -30,7 +30,7 @@ Template.snippetPage.helpers({
time() {
const snippet = Template.instance().message.get();
if (snippet !== undefined) {
return DateFormat.formatTime(snippet.ts);
return formatTime(snippet.ts);
}
},
});

@ -4,12 +4,12 @@ import { TAPi18n } from 'meteor/rocketchat:tap-i18n';
import { FlowRouter } from 'meteor/kadira:flow-router';
import toastr from 'toastr';
import { handleError } from '../../utils';
import { settings } from '../../settings';
import { RoomHistoryManager, MessageAction } from '../../ui-utils';
import { messageArgs } from '../../ui-utils/client/lib/messageArgs';
import { Rooms } from '../../models/client';
import { roomTypes } from '../../utils/client';
import { handleError } from '../../../client/lib/utils/handleError';
Meteor.startup(function() {
MessageAction.addButton({

@ -3,9 +3,7 @@ import { ReactiveVar } from 'meteor/reactive-var';
import * as Models from '..';
const Roles = new Mongo.Collection(null);
Object.assign(Roles, {
const Roles = Object.assign(new Mongo.Collection(null), {
findUsersInRole(name, scope, options) {
const role = this.findOne(name);
const roleScope = (role && role.scope) || 'Users';

@ -17,7 +17,7 @@ const makeCursorReactive = function(obj) {
}
};
Blaze.toHTMLWithDataNonReactive = function(content, data) {
const toHTMLWithDataNonReactive = function(content, data) {
makeCursorReactive(data);
if (data instanceof Spacebars.kw && Object.keys(data.hash).length > 0) {
@ -27,20 +27,14 @@ Blaze.toHTMLWithDataNonReactive = function(content, data) {
return Tracker.nonreactive(() => Blaze.toHTMLWithData(content, data));
};
Blaze.registerHelper('nrrargs', function(...args) {
return {
_arguments: args,
};
});
Blaze.renderNonReactive = function(templateName, data) {
const renderNonReactive = function(templateName, data) {
const { _arguments } = this.parentView.dataVar.get();
[templateName, data] = _arguments;
return Tracker.nonreactive(() => {
console.warn('Nrr template is deprecated');
const view = new Blaze.View('nrr', () => HTML.Raw(Blaze.toHTMLWithDataNonReactive(Template[templateName], data)));
const view = new Blaze.View('nrr', () => HTML.Raw(toHTMLWithDataNonReactive(Template[templateName], data)));
view.onViewReady(() => {
const { onViewReady } = Template[templateName];
@ -56,4 +50,4 @@ Blaze.renderNonReactive = function(templateName, data) {
});
};
Blaze.registerHelper('nrr', Blaze.Template('nrr', Blaze.renderNonReactive));
Template.nrr = new Blaze.Template('nrr', renderNonReactive);

@ -10,9 +10,9 @@ import toastr from 'toastr';
import { OTR } from './rocketchat.otr';
import { Notifications } from '../../notifications';
import { getUidDirectMessage } from '../../ui-utils/client/lib/getUidDirectMessage';
import { getUidDirectMessage } from '../../../client/lib/utils/getUidDirectMessage';
import { Presence } from '../../../client/lib/presence';
import { goToRoomById } from '../../../client/lib/goToRoomById';
import { goToRoomById } from '../../../client/lib/utils/goToRoomById';
import { imperativeModal } from '../../../client/lib/imperativeModal';
import GenericModal from '../../../client/components/GenericModal';

@ -11,7 +11,7 @@ import { MessageAction, RoomHistoryManager } from '../../../ui-utils';
import { messageArgs } from '../../../ui-utils/client/lib/messageArgs';
import { Rooms } from '../../../models/client';
import { getCommonRoomEvents } from '../../../ui/client/views/app/lib/getCommonRoomEvents';
import { goToRoomById } from '../../../../client/lib/goToRoomById';
import { goToRoomById } from '../../../../client/lib/utils/goToRoomById';
Meteor.startup(function() {
MessageAction.addButton({

@ -1,7 +1,7 @@
import { Meteor } from 'meteor/meteor';
import { TAPi18n } from 'meteor/rocketchat:tap-i18n';
import { handleError, slashCommands } from '../../utils';
import { slashCommands } from '../../utils';
import { api } from '../../../server/sdk/api';
function Status(command, params, item) {
@ -11,6 +11,7 @@ function Status(command, params, item) {
Meteor.call('setUserStatus', null, params, (err) => {
if (err) {
if (Meteor.isClient) {
const { handleError } = require('../../../client/lib/utils/handleError');
return handleError(err);
}

@ -1,6 +1,6 @@
import { Meteor } from 'meteor/meteor';
import { handleError, slashCommands } from '../../utils';
import { slashCommands } from '../../utils';
import { ChatRoom } from '../../models';
import { callbacks } from '../../callbacks';
import { hasPermission } from '../../authorization';
@ -11,6 +11,7 @@ function Topic(command, params, item) {
Meteor.call('saveRoomSettings', item.rid, 'roomTopic', params, (err) => {
if (err) {
if (Meteor.isClient) {
const { handleError } = require('../../../client/lib/utils/handleError');
return handleError(err);
}
throw err;

@ -16,7 +16,7 @@ import ThreadView from './ThreadView';
import { IMessage } from '../../../../definition/IMessage';
import { IRoom } from '../../../../definition/IRoom';
import { useTabBarOpenUserInfo } from '../../../../client/views/room/providers/ToolboxProvider';
import { mapMessageFromApi } from '../../../../client/lib/fromApi';
import { mapMessageFromApi } from '../../../../client/lib/utils/mapMessageFromApi';
const subscriptionFields = {};

@ -1,11 +1,11 @@
import { Template } from 'meteor/templating';
import { callWithErrorHandling } from '../../../../client/lib/utils/callWithErrorHandling';
import './messageBoxFollow.html';
import { call } from '../../../ui-utils/client';
Template.messageBoxFollow.events({
'click .js-follow'() {
const { tmid } = this;
call('followMessage', { mid: tmid });
callWithErrorHandling('followMessage', { mid: tmid });
},
});

@ -8,7 +8,7 @@ import { Tracker } from 'meteor/tracker';
import { FlowRouter } from 'meteor/kadira:flow-router';
import { chatMessages, ChatMessages } from '../../../ui';
import { call, keyCodes } from '../../../ui-utils/client';
import { callWithErrorHandling } from '../../../../client/lib/utils/callWithErrorHandling';
import { messageContext } from '../../../ui-utils/client/lib/messageContext';
import { upsertMessageBulk } from '../../../ui-utils/client/lib/RoomHistoryManager';
import { Messages } from '../../../models';
@ -20,6 +20,7 @@ import { settings } from '../../../settings/client';
import { callbacks } from '../../../callbacks/client';
import './messageBoxFollow';
import { getCommonRoomEvents } from '../../../ui/client/views/app/lib/getCommonRoomEvents';
import { keyCodes } from '../../../../client/lib/utils/keyCodes';
const sort = { ts: 1 };
@ -243,7 +244,7 @@ Template.thread.onCreated(async function() {
this.state.set('loading', true);
const messages = await call('getThreadMessages', { tmid });
const messages = await callWithErrorHandling('getThreadMessages', { tmid });
upsertMessageBulk({ msgs: messages }, this.Threads);

@ -5,9 +5,10 @@ import toastr from 'toastr';
import { Messages } from '../../../models/client';
import { settings } from '../../../settings/client';
import { MessageAction, call } from '../../../ui-utils/client';
import { MessageAction } from '../../../ui-utils/client';
import { messageArgs } from '../../../ui-utils/client/lib/messageArgs';
import { roomTypes } from '../../../utils/client';
import { callWithErrorHandling } from '../../../../client/lib/utils/callWithErrorHandling';
Meteor.startup(function() {
Tracker.autorun(() => {
@ -21,7 +22,7 @@ Meteor.startup(function() {
context: ['message', 'message-mobile', 'threads'],
async action() {
const { msg } = messageArgs(this);
call('followMessage', { mid: msg._id }).then(() =>
callWithErrorHandling('followMessage', { mid: msg._id }).then(() =>
toastr.success(TAPi18n.__('You_followed_this_message')),
);
},

@ -5,7 +5,8 @@ import toastr from 'toastr';
import { Messages } from '../../../models/client';
import { settings } from '../../../settings/client';
import { MessageAction, call } from '../../../ui-utils/client';
import { MessageAction } from '../../../ui-utils/client';
import { callWithErrorHandling } from '../../../../client/lib/utils/callWithErrorHandling';
import { messageArgs } from '../../../ui-utils/client/lib/messageArgs';
Meteor.startup(function() {
@ -20,7 +21,7 @@ Meteor.startup(function() {
context: ['message', 'message-mobile', 'threads'],
async action() {
const { msg } = messageArgs(this);
call('unfollowMessage', { mid: msg._id }).then(() =>
callWithErrorHandling('unfollowMessage', { mid: msg._id }).then(() =>
toastr.success(TAPi18n.__('You_unfollowed_this_message')),
);
},

@ -4,8 +4,9 @@ import { Template } from 'meteor/templating';
import { TAPi18n } from 'meteor/rocketchat:tap-i18n';
import toastr from 'toastr';
import { t, handleError } from '../../utils';
import { t } from '../../utils';
import { ChatRoom } from '../../models';
import { handleError } from '../../../client/lib/utils/handleError';
Template.channelSettings__tokenpass.helpers({
addDisabled() {

@ -10,8 +10,8 @@ import { Emitter } from '@rocket.chat/emitter';
import { callbacks } from '../../../callbacks';
import Notifications from '../../../notifications/client/lib/Notifications';
import { getConfig } from '../../../ui-utils/client/config';
import { callMethod } from '../../../ui-utils/client/lib/callMethod';
import { getConfig } from '../../../../client/lib/utils/getConfig';
import { call } from '../../../../client/lib/utils/call';
const wrap = (fn) => (...args) => new Promise((resolve, reject) => {
fn(...args, (err, result) => {
@ -218,7 +218,7 @@ export class CachedCollection extends Emitter {
async loadFromServer() {
const startTime = new Date();
const lastTime = this.updatedAt;
const data = await callMethod(this.methodName);
const data = await call(this.methodName);
this.log(`${ data.length } records loaded from server`);
data.forEach((record) => {
callbacks.run(`cachedCollection-loadFromServer-${ this.name }`, record, 'changed');
@ -318,7 +318,7 @@ export class CachedCollection extends Emitter {
this.log(`syncing from ${ this.updatedAt }`);
const data = await callMethod(this.syncMethodName, this.updatedAt);
const data = await call(this.syncMethodName, this.updatedAt);
let changes = [];
if (data.update && data.update.length > 0) {

@ -10,7 +10,8 @@ import toastr from 'toastr';
import { settings } from '../../../settings';
import { callbacks } from '../../../callbacks';
import { t, handleError } from '../../../utils';
import { t } from '../../../utils';
import { handleError } from '../../../../client/lib/utils/handleError';
Template.loginForm.helpers({
userName() {

@ -7,12 +7,14 @@ import { Template } from 'meteor/templating';
import { t } from '../../utils/client';
import { chatMessages } from '../../ui';
import { Layout, popover, fireGlobalEvent, RoomManager } from '../../ui-utils';
import { popover, RoomManager } from '../../ui-utils';
import { settings } from '../../settings';
import { ChatSubscription } from '../../models';
import './body.html';
import { imperativeModal } from '../../../client/lib/imperativeModal';
import GenericModal from '../../../client/components/GenericModal';
import { fireGlobalEvent } from '../../../client/lib/utils/fireGlobalEvent';
import { isLayoutEmbedded } from '../../../client/lib/utils/isLayoutEmbedded';
Template.body.onRendered(function() {
new Clipboard('.clipboard');
@ -99,7 +101,7 @@ Template.body.onRendered(function() {
};
this.autorun(() => {
if (Layout.isEmbedded()) {
if (isLayoutEmbedded()) {
$(document.body).on('click', 'a', handleMessageLinkClick);
} else {
$(document.body).off('click', 'a', handleMessageLinkClick);

@ -5,22 +5,22 @@ import { Session } from 'meteor/session';
import { Template } from 'meteor/templating';
import { getUserPreference } from '../../utils/client';
import { mainReady, Layout, iframeLogin } from '../../ui-utils';
import { mainReady, iframeLogin } from '../../ui-utils';
import { settings } from '../../settings';
import { CachedChatSubscription, Roles, Users } from '../../models';
import { CachedCollectionManager } from '../../ui-cached-collection';
import { tooltip } from '../../ui/client/components/tooltip';
import { callbacks } from '../../callbacks/client';
import { isSyncReady } from '../../../client/lib/userData';
import { fireGlobalEvent } from '../../ui-utils/client';
import { fireGlobalEvent } from '../../../client/lib/utils/fireGlobalEvent';
import './main.html';
import { isLayoutEmbedded } from '../../../client/lib/utils/isLayoutEmbedded';
callbacks.add('afterLogoutCleanUp', () => fireGlobalEvent('Custom_Script_On_Logout'), callbacks.priority.LOW, 'custom-script-on-logout');
Template.main.helpers({
removeSidenav: () => Layout.isEmbedded() && !/^\/admin/.test(FlowRouter.current().route.path),
removeSidenav: () => isLayoutEmbedded() && !/^\/admin/.test(FlowRouter.current().route.path),
logged: () => {
if (!!Meteor.userId() || (settings.get('Accounts_AllowAnonymousRead') === true && Session.get('forceLogin') !== true)) {
document.documentElement.classList.add('noscroll');
@ -78,7 +78,7 @@ Template.main.helpers({
fireGlobalEvent('Custom_Script_Logged_In');
},
embeddedVersion: () => {
if (Layout.isEmbedded()) {
if (isLayoutEmbedded()) {
return 'embedded-view';
}
},

@ -26,7 +26,7 @@
{{#if msg.emoji}}
<button aria-label="{{msg.u.username}}" class="thumb user-card-message" data-username="{{msg.u.username}}">
<div class="avatar">
{{> renderEmoji msg.emoji}}
{{{renderEmoji msg.emoji}}}
</div>
</button>
{{else}}

@ -5,18 +5,20 @@ import { Template } from 'meteor/templating';
import { TAPi18n } from 'meteor/rocketchat:tap-i18n';
import { escapeHTML } from '@rocket.chat/string-helpers';
import { timeAgo, formatDateAndTime } from '../../lib/client/lib/formatDate';
import { DateFormat } from '../../lib/client';
import { timeAgo } from '../../../client/lib/utils/timeAgo';
import { formatDateAndTime } from '../../../client/lib/utils/formatDateAndTime';
import { normalizeThreadTitle } from '../../threads/client/lib/normalizeThreadTitle';
import { MessageTypes, MessageAction } from '../../ui-utils/client';
import { RoomRoles, UserRoles, Roles } from '../../models/client';
import { Markdown } from '../../markdown/client';
import { t, roomTypes } from '../../utils';
import './messageThread';
import { AutoTranslate } from '../../autotranslate/client';
import { renderMentions } from '../../mentions/client/client';
import { renderMessageBody } from '../../../client/lib/renderMessageBody';
import { renderMessageBody } from '../../../client/lib/utils/renderMessageBody';
import { settings } from '../../settings/client';
import { formatTime } from '../../../client/lib/utils/formatTime';
import { formatDate } from '../../../client/lib/utils/formatDate';
import './messageThread';
import './message.html';
const renderBody = (msg, settings) => {
@ -203,11 +205,11 @@ Template.message.helpers({
time() {
const { msg, timeAgo: useTimeAgo } = this;
return useTimeAgo ? timeAgo(msg.ts) : DateFormat.formatTime(msg.ts);
return useTimeAgo ? timeAgo(msg.ts) : formatTime(msg.ts);
},
date() {
const { msg } = this;
return DateFormat.formatDate(msg.ts);
return formatDate(msg.ts);
},
isTemp() {
const { msg } = this;
@ -250,7 +252,7 @@ Template.message.helpers({
},
editTime() {
const { msg } = this;
return msg.editedAt ? DateFormat.formatDateAndTime(msg.editedAt) : '';
return msg.editedAt ? formatDateAndTime(msg.editedAt) : '';
},
editedBy() {
const { msg } = this;

@ -22,8 +22,6 @@ import {
messageBox,
popover,
call,
keyCodes,
isRTL,
} from '../../../ui-utils';
import {
t,
@ -37,6 +35,8 @@ import './messageBoxAudioMessage';
import './messageBoxNotSubscribed';
import './messageBox.html';
import './messageBoxReadOnly';
import { keyCodes } from '../../../../client/lib/utils/keyCodes';
import { isRTL } from '../../../../client/lib/utils/isRTL';
Template.messageBox.onCreated(function() {
this.state = new ReactiveDict();

@ -2,7 +2,7 @@ import { Template } from 'meteor/templating';
import { MsgTyping } from '../../../ui';
import { t } from '../../../utils';
import { getConfig } from '../../../ui-utils/client/config';
import { getConfig } from '../../../../client/lib/utils/getConfig';
import './messageBoxTyping.html';
const maxUsernames = parseInt(getConfig('max-usernames-typing')) || 4;

@ -2,10 +2,10 @@ import { ReactiveVar } from 'meteor/reactive-var';
import { Template } from 'meteor/templating';
import _ from 'underscore';
import { call } from '../../ui-utils/client';
import { callWithErrorHandling } from '../../../client/lib/utils/callWithErrorHandling';
import { Messages } from '../../models/client';
import './messageThread.html';
import { normalizeThreadTitle } from '../../threads/client/lib/normalizeThreadTitle';
import './messageThread.html';
const findParentMessage = (() => {
const waiting = [];
@ -15,7 +15,7 @@ const findParentMessage = (() => {
const getMessages = _.debounce(async function() {
const _tmp = [...waiting];
waiting.length = 0;
resolve(call('getMessages', _tmp));
resolve(callWithErrorHandling('getMessages', _tmp));
pending = new Promise((r) => { resolve = r; });
}, 500);

@ -12,7 +12,7 @@ import { Messages, Subscriptions } from '../../../models/client';
import { settings } from '../../../settings/client';
import { hasAllPermission, hasAtLeastOnePermission } from '../../../authorization/client';
import { EmojiPicker, emoji } from '../../../emoji';
import { call } from '../../../ui-utils/client';
import { callWithErrorHandling } from '../../../../client/lib/utils/callWithErrorHandling';
import { t, getUserPreference, slashCommands } from '../../../utils/client';
import { customMessagePopups } from './customMessagePopups';
import './messagePopupConfig.html';
@ -61,7 +61,7 @@ const reloadUsersFromRoomMessages = (rid, template) => {
const fetchUsersFromServer = _.throttle(async (filterText, records, rid, cb) => {
const usernames = records.map(({ username }) => username);
const { users } = await call('spotlight', filterText, usernames, { users: true, mentions: true }, rid);
const { users } = await callWithErrorHandling('spotlight', filterText, usernames, { users: true, mentions: true }, rid);
if (!users || users.length <= 0) {
return;
@ -95,7 +95,7 @@ const fetchRoomsFromServer = _.throttle(async (filterText, records, rid, cb) =>
return;
}
const { rooms } = await call('spotlight', filterText, null, { rooms: true, mentions: true }, rid);
const { rooms } = await callWithErrorHandling('spotlight', filterText, null, { rooms: true, mentions: true }, rid);
if (!rooms || rooms.length <= 0) {
return;

@ -1,4 +1,4 @@
<template name="messagePopupEmoji">
{{> renderEmoji _id}}
{{{renderEmoji _id}}}
{{_id}}
</template>

@ -1,9 +0,0 @@
import { Meteor } from 'meteor/meteor';
const url = new URL(window.location);
const keys = new Set();
export const getConfig = (key) => {
keys.add(key);
return url.searchParams.get(key) || Meteor._localStorage.getItem(`rc-config-${ key }`);
};

@ -2,7 +2,6 @@ export { modal } from './lib/modal';
export { SideNav } from './lib/SideNav';
export { AccountBox } from './lib/AccountBox';
export { menu } from './lib/menu';
export { call } from './lib/callMethod';
export { MessageAction } from './lib/MessageAction';
export { messageBox } from './lib/messageBox';
export { popover } from './lib/popover';
@ -10,18 +9,11 @@ export { readMessage } from './lib/readMessages';
export { RoomManager } from './lib/RoomManager';
export { upsertMessage, RoomHistoryManager, normalizeThreadMessage } from './lib/RoomHistoryManager';
export { mainReady } from './lib/mainReady';
export { Layout } from './lib/Layout';
export { IframeLogin, iframeLogin } from './lib/IframeLogin';
export { fireGlobalEvent } from './lib/fireGlobalEvent';
export { getAvatarAsPng } from './lib/avatar';
export { popout } from './lib/popout';
export { messageProperties } from '../lib/MessageProperties';
export { MessageTypes } from '../lib/MessageTypes';
export { Message } from '../lib/Message';
export { openRoom } from './lib/openRoom';
export { warnUserDeletionMayRemoveRooms } from './lib/warnUserDeletionMayRemoveRooms';
export * from './lib/rtl';
export * from './lib/keyCodes';
export * from './lib/prependReplies';
export * from './lib/collapseArrow';
export * from './lib/messageArgs';

@ -1,17 +0,0 @@
import { Tracker } from 'meteor/tracker';
import { FlowRouter } from 'meteor/kadira:flow-router';
import { ReactiveVar } from 'meteor/reactive-var';
export const Layout = new class RocketChatLayout {
constructor() {
this.embedded = new ReactiveVar();
Tracker.autorun(() => {
this.layout = FlowRouter.getQueryParam('layout');
this.embedded.set(this.layout === 'embedded');
});
}
isEmbedded() {
return this.embedded.get();
}
}();

@ -10,21 +10,14 @@ import { Tracker } from 'meteor/tracker';
import { Session } from 'meteor/session';
import { messageArgs } from './messageArgs';
import { roomTypes, canDeleteMessage } from '../../../utils/client';
import { roomTypes } from '../../../utils/client';
import { Messages, Rooms, Subscriptions } from '../../../models/client';
import { hasAtLeastOnePermission, hasPermission } from '../../../authorization/client';
import { modal } from './modal';
import { imperativeModal } from '../../../../client/lib/imperativeModal';
import ReactionList from '../../../../client/components/modals/ReactionList';
const call = (method, ...args) => new Promise((resolve, reject) => {
Meteor.call(method, ...args, function(err, data) {
if (err) {
return reject(err);
}
resolve(data);
});
});
import { call } from '../../../../client/lib/utils/call';
import { canDeleteMessage } from '../../../../client/lib/utils/canDeleteMessage';
export const addMessageToList = (messagesList, message) => {
// checks if the message is not already on the list

@ -10,10 +10,10 @@ import { escapeHTML } from '@rocket.chat/string-helpers';
import { promises } from '../../../promises/client';
import { RoomManager } from './RoomManager';
import { readMessage } from './readMessages';
import { renderMessageBody } from '../../../../client/lib/renderMessageBody';
import { getConfig } from '../config';
import { renderMessageBody } from '../../../../client/lib/utils/renderMessageBody';
import { getConfig } from '../../../../client/lib/utils/getConfig';
import { ChatMessage, ChatSubscription, ChatRoom } from '../../../models';
import { call } from './callMethod';
import { callWithErrorHandling } from '../../../../client/lib/utils/callWithErrorHandling';
import { filterMarkdown } from '../../../markdown/lib/markdown';
import { getUserPreference } from '../../../utils/client';
@ -190,7 +190,7 @@ export const RoomHistoryManager = new class extends Emitter {
}
const showMessageInMainThread = getUserPreference(Meteor.userId(), 'showMessageInMainThread', false);
const result = await call('loadHistory', rid, ts, limit, ls, showMessageInMainThread);
const result = await callWithErrorHandling('loadHistory', rid, ts, limit, ls, showMessageInMainThread);
this.unqueue();
@ -269,7 +269,7 @@ export const RoomHistoryManager = new class extends Emitter {
const { ts } = lastMessage;
if (ts) {
const result = await call('loadNextMessages', rid, ts, limit);
const result = await callWithErrorHandling('loadNextMessages', rid, ts, limit);
upsertMessageBulk({
msgs: Array.from(result.messages).filter((msg) => msg.t !== 'command'),
subscription,

@ -6,7 +6,7 @@ import { Blaze } from 'meteor/blaze';
import { FlowRouter } from 'meteor/kadira:flow-router';
import _ from 'underscore';
import { fireGlobalEvent } from './fireGlobalEvent';
import { fireGlobalEvent } from '../../../../client/lib/utils/fireGlobalEvent';
import { upsertMessage, RoomHistoryManager } from './RoomHistoryManager';
import { mainReady } from './mainReady';
import { menu } from './menu';
@ -15,9 +15,9 @@ import { callbacks } from '../../../callbacks';
import { Notifications } from '../../../notifications';
import { CachedChatRoom, ChatMessage, ChatSubscription, CachedChatSubscription, ChatRoom } from '../../../models';
import { CachedCollectionManager } from '../../../ui-cached-collection';
import { getConfig } from '../config';
import { getConfig } from '../../../../client/lib/utils/getConfig';
import { ROOM_DATA_STREAM } from '../../../utils/stream/constants';
import { call } from '..';
import { callWithErrorHandling } from '../../../../client/lib/utils/callWithErrorHandling';
import { RoomManager as NewRoomManager } from '../../../../client/lib/RoomManager';
const maxRoomsOpen = parseInt(getConfig('maxRoomsOpen')) || 5;
@ -286,7 +286,7 @@ const loadMissedMessages = async function(rid) {
try {
const result = await call('loadMissedMessages', rid, lastMessage.ts);
const result = await callWithErrorHandling('loadMissedMessages', rid, lastMessage.ts);
if (result) {
const subscription = ChatSubscription.findOne({ rid });
return Promise.all(Array.from(result).map((msg) => upsertMessage({ msg, subscription })));

@ -1,26 +0,0 @@
import { Blaze } from 'meteor/blaze';
import { getUserAvatarURL } from '../../../utils/lib/getUserAvatarURL';
Blaze.registerHelper('avatarUrlFromUsername', getUserAvatarURL);
export const getAvatarAsPng = function(username, cb) {
const image = new Image();
image.src = getUserAvatarURL(username);
image.onload = function() {
const canvas = document.createElement('canvas');
canvas.width = image.width;
canvas.height = image.height;
const context = canvas.getContext('2d');
context.drawImage(image, 0, 0);
try {
return cb(canvas.toDataURL('image/png'));
} catch (e) {
return cb('');
}
};
image.onerror = function() {
return cb('');
};
return image.onerror;
};

@ -1,28 +0,0 @@
import { Meteor } from 'meteor/meteor';
import { handleError } from '../../../utils/client/lib/handleError';
/**
* Wraps a Meteor method into a Promise.
* This is particularly useful for creating information dialogs after execution of a Meteor method
* @param {The Meteor method to be calls} method
* @param {the method's parameters} params
*/
export const call = (method, ...params) => new Promise((resolve, reject) => {
Meteor.call(method, ...params, (err, result) => {
if (err) {
handleError(err);
return reject(err);
}
return resolve(result);
});
});
export const callMethod = (method, ...params) => new Promise((resolve, reject) => {
Meteor.call(method, ...params, (err, result) => {
if (err) {
return reject(err);
}
return resolve(result);
});
});

@ -1,21 +0,0 @@
import { Tracker } from 'meteor/tracker';
import { settings } from '../../../settings';
export const fireGlobalEvent = function _fireGlobalEvent(eventName, params) {
window.dispatchEvent(new CustomEvent(eventName, { detail: params }));
Tracker.autorun((computation) => {
const enabled = settings.get('Iframe_Integration_send_enable');
if (enabled === undefined) {
return;
}
computation.stop();
if (enabled) {
parent.postMessage({
eventName,
data: params,
}, settings.get('Iframe_Integration_send_target_origin'));
}
});
};

@ -1,15 +0,0 @@
import { Meteor } from 'meteor/meteor';
import { Rooms } from '../../../models/client';
export const getUidDirectMessage = (rid, userId = Meteor.userId()) => {
const room = Rooms.findOne({ _id: rid }, { fields: { uids: 1 } });
if (!room || !room.uids || room.uids.length > 2) {
return false;
}
const other = room && room.uids.filter((uid) => uid !== userId);
return other && other[0];
};

@ -6,12 +6,13 @@ import { Tracker } from 'meteor/tracker';
import { Subscriptions, Rooms, Users } from '../../../models/client';
import { hasPermission } from '../../../authorization/client';
import { settings } from '../../../settings/client';
import { getUserPreference, roomTypes, handleError } from '../../../utils/client';
import { getUserPreference, roomTypes } from '../../../utils/client';
import { AutoTranslate } from '../../../autotranslate/client';
import { Layout } from './Layout';
import { fireGlobalEvent } from './fireGlobalEvent';
import { fireGlobalEvent } from '../../../../client/lib/utils/fireGlobalEvent';
import { actionLinks } from '../../../action-links/client';
import { goToRoomById } from '../../../../client/lib/goToRoomById';
import { goToRoomById } from '../../../../client/lib/utils/goToRoomById';
import { isLayoutEmbedded } from '../../../../client/lib/utils/isLayoutEmbedded';
import { handleError } from '../../../../client/lib/utils/handleError';
const fields = { name: 1, username: 1, 'settings.preferences.enableMessageParserEarlyAdoption': 1, 'settings.preferences.showMessageInMainThread': 1, 'settings.preferences.autoImageLoad': 1, 'settings.preferences.saveMobileBandwidth': 1, 'settings.preferences.collapseMediaByDefault': 1, 'settings.preferences.hideRoles': 1 };
@ -34,7 +35,7 @@ export function messageContext({ rid } = Template.instance()) {
e.stopPropagation();
};
const runAction = Layout.isEmbedded() ? (msg, e) => {
const runAction = isLayoutEmbedded() ? (msg, e) => {
const { actionlink } = e.currentTarget.dataset;
return fireGlobalEvent('click-action-link', {
actionlink,

@ -2,8 +2,9 @@ import { Meteor } from 'meteor/meteor';
import { Blaze } from 'meteor/blaze';
import { Template } from 'meteor/templating';
import { t, getUserPreference, handleError } from '../../../utils';
import { t, getUserPreference } from '../../../utils';
import './modal.html';
import { handleError } from '../../../../client/lib/utils/handleError';
let modalStack = [];

@ -9,10 +9,12 @@ import { Messages, ChatSubscription } from '../../../models';
import { settings } from '../../../settings';
import { callbacks } from '../../../callbacks';
import { roomTypes } from '../../../utils';
import { call, callMethod } from './callMethod';
import { RoomManager, fireGlobalEvent, RoomHistoryManager } from '..';
import { callWithErrorHandling } from '../../../../client/lib/utils/callWithErrorHandling';
import { call } from '../../../../client/lib/utils/call';
import { RoomManager, RoomHistoryManager } from '..';
import { RoomManager as NewRoomManager } from '../../../../client/lib/RoomManager';
import { Rooms } from '../../../models/client';
import { fireGlobalEvent } from '../../../../client/lib/utils/fireGlobalEvent';
window.currentTracker = undefined;
@ -34,7 +36,7 @@ export const openRoom = async function(type, name, render = true) {
}
try {
const room = roomTypes.findRoom(type, name, user) || await callMethod('getRoomByTypeAndName', type, name);
const room = roomTypes.findRoom(type, name, user) || await call('getRoomByTypeAndName', type, name);
Rooms.upsert({ _id: room._id }, _.omit(room, '_id'));
if (room._id !== name && type === 'd') { // Redirect old url using username to rid
@ -67,14 +69,14 @@ export const openRoom = async function(type, name, render = true) {
// update user's room subscription
const sub = ChatSubscription.findOne({ rid: room._id });
if (sub && sub.open === false) {
call('openRoom', room._id);
callWithErrorHandling('openRoom', room._id);
}
if (FlowRouter.getQueryParam('msg')) {
const messageId = FlowRouter.getQueryParam('msg');
const msg = { _id: messageId, rid: room._id };
const message = Messages.findOne({ _id: msg._id }) || (await call('getMessages', [msg._id]))[0];
const message = Messages.findOne({ _id: msg._id }) || (await callWithErrorHandling('getMessages', [msg._id]))[0];
if (message && (message.tmid || message.tcount)) {
return FlowRouter.setParams({ tab: 'thread', context: message.tmid || message._id });
@ -90,7 +92,7 @@ export const openRoom = async function(type, name, render = true) {
} catch (error) {
c.stop();
if (type === 'd') {
const result = await call('createDirectMessage', ...name.split(', '));
const result = await callWithErrorHandling('createDirectMessage', ...name.split(', '));
if (result) {
return FlowRouter.go('direct', { rid: result.rid }, FlowRouter.current().queryParams);
}

@ -1,23 +0,0 @@
import { Meteor } from 'meteor/meteor';
import { MessageAction } from './MessageAction';
import { Rooms, Users } from '../../../models/client';
export const prependReplies = async (msg, replies = [], mention = false) => {
const { username } = Users.findOne({ _id: Meteor.userId() }, { fields: { username: 1 } });
const chunks = await Promise.all(replies.map(async ({ _id, rid, u }) => {
const permalink = await MessageAction.getPermaLink(_id);
const room = Rooms.findOne(rid, { fields: { t: 1 } });
let chunk = `[ ](${ permalink })`;
if (room.t === 'd' && u.username !== username && mention) {
chunk += ` @${ u.username }`;
}
return chunk;
}));
chunks.push(msg);
return chunks.join(' ');
};

@ -1,7 +0,0 @@
// http://stackoverflow.com/a/14824756
const ltrChars = 'A-Za-z\u00C0-\u00D6\u00D8-\u00F6\u00F8-\u02B8\u0300-\u0590\u0800-\u1FFF\u2C00-\uFB1C\uFDFE-\uFE6F\uFEFD-\uFFFF';
const rtlChars = '\u0591-\u07FF\uFB1D-\uFDFD\uFE70-\uFEFC';
const rtlRegExp = new RegExp(`^[^${ ltrChars }]*[${ rtlChars }]`);
export const isRTL = (text) => rtlRegExp.test(text);

@ -1,63 +0,0 @@
import { TAPi18n } from 'meteor/rocketchat:tap-i18n';
import { t } from '../../../utils/client';
import { modal } from './modal';
export const warnUserDeletionMayRemoveRooms = async function(userId, callbackFn, { warningKey, confirmButtonKey, closeOnConfirm = false, skipModalIfEmpty = false, shouldChangeOwner, shouldBeRemoved }) {
let warningText = warningKey ? t(warningKey) : false;
if (shouldBeRemoved.length + shouldChangeOwner.length === 0 && skipModalIfEmpty) {
callbackFn();
return;
}
if (shouldChangeOwner.length > 0) {
let newText;
if (shouldChangeOwner.length === 1) {
newText = TAPi18n.__('A_new_owner_will_be_assigned_automatically_to_the__roomName__room', { roomName: shouldChangeOwner.pop() });
} else if (shouldChangeOwner.length <= 5) {
newText = TAPi18n.__('A_new_owner_will_be_assigned_automatically_to_those__count__rooms__rooms__', { count: shouldChangeOwner.length, rooms: shouldChangeOwner.join(', ') });
} else {
newText = TAPi18n.__('A_new_owner_will_be_assigned_automatically_to__count__rooms', { count: shouldChangeOwner.length });
}
if (warningText) {
warningText = `${ warningText }<p>&nbsp;</p><p>${ newText }</p>`;
} else {
warningText = newText;
}
}
if (shouldBeRemoved.length > 0) {
let newText;
if (shouldBeRemoved.length === 1) {
newText = TAPi18n.__('The_empty_room__roomName__will_be_removed_automatically', { roomName: shouldBeRemoved.pop() });
} else if (shouldBeRemoved.length <= 5) {
newText = TAPi18n.__('__count__empty_rooms_will_be_removed_automatically__rooms__', { count: shouldBeRemoved.length, rooms: shouldBeRemoved.join(', ') });
} else {
newText = TAPi18n.__('__count__empty_rooms_will_be_removed_automatically', { count: shouldBeRemoved.length });
}
if (warningText) {
warningText = `${ warningText }<p>&nbsp;</p><p>${ newText }</p>`;
} else {
warningText = newText;
}
}
modal.open({
title: t('Are_you_sure'),
text: warningText,
type: 'warning',
showCancelButton: true,
confirmButtonColor: '#DD6B55',
confirmButtonText: t(confirmButtonKey || 'Yes_delete_it'),
cancelButtonText: t('Cancel'),
closeOnConfirm,
html: true,
}, () => {
callbackFn();
});
};

@ -1,6 +1,7 @@
import { Template } from 'meteor/templating';
import { fireGlobalEvent } from '../../../../ui-utils';
import { fireGlobalEvent } from '../../../../../client/lib/utils/fireGlobalEvent';
import './header.html';
Template.header.helpers({

@ -1,7 +1,7 @@
import { FlowRouter } from 'meteor/kadira:flow-router';
import { Template } from 'meteor/templating';
import { baseURI } from '../../../utils/client/lib/baseuri';
import { baseURI } from '../../../../client/lib/baseURI';
import './icon.html';

@ -11,15 +11,12 @@ import { escapeHTML } from '@rocket.chat/string-helpers';
import { KonchatNotification } from './notification';
import { MsgTyping } from './msgTyping';
import { fileUpload } from './fileUpload';
import { t, slashCommands, handleError } from '../../../utils/client';
import { t, slashCommands } from '../../../utils/client';
import {
messageProperties,
MessageTypes,
readMessage,
modal,
call,
keyCodes,
prependReplies,
} from '../../../ui-utils/client';
import { settings } from '../../../settings/client';
import { callbacks } from '../../../callbacks/client';
@ -30,6 +27,10 @@ import { emoji } from '../../../emoji/client';
import { generateTriggerId } from '../../../ui-message/client/ActionManager';
import { imperativeModal } from '../../../../client/lib/imperativeModal';
import GenericModal from '../../../../client/components/GenericModal';
import { keyCodes } from '../../../../client/lib/utils/keyCodes';
import { prependReplies } from '../../../../client/lib/utils/prependReplies';
import { callWithErrorHandling } from '../../../../client/lib/utils/callWithErrorHandling';
import { handleError } from '../../../../client/lib/utils/handleError';
const messageBoxState = {
@ -102,7 +103,7 @@ export class ChatMessages {
return;
}
const message = Messages.findOne(mid) || await call('getSingleMessage', mid);
const message = Messages.findOne(mid) || await callWithErrorHandling('getSingleMessage', mid);
if (!message) {
return;
}
@ -257,7 +258,7 @@ export class ChatMessages {
MsgTyping.stop(rid);
if (!ChatSubscription.findOne({ rid })) {
await call('joinRoom', rid);
await callWithErrorHandling('joinRoom', rid);
}
messageBoxState.save({ rid, tmid }, this.input);
@ -345,7 +346,7 @@ export class ChatMessages {
return;
}
await call('sendMessage', message);
await callWithErrorHandling('sendMessage', message);
}
async processSetReaction({ rid, tmid, msg }) {
@ -359,7 +360,7 @@ export class ChatMessages {
}
const lastMessage = this.collection.findOne({ rid, tmid }, { fields: { ts: 1 }, sort: { ts: -1 } });
await call('setReaction', reaction, lastMessage._id);
await callWithErrorHandling('setReaction', reaction, lastMessage._id);
return true;
}
@ -406,7 +407,7 @@ export class ChatMessages {
}
this.clearEditing();
await call('updateMessage', message);
await callWithErrorHandling('updateMessage', message);
return true;
}
@ -521,7 +522,7 @@ export class ChatMessages {
}
await call('deleteMessage', { _id });
await callWithErrorHandling('deleteMessage', { _id });
}
keydown(event) {

@ -4,9 +4,9 @@ import { Random } from 'meteor/random';
import { settings } from '../../../settings/client';
import { fileUploadIsValidContentType, APIClient } from '../../../utils';
import { prependReplies } from '../../../ui-utils';
import { imperativeModal } from '../../../../client/lib/imperativeModal';
import FileUploadModal from '../../../../client/components/modals/FileUploadModal';
import { prependReplies } from '../../../../client/lib/utils/prependReplies';
export const uploadFileWithMessage = async (rid, tmid, { description, fileName, msg, file }) => {
const data = new FormData();

@ -7,8 +7,8 @@ import { escapeRegExp } from '@rocket.chat/string-helpers';
import { AccountBox } from '../../../ui-utils';
import { settings } from '../../../settings';
import { callbacks } from '../../../callbacks';
import { baseURI } from '../../../utils/client/lib/baseuri.js';
import { add, remove } from '../../../../client/views/room/lib/Toolbox/IframeButtons';
import { baseURI } from '../../../../client/lib/baseURI';
const commands = {
go(data) {

@ -12,9 +12,9 @@ import { e2e } from '../../../e2e/client';
import { Users, ChatSubscription } from '../../../models';
import { getUserPreference } from '../../../utils';
import { getUserAvatarURL } from '../../../utils/lib/getUserAvatarURL';
import { getAvatarAsPng } from '../../../ui-utils';
import { promises } from '../../../promises/client';
import { CustomSounds } from '../../../custom-sounds/client/lib/CustomSounds';
import { getAvatarAsPng } from '../../../../client/lib/utils/getAvatarAsPng';
export const KonchatNotification = {
notificationStatus: new ReactiveVar(),

@ -3,7 +3,8 @@ import { Session } from 'meteor/session';
import { Template } from 'meteor/templating';
import { ChatSubscription } from '../../../../models/client';
import { Layout, menu } from '../../../../ui-utils/client';
import { menu } from '../../../../ui-utils/client';
import { isLayoutEmbedded } from '../../../../../client/lib/utils/isLayoutEmbedded';
import { getUserPreference } from '../../../../utils';
Template.burger.helpers({
@ -50,7 +51,7 @@ Template.burger.helpers({
},
embeddedVersion() {
return Layout.isEmbedded();
return isLayoutEmbedded();
},
});

@ -4,15 +4,13 @@ import { Random } from 'meteor/random';
import { FlowRouter } from 'meteor/kadira:flow-router';
import {
fireGlobalEvent,
popover,
Layout,
MessageAction,
} from '../../../../../ui-utils/client';
import {
addMessageToList,
} from '../../../../../ui-utils/client/lib/MessageAction';
import { call } from '../../../../../ui-utils/client/lib/callMethod';
import { callWithErrorHandling } from '../../../../../../client/lib/utils/callWithErrorHandling';
import { promises } from '../../../../../promises/client';
import { isURL } from '../../../../../utils/lib/isURL';
import { openUserCard } from '../../../lib/UserCard';
@ -21,7 +19,9 @@ import { ChatMessage, Rooms, Messages } from '../../../../../models';
import { t } from '../../../../../utils/client';
import { chatMessages } from '../room';
import { EmojiEvents } from '../../../../../reactions/client/init';
import { goToRoomById } from '../../../../../../client/lib/goToRoomById';
import { goToRoomById } from '../../../../../../client/lib/utils/goToRoomById';
import { fireGlobalEvent } from '../../../../../../client/lib/utils/fireGlobalEvent';
import { isLayoutEmbedded } from '../../../../../../client/lib/utils/isLayoutEmbedded';
const mountPopover = (e, i, outerContext) => {
let context = $(e.target).parents('.message').data('context');
@ -163,13 +163,13 @@ export const getCommonRoomEvents = () => ({
e.preventDefault();
e.stopPropagation();
const { msg } = messageArgs(this);
call('followMessage', { mid: msg._id });
callWithErrorHandling('followMessage', { mid: msg._id });
},
'click .js-unfollow-thread'(e) {
e.preventDefault();
e.stopPropagation();
const { msg } = messageArgs(this);
call('unfollowMessage', { mid: msg._id });
callWithErrorHandling('unfollowMessage', { mid: msg._id });
},
'click .js-open-thread'(event) {
event.preventDefault();
@ -259,7 +259,7 @@ export const getCommonRoomEvents = () => ({
return;
}
await call('sendMessage', msgObject);
await callWithErrorHandling('sendMessage', msgObject);
},
'click .message-actions__menu'(e, template) {
const messageContext = messageArgs(this);
@ -311,7 +311,7 @@ export const getCommonRoomEvents = () => ({
const { currentTarget: { dataset: { channel, group, username } } } = e;
if (channel) {
if (Layout.isEmbedded()) {
if (isLayoutEmbedded()) {
fireGlobalEvent('click-mention-link', { path: FlowRouter.path('channel', { name: channel }), channel });
}
goToRoomById(channel);

@ -10,15 +10,13 @@ import { FlowRouter } from 'meteor/kadira:flow-router';
import { Session } from 'meteor/session';
import { Template } from 'meteor/templating';
import { t, roomTypes, getUserPreference, handleError } from '../../../../utils/client';
import { t, roomTypes, getUserPreference } from '../../../../utils/client';
import { WebRTC } from '../../../../webrtc/client';
import { ChatMessage, RoomRoles, Users, Subscriptions, Rooms } from '../../../../models';
import {
fireGlobalEvent,
RoomHistoryManager,
RoomManager,
readMessage,
Layout,
} from '../../../../ui-utils/client';
import { messageContext } from '../../../../ui-utils/client/lib/messageContext';
import { messageArgs } from '../../../../ui-utils/client/lib/messageArgs';
@ -30,6 +28,9 @@ import { fileUpload } from '../../lib/fileUpload';
import './room.html';
import { getCommonRoomEvents } from './lib/getCommonRoomEvents';
import { RoomManager as NewRoomManager } from '../../../../../client/lib/RoomManager';
import { fireGlobalEvent } from '../../../../../client/lib/utils/fireGlobalEvent';
import { isLayoutEmbedded } from '../../../../../client/lib/utils/isLayoutEmbedded';
import { handleError } from '../../../../../client/lib/utils/handleError';
export const chatMessages = {};
@ -39,7 +40,7 @@ const userCanDrop = (_id) => !roomTypes.readOnly(_id, Users.findOne({ _id: Meteo
export const openProfileTab = (e, tabBar, username) => {
e.stopPropagation();
if (Layout.isEmbedded()) {
if (isLayoutEmbedded()) {
fireGlobalEvent('click-user-card-message', { username });
e.preventDefault();
return;
@ -272,7 +273,7 @@ Template.roomOld.helpers({
messageboxData() {
const { sendToBottomIfNecessary, subscription } = Template.instance();
const { _id: rid } = this;
const isEmbedded = Layout.isEmbedded();
const isEmbedded = isLayoutEmbedded();
const showFormattingTips = settings.get('Message_ShowFormattingTips');
return {

@ -2,7 +2,6 @@ export { t, isRtl } from '../lib/tapi18n';
export { getDefaultSubscriptionPref } from '../lib/getDefaultSubscriptionPref';
export { Info } from '../rocketchat.info';
export { isEmail } from '../lib/isEmail';
export { handleError } from './lib/handleError';
export { getUserPreference } from '../lib/getUserPreference';
export { fileUploadMediaWhiteList, fileUploadIsValidContentType } from '../lib/fileUploadRestrictions';
export { roomTypes } from './lib/roomTypes';
@ -11,12 +10,9 @@ export { RoomTypesCommon } from '../lib/RoomTypesCommon';
export { getUserAvatarURL } from '../lib/getUserAvatarURL';
export { slashCommands } from '../lib/slashCommand';
export { getUserNotificationPreference } from '../lib/getUserNotificationPreference';
export { applyCustomTranslations } from './lib/CustomTranslations';
export { getAvatarColor } from '../lib/getAvatarColor';
export { getURL } from '../lib/getURL';
export { placeholders } from '../lib/placeholders';
export { templateVarHandler } from '../lib/templateVarHandler';
export { APIClient, mountArrayQueryParameters } from './lib/RestApiClient';
export { canDeleteMessage } from './lib/canDeleteMessage';
export { APIClient } from './lib/RestApiClient';
export { secondsToHHMMSS } from '../lib/timeConverter';
export { waitUntilFind } from './lib/waitUntilFind';

@ -1,22 +0,0 @@
import { TAPi18n, TAPi18next } from 'meteor/rocketchat:tap-i18n';
import { settings } from '../../../settings';
export function applyCustomTranslations() {
let CustomTranslations = settings.get('Custom_Translations');
if (typeof CustomTranslations === 'string' && CustomTranslations.trim() !== '') {
try {
CustomTranslations = JSON.parse(CustomTranslations);
for (const lang in CustomTranslations) {
if (CustomTranslations.hasOwnProperty(lang)) {
const translations = CustomTranslations[lang];
TAPi18next.addResourceBundle(lang, 'project', translations);
}
}
TAPi18n._language_changed_tracker.changed();
} catch (e) {
console.error('Invalid setting Custom_Translations', e);
}
}
}

@ -1,13 +1,8 @@
import { Meteor } from 'meteor/meteor';
import { Accounts } from 'meteor/accounts-base';
import { baseURI } from './baseuri';
import { process2faReturn } from '../../../2fa/client/callWithTwoFactorRequired';
export const mountArrayQueryParameters = (label, array) => array.reduce((acc, item) => {
acc += `${ label }[]=${ item }&`;
return acc;
}, '');
import { baseURI } from '../../../../client/lib/baseURI';
export const APIClient = {
delete(endpoint, params) {

@ -1,18 +0,0 @@
import { Meteor } from 'meteor/meteor';
export const baseURI = (() => {
if (document.baseURI) { return document.baseURI; }
// Should be exactly one tag:
// https://developer.mozilla.org/en-US/docs/Web/HTML/Element/base
const base = document.getElementsByTagName('base');
// Return location from BASE tag.
if (base.length > 0) { return base[0].href; }
// Else use implementation of documentURI:
// http://www.w3.org/TR/DOM-Level-3-Core/core.html#Node3-baseURI
return document.URL;
})();
Meteor.absoluteUrl.defaultOptions = { ...Meteor.absoluteUrl.defaultOptions, rootUrl: baseURI };

@ -1,41 +0,0 @@
import { Meteor } from 'meteor/meteor';
import moment from 'moment';
import { hasPermission } from '../../../authorization/client';
import { settings } from '../../../settings/client';
export const canDeleteMessage = ({ rid, ts, uid }) => {
const userId = Meteor.userId();
const forceDelete = hasPermission('force-delete-message', rid);
if (forceDelete) {
return true;
}
const isDeleteAllowed = settings.get('Message_AllowDeleting');
if (!isDeleteAllowed) {
return false;
}
const allowed = hasPermission('delete-message', rid);
const deleteOwn = allowed || (uid === userId && hasPermission('delete-own-message'));
if (!allowed && !deleteOwn) {
return false;
}
const blockDeleteInMinutes = settings.get('Message_AllowDeleting_BlockDeleteInMinutes');
if (blockDeleteInMinutes != null && blockDeleteInMinutes !== 0) {
let msgTs;
if (ts != null) {
msgTs = moment(ts);
}
let currentTsDiff;
if (msgTs != null) {
currentTsDiff = moment().diff(msgTs, 'minutes');
}
return currentTsDiff < blockDeleteInMinutes;
}
return true;
};

@ -1,32 +0,0 @@
import { TAPi18n } from 'meteor/rocketchat:tap-i18n';
import _ from 'underscore';
import toastr from 'toastr';
import { escapeHTML } from '@rocket.chat/string-helpers';
export const handleError = function(error, useToastr = true) {
if (error.xhr) {
error = error.xhr.responseJSON || {};
}
if (_.isObject(error.details)) {
for (const key in error.details) {
if (error.details.hasOwnProperty(key)) {
error.details[key] = TAPi18n.__(error.details[key]);
}
}
}
if (useToastr) {
if (error.toastrShowed) {
return;
}
const details = Object.entries(error.details || {})
.reduce((obj, [key, value]) => ({ ...obj, [key]: escapeHTML(value) }), {});
const message = TAPi18n.__(error.error || error.message, details);
const title = details.errorTitle && TAPi18n.__(details.errorTitle);
return toastr.error(message, title);
}
return escapeHTML(TAPi18n.__(error.error || error.message, error.details));
};

@ -1,14 +0,0 @@
import { Tracker } from 'meteor/tracker';
export const waitUntilFind = <T>(fn: () => T | undefined): Promise<T> => new Promise((resolve) => {
Tracker.autorun((c) => {
const result = fn();
if (result === undefined) {
return;
}
c.stop();
resolve(result);
});
});

@ -11,7 +11,7 @@ import { settings } from '../../settings';
import { modal } from '../../ui-utils';
import { ChatSubscription } from '../../models';
import { WEB_RTC_EVENTS } from '..';
import { goToRoomById } from '../../../client/lib/goToRoomById';
import { goToRoomById } from '../../../client/lib/utils/goToRoomById';
class WebRTCTransportClass extends Emitter {
constructor(webrtcInstance) {

@ -1,4 +1,4 @@
import { fireGlobalEvent } from '../../ui-utils';
import { fireGlobalEvent } from '../../../client/lib/utils/fireGlobalEvent';
export const ChromeScreenShare = {
callbacks: {},

@ -16,7 +16,10 @@ module.exports = {
},
],
'jsx-quotes': ['error', 'prefer-single'],
'new-cap': ['error', { capIsNewExceptions: ['HTML.Comment', 'HTML.DIV', 'SHA256'] }],
'new-cap': [
'error',
{ capIsNewExceptions: ['HTML.Comment', 'HTML.Raw', 'HTML.DIV', 'SHA256'] },
],
'prefer-arrow-callback': ['error', { allowNamedFunctions: true }],
'prettier/prettier': 2,
'react/display-name': 'error',
@ -83,7 +86,10 @@ module.exports = {
},
],
'jsx-quotes': ['error', 'prefer-single'],
'new-cap': ['error', { capIsNewExceptions: ['HTML.Comment', 'HTML.DIV', 'SHA256'] }],
'new-cap': [
'error',
{ capIsNewExceptions: ['HTML.Comment', 'HTML.Raw', 'HTML.DIV', 'SHA256'] },
],
'no-extra-parens': 'off',
'no-spaced-func': 'off',
'no-unused-vars': 'off',

@ -19,7 +19,7 @@ import { IUser } from '../../../definition/IUser';
import { useTranslation } from '../../contexts/TranslationContext';
import { useEndpointActionExperimental } from '../../hooks/useEndpointActionExperimental';
import { useForm } from '../../hooks/useForm';
import { goToRoomById } from '../../lib/goToRoomById';
import { goToRoomById } from '../../lib/utils/goToRoomById';
import RoomAutoComplete from '../RoomAutoComplete';
import UserAutoCompleteMultiple from '../UserAutoCompleteMultiple';
import DefaultParentRoomField from './DefaultParentRoomField';

@ -1,6 +1,6 @@
import React from 'react';
import { renderEmoji } from '../../app/emoji/client/index';
import { renderEmoji } from '../lib/utils/renderEmoji';
function Emoji({ emojiHandle, className = undefined }) {
const markup = { __html: `${renderEmoji(emojiHandle)}` };

@ -3,7 +3,7 @@ import dompurify from 'dompurify';
import marked from 'marked';
import React, { ComponentProps, FC, useMemo } from 'react';
import { renderMessageEmoji } from '../lib/renderMessageEmoji';
import { renderMessageEmoji } from '../lib/utils/renderMessageEmoji';
type MarkdownTextParams = {
content: string;

@ -1,7 +1,7 @@
import { Link as ASTLink } from '@rocket.chat/message-parser';
import React, { FC } from 'react';
import { baseURI } from '../../../lib/baseuri';
import { baseURI } from '../../../lib/baseURI';
import Bold from './Bold';
import Italic from './Italic';
import Strike from './Strike';

@ -1,6 +1,6 @@
import React, { ReactElement } from 'react';
import { isIE11 } from '../../../../app/ui-utils/client/lib/isIE11';
import { isIE11 } from '../../../lib/utils/isIE11';
import GenericPreview from './GenericPreview';
import MediaPreview from './MediaPreview';

@ -1,7 +1,7 @@
import { Box, Icon } from '@rocket.chat/fuselage';
import React, { ReactElement } from 'react';
import { formatBytes } from '../../../lib/formatBytes';
import { formatBytes } from '../../../lib/utils/formatBytes';
const GenericPreview = ({ file }: { file: File }): ReactElement => (
<Box display='flex' alignItems='center' w='full' fontScale='s2'>

Some files were not shown because too many files have changed in this diff Show More

Loading…
Cancel
Save