Jobs::SyncTopicUserBookmarked in einer Schleife, die 100% CPU nutzt

In den letzten ~18 Stunden verbraucht unser Server fast 100 % CPU.

Wenn ich mir Sidekiq ansehe, läuft es intensiv mit denselben 5 Jobs:

Sie stehen immer auf „Gerade eben“ und scheinen immer wieder über dieselben 3 Topic-IDs zu laufen.

Ich habe versucht, Discourse neu zu starten, aber die Situation blieb unverändert.

Ich bin mir nicht sicher, ob es damit zusammenhängt, aber dies begann etwa 24 Stunden, nachdem wir von 3.3.3 auf 3.3.4 aktualisiert hatten. Ich sehe keine kürzlichen Änderungen an app/jobs/regular/sync_topic_user_bookmarked.rb und konnte keine Änderung in 3.3.4 feststellen, die damit zusammenhängen könnte, aber ich kenne den Code nicht.

Irgendwelche Hinweise, was passieren könnte?

Ein Update dazu. Wir haben gerade festgestellt, dass die 3 Topic-IDs, über die die Aufgaben immer wieder ausgeführt werden, Topics sind, für die wir gestern, kurz bevor dies begann, die automatische Löschung von Antworten aktiviert haben. Es handelt sich allesamt um sehr große Topics.

Wir kennen also den Auslöser, aber die wiederholte SQL-Abfrage scheint keine Stapelverarbeitung durchzuführen, daher verstehe ich nicht, warum sie immer wieder ausgeführt wird.

Wird dies durch einen anderen Job ausgelöst, der immer noch die große Anzahl von Antworten löscht, und Jobs::SyncTopicUserBookmarked wird für jeden einzelnen gelöschten Beitrag ausgeführt? Oder ist dies ein Fehler?

Wir haben die automatische Löschung für eines der großen Topics entfernt, und dies schien keinen Einfluss auf die wiederholten Aufrufe von Jobs::SyncTopicUserBookmarked für diese Topic-ID zu haben.

Ich habe SIDEKIQ_WORKERS auf 2 reduziert und kurz darauf hat sich die Warteschlange (mit vielen ausstehenden Dingen) geleert und es laufen keine Jobs::SyncTopicUserBookmarked mehr… :thinking:

Bevor ich das versucht habe, habe ich die untenstehende Abfrage mehrmals gleichzeitig laufen sehen (mit derselben topic id):

SELECT bookmarks.user_id, COUNT(*)
INTO TEMP TABLE tmp_sync_topic_user_bookmarks
FROM bookmarks
LEFT JOIN posts ON posts.id = bookmarks.bookmarkable_id AND bookmarks.bookmarkable_type = 'Post'
LEFT JOIN topics ON (topics.id = bookmarks.bookmarkable_id AND bookmarks.bookmarkable_type = 'Topic') OR
 (topics.id = posts.topic_id)
WHERE (topics.id = 51303 OR posts.topic_id = 51303)
AND posts.deleted_at IS NULL AND topics.deleted_at IS NULL
GROUP BY bookmarks.user_id;

UPDATE topic_users
SET bookmarked = true
FROM tmp_sync_topic_user_bookmarks
WHERE topic_users.user_id = tmp_sync_topic_user_bookmarks.user_id AND
  topic_users.topic_id = 51303 AND
  tmp_sync_topic_user_bookmarks.count > 0;

UPDATE topic_users
SET bookmarked = false
FROM tmp_sync_topic_user_bookmarks
WHERE topic_users.topic_id = 51303 AND
  topic_users.bookmarked = true AND
  topic_users.user_id NOT IN (
    SELECT tmp_sync_topic_user_bookmarks.user_id
    FROM tmp_sync_topic_user_bookmarks
  );

DROP TABLE tmp_sync_topic_user_bookmarks;

Mir ist nicht klar, wie PostgreSQL mehrere Anweisungen in einer einzigen Abfrage ausführt, aber wenn sie mehrmals gleichzeitig ausgeführt wird, könnte das eine Schleife verursachen?