FIX: prevents duplicate reactions (#20527)

This was possible due to specific events which are hard to represent in a test. The provided test is as close as possible to what was happening in production: a message bus event was played on a channel which has just loaded its state with the existing reaction.
This commit is contained in:
Joffrey JAFFEUX 2023-03-03 20:29:24 +01:00 committed by GitHub
parent 0dc9c6c96d
commit cdcd20fe1e
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 28 additions and 1 deletions

View File

@ -130,7 +130,13 @@ export default class ChatMessage {
if (existingReaction) {
if (action === "add") {
if (selfReaction && existingReaction.reacted) {
return false;
return;
}
// we might receive a message bus event while loading a channel who would
// already have the reaction added to the message
if (existingReaction.users.find((user) => user.id === actor.id)) {
return;
}
existingReaction.count = existingReaction.count + 1;

View File

@ -140,5 +140,26 @@ RSpec.describe "React to message", type: :system, js: true do
context "when mobile", mobile: true do
include_examples "inline reactions"
end
context "when receiving a duplicate reaction event" do
fab!(:user_1) { Fabricate(:user) }
fab!(:reaction_2) do
Chat::ChatMessageReactor.new(user_1, category_channel_1).react!(
message_id: message_1.id,
react_action: :add,
emoji: "heart",
)
end
it "doesnt create duplicate reactions" do
chat.visit_channel(category_channel_1)
ChatPublisher.publish_reaction!(category_channel_1, message_1, "add", user_1, "heart")
channel.send_message("test") # cheap trick to ensure reaction has been processed
expect(channel).to have_reaction(message_1, reaction_2, "1")
end
end
end
end