bjlarouche
(Brandon LaRouche)
2023 年 2 月 15 日午後 6:12
22
post_actions の場合はこれで解決しました。提案ありがとうございます!
現在、主に 2 つの障害が引き続き発生しています。
GET https://devforum.roblox.com/notifications は、bigInt ID を持つ通知があるユーザーに対して 404 エラーを返します。
Jobs::GrantAnniversaryBadges スケジュール済みジョブが失敗します。
通知のモデル/コントローラー/サービスが、notifications.id フィールドを整数としてハードコーディングしている可能性はありますか?
sam
(Sam Saffron)
2023 年 2 月 16 日午前 12:16
23
可能性は非常に低い… 404 は正しくないように聞こえますが、/logs に問題に関する記述はありますか?
bjlarouche
(Brandon LaRouche)
2023 年 2 月 16 日午前 1:19
24
残念ながら、/logs 自体には特に有用なものは見つかりませんが、ローカルで再現すると、リクエストが来てから 404 になることがわかります。ただし、これは最新の通知の ID を bigint に設定した場合にのみ発生します (int32 の範囲内であれば問題なく動作します)。
調べてみると、http://localhost/notifications.json?limit=30 を呼び出すと有効な応答が得られることに気づきました。
{
"notifications": [
{
"id": 2148935910,
"user_id": 2,
"notification_type": 5,
"read": true,
"high_priority": false,
"created_at": "2023-02-16T00:50:53.135Z",
"post_number": 2,
"topic_id": 8,
"fancy_title": "Welcome to the Lounge",
"slug": "welcome-to-the-lounge",
"data": {
"topic_title": "Welcome to the Lounge",
"original_post_id": 13,
"original_post_type": 1,
"original_username": "blarouche",
"revision_number": null,
"display_username": "blarouche"
}
}
],
"total_rows_notifications": 1,
"seen_notification_id": 1001,
"load_more_notifications": "/notifications?offset=60&username=bjlarouche"
}
しかし、recent クエリパラメータを渡すと、つまり http://localhost/notifications.json?recent=true&limit=30 とすると、これは通知メニューから呼び出されるものですが、どうなるでしょうか?
{
"errors": [
"The requested URL or resource could not be found."
],
"error_type": "not_found"
}
編集: これは、current_user.seen_notification_id がまだ整数であるためではないかと考えています
bjlarouche
(Brandon LaRouche)
2023 年 2 月 16 日午後 8:01
26
これで大丈夫だと思います!
notifications.id だけでなく、notification_id を参照する他のテーブルの列も移行する必要があることに気づきました。そうでなければ、services/notifications.rb または services/badge_granter.rb でエラーが発生していました。
将来、同様の問題に直面する他の大規模なフォーラム設定のために、以下に実施したことを示します…
合計で、4つのテーブルの4つの列を移行する必要がありました。
notifications.id
user.seen_notification_id
user_badges.notification_id
shelved_notifications.notification_id
当初は上記で提案された ALTER コマンドで #1 を行いましたが、その後、言及したように ActiveRecord のマイグレーションを使用することにしました。これにより、マイグレーションファイルがスキーマに追加されます。
20230215070319_change_notifications_id_to_bigint.rb
# frozen_string_literal: true
class ChangeNotificationsIdToBigint < ActiveRecord::Migration[6.1]
def change
change_column :notifications, :id, :bigint
end
end
20230215070320_change_user_seen_notification_id_to_bigint.rb
# frozen_string_literal: true
class ChangeUserSeenNotificationIdToBigint < ActiveRecord::Migration[6.1]
def change
change_column :users, :seen_notification_id, :bigint
end
end
20230215070321_change_user_badges_notification_id_to_bigint.rb
# frozen_string_literal: true
class ChangeUserBadgesNotificationIdToBigint < ActiveRecord::Migration[6.1]
def change
change_column :user_badges, :notification_id, :bigint
end
end
20230215070322_change_shelved_notifications_notification_id_to_bigint.rb
# frozen_string_literal: true
class ChangeShelvedNotificationsNotificationIdToBigint < ActiveRecord::Migration[6.1]
def change
change_column :shelved_notifications, :notification_id, :bigint
end
end
カスタム Dockerfile を使用しているため(Kubernetes 上で discourse と sidekiq を別々のリソースで実行できるようにイメージをビルドしています)、これらのファイルを /db/migrate にコピーするのは Dockerfile で簡単に行えました。
その後は rake db:migrate にすべてを任せました。すべての discourse および sidekiq ポッドでローリング再起動を行ったところ、すべてが期待どおりに動作しました 。
「いいね!」 3
sam
(Sam Saffron)
2023 年 2 月 16 日午後 11:11
27
素晴らしいデータです。コアのDiscourseでこれをbigintに移行することにしましょう。コストはかかりますが、大きなフォーラムでは必ずまた問題になるでしょうから、今のうちに修正しておくのが良いでしょう。
注意…OPはpost_idについてです…それをオーバーフローさせるのは、notificationsよりもはるかに困難になります。21億件の投稿は確かに起こるでしょうが、post_idをbigintにするコストはnotification idよりもはるかに高価です。この時限爆弾については、もう少し待つことができます。
「いいね!」 4
sam
(Sam Saffron)
2023 年 3 月 2 日午前 5:23
28
ブランドン、
以下を採用する可能性があります。
main ← rake-task
opened 05:18AM - 02 Mar 23 UTC
Under exceptional cases people may need to resize the notification table.
This o… nly happens on forums with a total of more than 2.5 billion notifications.
This rake task can be used to convert all the notification columns to
bigint to make more room.
ここでバランスを取る必要があるのは、25億件の通知という驚異的な偉業を達成した1つか2つの外れ値フォーラムのために、40,000のDiscourseインスタンスを「罰したくない」ということです。
どう思いますか?
(注:これには、あなたが逃したものが少なくとも1つ含まれます。チャットテーブルもあります)
「いいね!」 3
これは素晴らしいですし、賢い解決策のように見えます
このトピックは4日後に自動的に閉じられました。新しい返信は許可されていません。