Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
283 commits
Select commit Hold shift + click to select a range
956316e
Merge branch 'develop' into feat/encrypted-files
rodrigok Jun 12, 2024
13566ab
Merge remote-tracking branch 'upstream/feat/encrypted-files' into fea…
abhipatel0211 Jun 13, 2024
611f91e
Merge branch 'RocketChat:develop' into feat/encrypted-file
abhipatel0211 Jun 13, 2024
48a97f7
Fix placeholder message for threads
rodrigok Jun 13, 2024
446b1a7
Unskip test
rodrigok Jun 13, 2024
35363b6
Merge branch 'develop' into feat/encrypted-files
rodrigok Jun 13, 2024
c258b21
Fix ts
rodrigok Jun 13, 2024
989c61c
Fix tests
rodrigok Jun 13, 2024
0a3cb4d
Merge remote-tracking branch 'upstream/feat/encrypted-files' into fea…
abhipatel0211 Jun 14, 2024
403ced3
Merge branch 'develop' into feat/encrypted-files
rodrigok Jun 14, 2024
ae670ff
Merge branch 'RocketChat:develop' into feat/encrypted-file
abhipatel0211 Jun 14, 2024
de94f83
Merge branch 'develop' into feat/encrypted-files
rodrigok Jun 14, 2024
9da9640
Add test for old e2ee msg format
rodrigok Jun 14, 2024
8c7310f
Merge branch 'develop' into feat/encrypted-files
rodrigok Jun 18, 2024
5228bdb
Add tests for new upload API
rodrigok Jun 18, 2024
9e83634
Save encrypted content info to the file upload
rodrigok Jun 19, 2024
8f81edd
Add dimensions to image attachments
rodrigok Jun 19, 2024
b9ff006
Fix TS
rodrigok Jun 19, 2024
9a39914
Merge branch 'develop' into feat/encrypted-files
rodrigok Jun 19, 2024
20962c4
Fix tests
rodrigok Jun 19, 2024
74cfee1
Fix image preview
rodrigok Jun 19, 2024
6508ebe
Prevent keys to be set on top of existent keys
rodrigok Jun 19, 2024
1a1788e
Merge branch 'develop' into feat/encrypted-files
rodrigok Jun 19, 2024
64a27cb
Fix API tests
rodrigok Jun 19, 2024
b5e1ba5
Fix e2ee change password
rodrigok Jun 19, 2024
f108fd4
Fix TS
rodrigok Jun 19, 2024
ae76481
Fix API tests
rodrigok Jun 19, 2024
18d0e87
Decrypt room's last message correctly
rodrigok Jun 19, 2024
e984ad2
Merge remote-tracking branch 'origin/develop' into feat/encrypted-files
rodrigok Jun 19, 2024
c251e17
Merge branch 'develop' into feat/encrypted-files
rodrigok Jun 19, 2024
a96fa61
Try to fix tests
rodrigok Jun 19, 2024
3f480b0
Merge branch 'develop' into feat/encrypted-files
rodrigok Jun 19, 2024
fa2456a
Fix tests
rodrigok Jun 20, 2024
365cef8
Fix preview of encrypted files
rodrigok Jun 20, 2024
bd90357
Merge branch 'develop' into feat/encrypted-files
rodrigok Jun 20, 2024
81dad69
Fix download button
rodrigok Jun 20, 2024
8402305
Fix download from files list
rodrigok Jun 20, 2024
503218e
Merge branch 'develop' into feat/encrypted-files
rodrigok Jun 20, 2024
09e3bb7
Force cors on SW
rodrigok Jun 20, 2024
f6162af
Merge remote-tracking branch 'upstream/feat/encrypted-files' into fea…
abhipatel0211 Jun 21, 2024
b739659
feat: multiple file sharing feature with encryption
abhipatel0211 Jun 29, 2024
a1f7848
Merge remote-tracking branch 'upstream/develop' into e2e_multiple_mer…
abhipatel0211 Jun 29, 2024
74ed1f2
fix: file name issue
abhipatel0211 Jun 29, 2024
cbb41bb
Merge branch 'develop' into feat/multiple_files_in_one_msg
rodrigok Jul 5, 2024
c93da30
multiple files shared one at a time
abhipatel0211 Jul 7, 2024
cfc177c
Change message API to handle file upload
abhipatel0211 Jul 16, 2024
2e344a1
fix: Ensure correct preview of multiple images in shared in single me…
abhipatel0211 Jul 17, 2024
7f0b615
Merge remote-tracking branch 'upstream/develop' into feat/multiple_fi…
abhipatel0211 Jul 18, 2024
671fd31
solved merge conflict
abhipatel0211 Jul 18, 2024
8379c94
Merge remote-tracking branch 'upstream/develop' into feat/multiple_fi…
abhipatel0211 Jul 25, 2024
9a97c3d
fix: type error of fileContent and remove extra code
abhipatel0211 Jul 25, 2024
62fbc56
added support for single file upload
abhipatel0211 Jul 31, 2024
f88cd26
UI update added cross button on hover and added the functionality of …
abhipatel0211 Jul 31, 2024
f39042b
Merge remote-tracking branch 'upstream/develop' into feat/multiple_fi…
abhipatel0211 Aug 6, 2024
5a9f646
merge develop
abhipatel0211 Aug 6, 2024
771314e
feat: Added a file upload preview inside the messageBox
abhipatel0211 Aug 7, 2024
755c08b
Fix issue in uploads.ts causing duplicate messages on send
abhipatel0211 Aug 7, 2024
f2bd552
Cleanup: Remove unnecessary code
abhipatel0211 Aug 7, 2024
39ff2a3
removed unused space
abhipatel0211 Aug 7, 2024
23eb009
fix: lint errors
abhipatel0211 Aug 8, 2024
e786f70
Merge remote-tracking branch 'upstream/develop' into feat/multiple_fi…
abhipatel0211 Aug 8, 2024
f4b60d5
fix: lint and TS errors
abhipatel0211 Aug 8, 2024
1c0ddde
fix: ensure file handling as array to resolve type errors in uploads
abhipatel0211 Aug 8, 2024
f5213b0
fix: lint error and TS errors
abhipatel0211 Aug 8, 2024
6f398b4
fix: lint and TS errors
abhipatel0211 Aug 8, 2024
cdc0ff5
removed unused code
abhipatel0211 Aug 8, 2024
a1faa22
fix: reorder imports to fix ESLint errors and removed unused changes
abhipatel0211 Aug 8, 2024
326a197
fix: changed the variable name with camelCase and removed unwanted ch…
abhipatel0211 Aug 8, 2024
c078083
fix: changed variable names to cameCase
abhipatel0211 Aug 8, 2024
0e4d827
fix: added toast message while uploading file
abhipatel0211 Aug 9, 2024
60a80f9
Added the files to upload in the sendMessage in the executeSendMessage
abhipatel0211 Aug 10, 2024
7ac5841
fix: Revert back as using message API
abhipatel0211 Aug 10, 2024
9f74219
Removed unused import
abhipatel0211 Aug 10, 2024
9afeee6
Remove unwanted code
abhipatel0211 Aug 10, 2024
97f743b
Added defineProperty for all the files selected
abhipatel0211 Aug 12, 2024
68f45dc
Added different function for files and encrypted files sharing
abhipatel0211 Aug 13, 2024
d7b92cc
changed uploadFiles.ts and FileUploadModal.tsx to handle single file …
abhipatel0211 Aug 13, 2024
21005c0
Merge branch 'develop' into feat/multiple_files_in_one_msg
rodrigok Aug 13, 2024
a0f6c83
Added the type check for the filesToUpload and also removed the refer…
abhipatel0211 Aug 14, 2024
de319d8
Added isUploading and removed the unnecessary changes
abhipatel0211 Aug 14, 2024
3ad5e63
Added a folder of FilePreview near the messageBox and also changed th…
abhipatel0211 Aug 15, 2024
72bc00d
feat: Enable file attachments after typing a message
abhipatel0211 Aug 16, 2024
fbd30c9
Merge remote-tracking branch 'upstream/develop' into dev_feat/multipl…
abhipatel0211 Aug 16, 2024
fe2b428
Merge remote-tracking branch 'upstream/develop' into feat/multiple_fi…
abhipatel0211 Aug 16, 2024
b3db9fc
added title to the generic and image preview
abhipatel0211 Aug 16, 2024
3aa8c3d
fix: issue while sharing the message after file shared
abhipatel0211 Aug 17, 2024
2eb9b64
Merge remote-tracking branch 'upstream/develop' into feat/multiple_fi…
abhipatel0211 Aug 18, 2024
11aac8e
passed uploadIdsToConfirm to the sendMessage in executeSendMessage
abhipatel0211 Aug 18, 2024
9ff1b9f
Added newe function parseMultipleFilesIntoMessageAttachments
abhipatel0211 Aug 18, 2024
2370b14
added ui changes and also added the transition
abhipatel0211 Aug 19, 2024
47b592e
Merge remote-tracking branch 'upstream/develop' into feat/multiple_fi…
abhipatel0211 Aug 19, 2024
9722194
shifted confirm files at last after save message and attached multipl…
abhipatel0211 Aug 21, 2024
84bfcae
fix: image thumbnail display and remove extra msgData parameter
abhipatel0211 Aug 22, 2024
335e886
removed console logs
abhipatel0211 Aug 22, 2024
a5598f7
added a function for parse and also solved eslint error of reshuffling
abhipatel0211 Aug 22, 2024
7ea18d7
fix: solved lint errors messageBox and uploadfiles
abhipatel0211 Aug 23, 2024
822e2c5
fix: lint and TS errors
abhipatel0211 Aug 23, 2024
d1b6922
fix: lint error and converted description to msg
abhipatel0211 Aug 23, 2024
b13bdd2
fix: added description for TS error
abhipatel0211 Aug 23, 2024
a8cff84
Merge branch 'develop' into feat/multiple_files_in_one_msg
rodrigok Aug 23, 2024
0fe3aee
Changed the location of parsing file into attachments and also added …
abhipatel0211 Aug 24, 2024
7347447
Merge remote-tracking branch 'upstream/develop' into feat/multiple_fi…
abhipatel0211 Aug 24, 2024
65c7be7
fix: maintain file upload order to ensure consistent fileId, fileUrl …
abhipatel0211 Aug 31, 2024
c4fb104
Added different function for file upload
abhipatel0211 Aug 31, 2024
12abfc5
removed unnecessary changes
abhipatel0211 Sep 2, 2024
ed463c0
Merge remote-tracking branch 'upstream/develop' into feat/multiple_fi…
abhipatel0211 Sep 2, 2024
8c91c8c
added file which upload the file and return back the file IDs and fil…
abhipatel0211 Sep 3, 2024
7e5081b
fix: added condition so it will remove extra space
abhipatel0211 Sep 5, 2024
e45e376
feat: Add drag-and-drop file upload to message box
abhipatel0211 Sep 8, 2024
d21dd7f
fix: added encryption of message also
abhipatel0211 Sep 11, 2024
8508954
fix: Issue inside the thread messages
abhipatel0211 Sep 20, 2024
ea689a2
fix: multiple dispatch messages
abhipatel0211 Sep 20, 2024
ce5b7dd
Merge branch 'feat/multiple_files_in_one_msg' into dev_feat/multiple_…
abhipatel0211 Sep 21, 2024
7a2324a
Merge remote-tracking branch 'upstream/develop' into dev_feat/multipl…
abhipatel0211 Sep 21, 2024
acdf3c1
removed onFileDrop as using setFilesToUpload
abhipatel0211 Sep 21, 2024
ca89baf
Merge branch 'develop' into dev_feat/multiple_files_in_one_msg
abhipatel0211 Sep 24, 2024
1ccc5f8
Merge branch 'develop' into feat/multiple_files_in_one_msg
abhipatel0211 Sep 24, 2024
724856b
Merge branch 'feat/multiple_files_in_one_msg' into dev_feat/multiple_…
abhipatel0211 Sep 27, 2024
f1ea0da
testing test
abhipatel0211 Oct 2, 2024
1d92433
Merge remote-tracking branch 'upstream/develop' into dev_feat/multipl…
abhipatel0211 Oct 2, 2024
8ce9034
return to old test
abhipatel0211 Oct 2, 2024
4437083
Merge remote-tracking branch 'upstream/develop' into dev_feat/multipl…
abhipatel0211 Oct 3, 2024
5f22315
fix: remove selected files when in edit mode
abhipatel0211 Oct 5, 2024
19df253
fix: diabled file sharing while editing
abhipatel0211 Oct 6, 2024
9d12bf6
Merge branch 'feat/multiple_files_in_one_msg' into dev_feat/multiple_…
abhipatel0211 Oct 6, 2024
71135f1
Merge remote-tracking branch 'upstream/develop' into feat/multiple_fi…
abhipatel0211 Oct 7, 2024
bbdd7a5
Merge branch 'develop' into feat/multiple_files_in_one_msg
abhipatel0211 Oct 9, 2024
ec6a12f
fix:TS_error_resolved
abhipatel0211 Oct 9, 2024
beb5723
Merge remote-tracking branch 'upstream/develop' into dev_feat/multipl…
abhipatel0211 Oct 11, 2024
d9a7452
Merge branch 'develop' into dev_feat/multiple_files_in_one_msg
abhipatel0211 Oct 15, 2024
176d676
Merge branch 'dev_feat/multiple_files_in_one_msg' into feat/multiple_…
abhipatel0211 Oct 15, 2024
056bfed
fix: Trans error
abhipatel0211 Oct 15, 2024
5dbdfc6
Merge branch 'develop' into dev_feat/multiple_files_in_one_msg
abhipatel0211 Oct 26, 2024
d68c421
Merge branch 'develop' into test_feat/multiple_files
abhipatel0211 Oct 26, 2024
11e6002
Merge branch 'develop' into feat/multiple_files_in_one_msg
abhipatel0211 Oct 26, 2024
d7e71b9
Merge branch 'develop' into dev_feat/multiple_files_in_one_msg
abhipatel0211 Oct 26, 2024
65e39c5
Merge branch 'develop' into test_feat/multiple_files
abhipatel0211 Oct 26, 2024
9fba829
Restore deleted subscriptions.ts file
abhipatel0211 Oct 26, 2024
945a224
Merge branch 'test_feat/multiple_files' into dev_feat/multiple_files_…
abhipatel0211 Oct 26, 2024
c060422
Merge branch 'dev_feat/multiple_files_in_one_msg' into feat/multiple_…
abhipatel0211 Oct 26, 2024
3cc6b17
Merge branch 'develop' into feat/multiple_files_in_one_msg
abhipatel0211 Nov 2, 2024
a89e0d7
Merge remote-tracking branch 'upstream/develop' into feat/multiple_fi…
abhipatel0211 Nov 28, 2024
08416f7
fix: merge conflict
abhipatel0211 Nov 28, 2024
fcc474e
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Jan 30, 2025
8b176c7
feat: replace file preview
dougfabris Jan 21, 2025
8db4e9d
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Feb 7, 2025
007a5cc
fix: remove excessive state
dougfabris Feb 11, 2025
94da580
feat: `MessageComposerFile`
dougfabris Feb 11, 2025
c565f4e
chore: upload API tweaks
dougfabris Feb 11, 2025
7bf3b59
feat: `MessageComposerFile` loading and error
dougfabris Feb 11, 2025
60b2262
chore: `RoomV2` not rendering attachments in composer
dougfabris Feb 11, 2025
e675268
chore: remove `UploadProgressIndicator`
dougfabris Feb 11, 2025
22b981c
feat: limit number of files
dougfabris Feb 11, 2025
0a001b9
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Feb 13, 2025
6340dbf
feat: move file error validation to uploads.send
dougfabris Feb 13, 2025
27464bb
feat: new endpoint to edit file name properly
dougfabris Feb 14, 2025
a11bfc0
refactor: UploadsStore
dougfabris Feb 14, 2025
15237a2
feat: introduce threadUploads
dougfabris Feb 14, 2025
2d7453e
chore: code cleanup
dougfabris Feb 18, 2025
eca7363
fix: remove `handleUploadFiles` from ThreadChat`
dougfabris Feb 18, 2025
6f69c6c
fix: webdav upload flow
dougfabris Feb 18, 2025
56da938
Merge branch 'develop' into feat/multiple_files_in_one_msg
rodrigok Feb 18, 2025
dd2839a
fix: unnecessary store clear
dougfabris Feb 18, 2025
7f34a38
fix: `rooms.mediaEdit` review
dougfabris Feb 18, 2025
b1796d4
chore: remove unnecessary file
dougfabris Feb 18, 2025
872f0c6
Fix some of my reviews
rodrigok Feb 18, 2025
da5dcf8
Fix last changes
rodrigok Feb 18, 2025
565abe1
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Feb 18, 2025
4b98e47
fix: some `rooms.mediaEdit` suggestions
dougfabris Feb 18, 2025
6b8ab8e
fix: remove props from sendMessage
dougfabris Feb 18, 2025
c21b037
fix: remove description param from `uploadFile`
dougfabris Feb 19, 2025
a003a4f
fix: `rooms.mediaEdit` fileName param
dougfabris Feb 19, 2025
40189e2
Fix some reviews
rodrigok Feb 19, 2025
7ab58a2
refactor: upload API
dougfabris Feb 20, 2025
7c6d0e4
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Feb 20, 2025
70ba3de
chore: handle `confirmFiles` inside `sendMessage`
dougfabris Feb 26, 2025
4c0be8e
chore: remove outdated unit test
dougfabris Feb 24, 2025
be927dd
chore: remove outdated translation
dougfabris Feb 24, 2025
c206d67
backend code improvements
pierre-lehnen-rc Feb 26, 2025
931b595
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Mar 6, 2025
bbfe281
chore: review tweaks
dougfabris Mar 5, 2025
7bea8d8
test: add unit test for `rooms.mediaEdit`
dougfabris Mar 6, 2025
3fe2d3b
test: adapt current e2e tests to the new behavior
dougfabris Mar 7, 2025
726e6ac
chore: max multiple uploaded files rule
dougfabris Mar 7, 2025
d8a38e3
fix: uploading continuously action not cleaning after upload
dougfabris Mar 7, 2025
df671b6
fix: keep encryption when renaming file
dougfabris Mar 10, 2025
fbaa990
backend renaming of encrypted files
pierre-lehnen-rc Mar 10, 2025
1635254
fix: encrypted message being send
dougfabris Mar 10, 2025
481f921
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Mar 12, 2025
33b659d
fix: remove `rooms.mediaEdit`
dougfabris Mar 12, 2025
29404ae
chore: disable update button when form is not dirty
dougfabris Mar 12, 2025
af68ef2
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Mar 12, 2025
7f50d02
fix: review
dougfabris Mar 12, 2025
cbff55d
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Mar 25, 2025
447c08a
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Apr 7, 2025
8bac67f
chore: changeset
dougfabris Apr 7, 2025
769c798
chore: add comment to the ImageGallery workaround
dougfabris Apr 7, 2025
afaf266
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Apr 10, 2025
26e9097
Merge branch 'develop' into feat/multiple_files_in_one_msg
ggazzo Apr 17, 2025
788ee6c
Merge remote-tracking branch 'origin/develop' into feat/multiple_file…
ggazzo Apr 17, 2025
4210798
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Jun 9, 2025
c4a76fe
Merge branch 'develop' into feat/multiple_files_in_one_msg
rodrigok Jun 12, 2025
23e9407
improvements to backend code
pierre-lehnen-rc Jun 16, 2025
e17fde6
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Jun 26, 2025
720add4
fix: test locators
dougfabris Jun 26, 2025
4286095
chore: update changeset
dougfabris Jul 3, 2025
e2b0cd8
i18n: missing translation
dougfabris Jul 3, 2025
8790dee
fix: review
dougfabris Jul 3, 2025
eb94859
refactor: do not disable submit button when updating file name
dougfabris Jul 3, 2025
43445e5
test: e2e-encryption
dougfabris Jul 4, 2025
dfa3435
test: wait large image request to send message
dougfabris Jul 4, 2025
b3e2541
fix: typo
dougfabris Jul 4, 2025
a96e873
i18n: remove unused translation
dougfabris Jul 4, 2025
7c8cfbb
test: `image-upload`
dougfabris Jul 7, 2025
822d1c1
test: quote-attachment
dougfabris Jul 7, 2025
573d5c6
test: file-upload
dougfabris Jul 7, 2025
21f11bf
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Dec 23, 2025
6850713
fix: ts
dougfabris Dec 23, 2025
230bc41
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Dec 29, 2025
2934c06
fix: sendMessage filesToConfirm check
dougfabris Dec 29, 2025
cc55b16
chore: revert `rocketchat.e2e.room` changes
dougfabris Dec 29, 2025
a4f4f43
Merge remote-tracking branch 'origin/develop' into pr/abhipatel0211/3…
rodrigok Dec 31, 2025
1f2cd49
test: fix outdated updated e2e tests
dougfabris Jan 5, 2026
6b6f901
fix: change upload sequence
dougfabris Jan 5, 2026
00415a5
fix: handle error of specific file in upload process
juliajforesti Jan 6, 2026
8aabc84
feat: add modal confirmation for failed file uploads
juliajforesti Jan 7, 2026
3bc60fc
test: add tests for handling multiple file uploads with failures
juliajforesti Jan 7, 2026
c556588
chore: display error message in file upload component tooltip
juliajforesti Jan 7, 2026
91c5825
chore: add error feedback translations
juliajforesti Jan 9, 2026
5688b08
test: add tests for multiple file uploads
juliajforesti Jan 9, 2026
9a24a2e
feat: add configurable max files per message limit
ricardogarim Jan 12, 2026
4e9d386
disable multi-file by default
pierre-lehnen-rc Jan 12, 2026
9077bfb
save `file` attribute with the first file on the list
pierre-lehnen-rc Jan 12, 2026
dce346c
Merge branch 'develop' into feat/multiple_files_in_one_msg
juliajforesti Jan 12, 2026
615c301
test: adjust composer locators
juliajforesti Jan 12, 2026
e450f82
test: adjust max files per message limit
ricardogarim Jan 12, 2026
2dc7cc3
fix: delete all files when removing reported messages with multiple a…
ricardogarim Jan 12, 2026
97f4868
test: update file composer methods to use new locator structure
juliajforesti Jan 13, 2026
84dc860
test: reset `FileUpload_MaxFilesPerMessage` before and after tests
dougfabris Jan 13, 2026
2dea937
chore: improve `MessageComposerFile` a11y with `aria-busy` and updat…
juliajforesti Jan 14, 2026
b3bd39f
fix: return public URLs for all files in message endpoint
ricardogarim Jan 15, 2026
1dd6c3e
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Jan 15, 2026
654ec75
test: set maxFilesPerMessage to 2 for omni multi-file scenario
ricardogarim Jan 16, 2026
5e81cf6
Merge branch 'develop' into feat/multiple_files_in_one_msg
juliajforesti Jan 19, 2026
7b1567a
test: add test fot multifile upload in threads
juliajforesti Jan 19, 2026
8314b0a
Merge branch 'develop' into feat/multiple_files_in_one_msg
dougfabris Jan 20, 2026
aa8a988
test: adjust input file locator
juliajforesti Jan 20, 2026
fefb435
chore: update snapshots
juliajforesti Jan 21, 2026
c41e08a
Merge branch 'develop' into feat/multiple_files_in_one_msg
juliajforesti Jan 21, 2026
d93c57e
test: adjust e2e and unit failing
juliajforesti Jan 21, 2026
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
9 changes: 9 additions & 0 deletions .changeset/mighty-moose-return.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
---
'@rocket.chat/model-typings': minor
'@rocket.chat/core-typings': minor
'@rocket.chat/models': minor
'@rocket.chat/i18n': minor
'@rocket.chat/meteor': minor
---

Introduces the ability to upload multiple files and send them in a single message
2 changes: 1 addition & 1 deletion apps/meteor/app/api/server/v1/rooms.ts
Original file line number Diff line number Diff line change
Expand Up @@ -274,7 +274,7 @@ API.v1.addRoute(
sendFileMessage(this.userId, { roomId: this.urlParams.rid, file, msgData: this.bodyParams }, { parseAttachmentsForE2EE: false }),
);

await Uploads.confirmTemporaryFile(this.urlParams.fileId, this.userId);
await Uploads.confirmTemporaryFile(file._id, this.userId);

const message = await Messages.getMessageByFileIdAndUsername(file._id, this.userId);

Expand Down
29 changes: 27 additions & 2 deletions apps/meteor/app/file-upload/server/methods/sendFileMessage.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,9 @@ import type {
FileProp,
} from '@rocket.chat/core-typings';
import type { ServerMethods } from '@rocket.chat/ddp-client';
import { Logger } from '@rocket.chat/logger';
import { Rooms, Uploads, Users } from '@rocket.chat/models';
import { wrapExceptions } from '@rocket.chat/tools';
import { Match, check } from 'meteor/check';
import { Meteor } from 'meteor/meteor';

Expand All @@ -23,13 +25,36 @@ import { FileUpload } from '../lib/FileUpload';

function validateFileRequiredFields(file: Partial<IUpload>): asserts file is AtLeast<IUpload, '_id' | 'name' | 'type' | 'size'> {
const requiredFields = ['_id', 'name', 'type', 'size'];
requiredFields.forEach((field) => {
for (const field of requiredFields) {
if (!Object.keys(file).includes(field)) {
throw new Meteor.Error('error-invalid-file', 'Invalid file');
}
});
}
}

const logger = new Logger('sendFileMessage');

export const parseMultipleFilesIntoMessageAttachments = async (
filesToConfirm: Partial<IUpload>[],
roomId: string,
user: IUser,
): Promise<{ files: FileProp[]; attachments: MessageAttachment[] }> => {
const results = await Promise.all(
filesToConfirm.map((file) =>
wrapExceptions(() => parseFileIntoMessageAttachments(file, roomId, user)).catch(async (error) => {
// Not an important error, it should not happen and if it happens wil affect the attachment preview in the message object only
logger.warn({ msg: 'Error processing file: ', file, error });
return { files: [], attachments: [] };
}),
),
);

return {
files: results.flatMap(({ files }) => files),
attachments: results.flatMap(({ attachments }) => attachments),
};
};

export const parseFileIntoMessageAttachments = async (
file: Partial<IUpload>,
roomId: string,
Expand Down
58 changes: 55 additions & 3 deletions apps/meteor/app/lib/server/functions/sendMessage.ts
Original file line number Diff line number Diff line change
@@ -1,14 +1,15 @@
import { AppEvents, Apps } from '@rocket.chat/apps';
import { Message } from '@rocket.chat/core-services';
import type { IMessage, IRoom } from '@rocket.chat/core-typings';
import { Messages } from '@rocket.chat/models';
import { isE2EEMessage, type IMessage, type IRoom, type IUpload, type IUploadToConfirm } from '@rocket.chat/core-typings';
import { Messages, Uploads } from '@rocket.chat/models';
import { Match, check } from 'meteor/check';

import { parseUrlsInMessage } from './parseUrlsInMessage';
import { isRelativeURL } from '../../../../lib/utils/isRelativeURL';
import { isURL } from '../../../../lib/utils/isURL';
import { hasPermissionAsync } from '../../../authorization/server/functions/hasPermission';
import { FileUpload } from '../../../file-upload/server';
import { parseMultipleFilesIntoMessageAttachments } from '../../../file-upload/server/methods/sendFileMessage';
import { settings } from '../../../settings/server';
import { afterSaveMessage } from '../lib/afterSaveMessage';
import { notifyOnRoomChangedById } from '../lib/notifyListener';
Expand Down Expand Up @@ -213,15 +214,62 @@ export function prepareMessageObject(
}

/**
* Update file names on the Uploads collection, as the names may have changed between the upload and the sending of the message
* For encrypted rooms, the full `content` of the file is updated as well, as the name is included there
**/
const updateFileNames = async (filesToConfirm: IUploadToConfirm[], isE2E: boolean) => {
return Promise.all(
filesToConfirm.map(async (upload) => {
if (isE2E) {
// on encrypted files, the `upload.name` is an useless attribute, so it doesn't need to be updated
// the name will be loaded from the encrypted data on `upload.content` instead
if (upload.content) {
await Uploads.updateFileContentById(upload._id, upload.content);
}
} else if (upload.name) {
await Uploads.updateFileNameById(upload._id, upload.name);
}
}),
);
};

/**
* Validates and sends the message object.
* Validates and sends the message object. This function does not verify the Message_MaxAllowedSize settings.
* Caller of the function should verify the Message_MaxAllowedSize if needed.
* There might be same use cases which needs to override this setting. Example - sending error logs.
*/
export const sendMessage = async function (user: any, message: any, room: any, upsert = false, previewUrls?: string[]) {
export const sendMessage = async (
user: any,
message: any,
room: any,
upsert = false,
previewUrls?: string[],
filesToConfirm?: IUploadToConfirm[],
) => {
if (!user || !message || !room._id) {
return false;
}

const isE2E = isE2EEMessage(message);

if (filesToConfirm) {
await updateFileNames(filesToConfirm, isE2E);
}

const uploadIdsToConfirm = filesToConfirm?.map(({ _id }) => _id);

if (uploadIdsToConfirm?.length && !isE2E) {
const uploadsToConfirm: Partial<IUpload>[] = await Uploads.findByIds(uploadIdsToConfirm).toArray();
const { files, attachments } = await parseMultipleFilesIntoMessageAttachments(uploadsToConfirm, message.rid, user);
message.files = files;
message.attachments = attachments;
// For compatibility with older integrations, we save the first file to the `file` attribute of the message
if (files.length) {
message.file = files[0];
}
}

await validateMessage(message, room, user);
prepareMessageObject(message, room._id, user);

Expand Down Expand Up @@ -287,6 +335,10 @@ export const sendMessage = async function (user: any, message: any, room: any, u

await afterSaveMessage(message, room, user);

if (uploadIdsToConfirm?.length) {
await Uploads.confirmTemporaryFiles(uploadIdsToConfirm, user._id);
}

void notifyOnRoomChangedById(message.rid);

return message;
Expand Down
43 changes: 37 additions & 6 deletions apps/meteor/app/lib/server/methods/sendMessage.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { api } from '@rocket.chat/core-services';
import type { AtLeast, IMessage, IUser } from '@rocket.chat/core-typings';
import { type AtLeast, type IMessage, type IUser, type IUploadToConfirm } from '@rocket.chat/core-typings';
import type { ServerMethods } from '@rocket.chat/ddp-client';
import type { RocketchatI18nKeys } from '@rocket.chat/i18n';
import { MessageTypes } from '@rocket.chat/message-types';
Expand Down Expand Up @@ -32,7 +32,7 @@ import { RateLimiter } from '../lib';
export async function executeSendMessage(
uid: IUser['_id'],
message: AtLeast<IMessage, 'rid'>,
extraInfo?: { ts?: Date; previewUrls?: string[] },
extraInfo?: { ts?: Date; previewUrls?: string[]; filesToConfirm?: IUploadToConfirm[] },
) {
if (message.tshow && !message.tmid) {
throw new Meteor.Error('invalid-params', 'tshow provided but missing tmid', {
Expand Down Expand Up @@ -106,7 +106,7 @@ export async function executeSendMessage(
}

metrics.messagesSent.inc(); // TODO This line needs to be moved to it's proper place. See the comments on: https://github.com/RocketChat/Rocket.Chat/pull/5736
return await sendMessage(user, message, room, false, extraInfo?.previewUrls);
return await sendMessage(user, message, room, false, extraInfo?.previewUrls, extraInfo?.filesToConfirm);
} catch (err: any) {
SystemLogger.error({ msg: 'Error sending message:', err });

Expand All @@ -127,12 +127,12 @@ export async function executeSendMessage(
declare module '@rocket.chat/ddp-client' {
// eslint-disable-next-line @typescript-eslint/naming-convention
interface ServerMethods {
sendMessage(message: AtLeast<IMessage, '_id' | 'rid' | 'msg'>, previewUrls?: string[]): any;
sendMessage(message: AtLeast<IMessage, '_id' | 'rid' | 'msg'>, previewUrls?: string[], filesToConfirm?: IUploadToConfirm[]): any;
}
}

Meteor.methods<ServerMethods>({
async sendMessage(message, previewUrls) {
async sendMessage(message, previewUrls, filesToConfirm) {
check(message, {
_id: Match.Maybe(String),
rid: Match.Maybe(String),
Expand All @@ -151,6 +151,37 @@ Meteor.methods<ServerMethods>({
sentByEmail: Match.Maybe(Boolean),
});

check(
filesToConfirm,
Match.Maybe([
Match.ObjectIncluding({
_id: String,
name: Match.Maybe(String),
content: Match.Maybe(
Match.OneOf(
{
algorithm: 'rc.v1.aes-sha2',
ciphertext: String,
},
{
algorithm: 'rc.v2.aes-sha2',
ciphertext: String,
kid: String,
iv: String,
},
),
),
}),
]),
);

const maxFilesPerMessage = settings.get<number>('FileUpload_MaxFilesPerMessage');
if (filesToConfirm && maxFilesPerMessage && filesToConfirm.length > maxFilesPerMessage) {
throw new Meteor.Error('error-too-many-files', `Cannot send more than ${maxFilesPerMessage} files in one message`, {
method: 'sendMessage',
});
}

const uid = Meteor.userId();
if (!uid) {
throw new Meteor.Error('error-invalid-user', 'Invalid user', {
Expand All @@ -163,7 +194,7 @@ Meteor.methods<ServerMethods>({
}

try {
return await applyAirGappedRestrictionsValidation(() => executeSendMessage(uid, message, { previewUrls }));
return await applyAirGappedRestrictionsValidation(() => executeSendMessage(uid, message, { previewUrls, filesToConfirm }));
} catch (error: any) {
if (['error-not-allowed', 'restricted-workspace'].includes(error.error || error.message)) {
throw new Meteor.Error(error.error || error.message, error.reason, {
Expand Down
4 changes: 2 additions & 2 deletions apps/meteor/app/livechat/server/api/v1/message.ts
Original file line number Diff line number Diff line change
Expand Up @@ -104,7 +104,7 @@ API.v1.addRoute(
throw new Error('invalid-message');
}

if (message.file) {
if (message.file || message.files?.length) {
message = { ...(await normalizeMessageFileUpload(message)), ...{ _updatedAt: message._updatedAt } };
}

Expand Down Expand Up @@ -148,7 +148,7 @@ API.v1.addRoute(
return API.v1.failure();
}

if (message?.file) {
if (message.file || message.files?.length) {
message = { ...(await normalizeMessageFileUpload(message)), ...{ _updatedAt: message._updatedAt } };
}

Expand Down
7 changes: 6 additions & 1 deletion apps/meteor/app/ui/client/lib/ChatMessages.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import { UserAction } from './UserAction';
import type { ChatAPI, ComposerAPI, DataAPI, UploadsAPI } from '../../../../client/lib/chats/ChatAPI';
import { createDataAPI } from '../../../../client/lib/chats/data';
import { processMessageEditing } from '../../../../client/lib/chats/flows/processMessageEditing';
import { processMessageUploads } from '../../../../client/lib/chats/flows/processMessageUploads';
import { processSetReaction } from '../../../../client/lib/chats/flows/processSetReaction';
import { processSlashCommand } from '../../../../client/lib/chats/flows/processSlashCommand';
import { processTooLongMessage } from '../../../../client/lib/chats/flows/processTooLongMessage';
Expand Down Expand Up @@ -44,6 +45,8 @@ export class ChatMessages implements ChatAPI {

public uploads: UploadsAPI;

public threadUploads: UploadsAPI;

public ActionManager: any;

public emojiPicker: {
Expand Down Expand Up @@ -147,7 +150,8 @@ export class ChatMessages implements ChatAPI {
this.tmid = tmid;
this.uid = params.uid;
this.data = createDataAPI({ rid, tmid });
this.uploads = createUploadsAPI({ rid, tmid });
this.uploads = createUploadsAPI({ rid });
this.threadUploads = createUploadsAPI({ rid });
this.ActionManager = params.actionManager;
this.currentEditingMessage = new CurrentEditingMessage(this);

Expand Down Expand Up @@ -180,6 +184,7 @@ export class ChatMessages implements ChatAPI {
processSlashCommand: processSlashCommand.bind(null, this),
processTooLongMessage: processTooLongMessage.bind(null, this),
processMessageEditing: processMessageEditing.bind(null, this),
processMessageUploads: processMessageUploads.bind(null, this),
processSetReaction: processSetReaction.bind(null, this),
requestMessageDeletion: requestMessageDeletion.bind(this, this),
replyBroadcast: replyBroadcast.bind(null, this),
Expand Down
Original file line number Diff line number Diff line change
@@ -1,30 +1,49 @@
import type { IMessage } from '@rocket.chat/core-typings';
import { Uploads } from '@rocket.chat/models';
import { isTruthy } from '@rocket.chat/tools';

import { FileUpload } from '../../../file-upload/server';
import { getURL } from '../getURL';

const generateFileUploadData = async (
message: Pick<IMessage, 'rid' | 'u'>,
fileId: string,
): Promise<{ publicFilePath: string; type?: string; size?: number } | null> => {
const jwt = FileUpload.generateJWTToFileUrls({
rid: message.rid,
userId: message.u._id,
fileId,
});
const file = await Uploads.findOne({ _id: fileId });
if (!file) {
return null;
}
return {
publicFilePath: file.name
? getURL(`${FileUpload.getPath(`${file._id}/${encodeURI(file.name)}`).substring(1)}${jwt ? `?token=${jwt}` : ''}`, {
cdn: false,
full: true,
})
: '',
type: file.type,
size: file.size,
};
};

export const normalizeMessageFileUpload = async (message: Omit<IMessage, '_updatedAt'>): Promise<Omit<IMessage, '_updatedAt'>> => {
// handle deprecated single file property for backward compatibility
if (message.file && !message.fileUpload) {
const jwt = FileUpload.generateJWTToFileUrls({
rid: message.rid,
userId: message.u._id,
fileId: message.file._id,
});
const file = await Uploads.findOne({ _id: message.file._id });
if (!file) {
return message;
const fileUploadData = await generateFileUploadData(message, message.file._id);
if (fileUploadData) {
message.fileUpload = fileUploadData;
}
message.fileUpload = {
publicFilePath: file.name
? getURL(`${FileUpload.getPath(`${file._id}/${encodeURI(file.name)}`).substring(1)}${jwt ? `?token=${jwt}` : ''}`, {
cdn: false,
full: true,
})
: '',
type: file.type,
size: file.size,
};
}

// handle multiple files
if (message.files?.length && !message.filesUpload) {
const filesUploadData = await Promise.all(message.files.map((file) => generateFileUploadData(message, file._id)));
message.filesUpload = filesUploadData.filter(isTruthy);
}

return message;
};
Loading
Loading