mirror of
https://github.com/discourse/discourse.git
synced 2025-02-25 18:55:32 -06:00
DEV: Redesign chat mentions (#24752)
At the moment, when someone is mentioning a group, or using here or
all mention, we create a chat_mention record per user. What we want
instead is to have special kinds of mentions, so we can create only one
chat_mention record in such cases. This PR implements that.
Note, that such mentions will still have N related notifications, one
notification per a user. We don't expect we'll have performance
problems on the notifications side, but if at some point we do, we
should be able to solve them on the side of notifications
(notifications are handled in jobs, also some little delays with
the notifications are acceptable, so we can make sure notifications
are properly queued, and that processing of every notification is
fast enough to make delays small enough).
The preparation work for this PR was done in fbd24fa, where we make
it possible for one mention to have several related notifications.
A pretty tricky part of this PR is schema and data migration, I've explained
related details inline on the migration files.
This commit is contained in:
committed by
GitHub
parent
6876c52857
commit
62f423da15
@@ -0,0 +1,15 @@
|
||||
# frozen_string_literal: true
|
||||
|
||||
class AddTypeAndTargetIdToChatMentions < ActiveRecord::Migration[7.0]
|
||||
def up
|
||||
add_column :chat_mentions, :type, :string, null: true
|
||||
add_column :chat_mentions, :target_id, :integer, null: true
|
||||
change_column_null :chat_mentions, :user_id, true
|
||||
end
|
||||
|
||||
def down
|
||||
change_column_null :chat_mentions, :user_id, false
|
||||
remove_column :chat_mentions, :target_id
|
||||
remove_column :chat_mentions, :type
|
||||
end
|
||||
end
|
||||
@@ -0,0 +1,24 @@
|
||||
# frozen_string_literal: true
|
||||
|
||||
class SetTypeAndTargetIdOnChatMentions < ActiveRecord::Migration[7.0]
|
||||
disable_ddl_transaction!
|
||||
BATCH_SIZE = 5000
|
||||
|
||||
def up
|
||||
begin
|
||||
updated_count = DB.exec(<<~SQL, batch_size: BATCH_SIZE)
|
||||
WITH cte AS (SELECT id, user_id
|
||||
FROM chat_mentions
|
||||
WHERE type IS NULL AND target_id IS NULL
|
||||
LIMIT :batch_size)
|
||||
UPDATE chat_mentions
|
||||
SET type = 'Chat::UserMention', target_id = cte.user_id
|
||||
FROM cte
|
||||
WHERE chat_mentions.id = cte.id;
|
||||
SQL
|
||||
end while updated_count > 0
|
||||
end
|
||||
|
||||
def down
|
||||
end
|
||||
end
|
||||
@@ -0,0 +1,23 @@
|
||||
# frozen_string_literal: true
|
||||
|
||||
class AddAndRemoveIndexesOnChatMentions < ActiveRecord::Migration[7.0]
|
||||
disable_ddl_transaction!
|
||||
def up
|
||||
remove_index :chat_mentions,
|
||||
name: :chat_mentions_index,
|
||||
algorithm: :concurrently,
|
||||
if_exists: true
|
||||
add_index :chat_mentions, %i[chat_message_id], algorithm: :concurrently
|
||||
add_index :chat_mentions, %i[target_id], algorithm: :concurrently
|
||||
end
|
||||
|
||||
def down
|
||||
remove_index :chat_mentions, %i[target_id], algorithm: :concurrently, if_exists: true
|
||||
remove_index :chat_mentions, %i[chat_message_id], algorithm: :concurrently, if_exists: true
|
||||
add_index :chat_mentions,
|
||||
%i[chat_message_id user_id notification_id],
|
||||
unique: true,
|
||||
name: "chat_mentions_index",
|
||||
algorithm: :concurrently
|
||||
end
|
||||
end
|
||||
@@ -0,0 +1,27 @@
|
||||
# frozen_string_literal: true
|
||||
|
||||
class SetTypeAndTargetIdOnChatMentionsPostMigrate < ActiveRecord::Migration[7.0]
|
||||
disable_ddl_transaction!
|
||||
BATCH_SIZE = 5000
|
||||
|
||||
def up
|
||||
# we're setting it again in post-migration
|
||||
# in case some mentions have been created after we run
|
||||
# this query the first time in the regular migration
|
||||
begin
|
||||
updated_count = DB.exec(<<~SQL, batch_size: BATCH_SIZE)
|
||||
WITH cte AS (SELECT id, user_id
|
||||
FROM chat_mentions
|
||||
WHERE type IS NULL AND target_id IS NULL
|
||||
LIMIT :batch_size)
|
||||
UPDATE chat_mentions
|
||||
SET type = 'Chat::UserMention', target_id = cte.user_id
|
||||
FROM cte
|
||||
WHERE chat_mentions.id = cte.id;
|
||||
SQL
|
||||
end while updated_count > 0
|
||||
end
|
||||
|
||||
def down
|
||||
end
|
||||
end
|
||||
@@ -0,0 +1,11 @@
|
||||
# frozen_string_literal: true
|
||||
|
||||
class MakeTypeOnChatMentionsNonNullable < ActiveRecord::Migration[7.0]
|
||||
def up
|
||||
change_column_null :chat_mentions, :type, false
|
||||
end
|
||||
|
||||
def down
|
||||
change_column_null :chat_mentions, :type, true
|
||||
end
|
||||
end
|
||||
Reference in New Issue
Block a user