Skip to content

אוספי לוג גדלים בלי גבול #3312

Description

@amirbiron

אוספי לוג גדלים בלי גבול — TTL קיים אך לא הוחל עליהם

קובץ/מודול מרכזי: database/manager.py (שם כבר יש _create_profiler_indexes עם TTL), ומקום כתיבת שני האוספים. לא תלוי ב: תיקון גבולות הפתק, ולא באף PR פתוח אחר.
חשוב: המנגנון כבר קיים בקוד. הבאג הוא שהוא לא הוחל על שני האוספים הגדולים — לא שהוא חסר. זה תיקון תוספת, לא בנייה מאפס.
מקור הבדיקה: צילומי /db-health ותוכן שני האוספים (ודאי), וחיפוש TTL index בקוד שהחזיר שלושה מקומות שבהם TTL כן קיים (ודאי). הקשר ל-latency של bookmarks — השערה לא מאומתת.


הממצא (ודאי, מהצילומים)

שני אוספים גדולים בסדר גודל של מאות אלפי מסמכים, פי מאה מכל אוסף תוכן אמיתי:

אוסף מסמכים גודל מה זה
service_metrics 435,229 90MB צבירת מדדי observability. כל רשומה request_agg עם bucket_seconds: 60דלי לדקה, פר endpoint
job_runs 305,436 106MB רשומת כל הרצת cron. הדוגמאות: predictive_sampler, sentry_poll, drive_rescheduletotal_items: 0, ריצות סרק שנרשמות

לשם השוואה: code_snippets — 1,121 מסמכים. התוכן האמיתי זעיר מול הלוגים.

הקצב מסביר את הגודל: service_metrics נכתב כל דקה × כל endpoint; job_runs נכתב בכל טיק של כל job. אלה נתונים שנוצרים אוטומטית 24/7 בלי שאף אחד קורא אותם לאחור — הם לתצוגה חיה בדשבורד בלבד.


מה שכבר קיים בקוד (ודאי, מהחיפוש)

TTL כן מיושם — על אוספים אחרים:

  • _create_profiler_indexes ב-database/manager.py: TTL של 7 ימים על slow_queries_log (expireAfterSeconds=604800, name: ttl_cleanup, על שדה timestamp).
  • attention_dismissals: TTL על expires_at (expireAfterSeconds=0 + שדה תאריך במסמך).
  • ensure_lock_indexes ב-main.py: TTL על expires_at/expiresAt של ה-lock collection, עם fallback רך אם היצירה נכשלת.

כלומר יש בפרויקט דפוס TTL מוכן, מוכח, ועם טיפול בכשל. הוא פשוט לא הוחל על job_runs ו-service_metrics.


מה לבדוק לפני כל תיקון (חובה — לא להניח)

  1. האם משהו קורא מ-service_metrics או מ-job_runs לאחור, מעבר לתצוגת הדשבורד. אם ה-observability מחשב מגמות על חלון של שבועות, TTL אגרסיבי ימחק נתונים שהוא צריך. לאתר את כל הקוראים לפני קביעת retention.
  2. האם באמת אין עליהם TTL, או שיש ופג/שגוי. הצילומים מראים TTL על אוספים אחרים; צריך לוודא במפורש ששני אלה חסרים אותו, ולא להסיק מהיעדרם בצילום.
  3. מה ה-retention הנכון לכל אחד. slow_queries_log נקבע ל-7 ימים (604800ש'). ל-service_metrics (תצוגה חיה) אולי מספיק פחות; ל-job_runs אולי יותר, אם יש ערך היסטורי לאבחון. החלטה של אמיר, אחרי שסעיף 1 עונה מי קורא.

הצעת התיקון (אחרי שהבדיקות עונות)

להרחיב את _create_profiler_indexes (או המקום המקביל) ולהוסיף TTL לשני האוספים, באותו דפוס שכבר קיים — כולל ה-fallback הרך של ensure_lock_indexes (אם היצירה נכשלת, לוג ו-emit_event, בלי להפיל).

# אותו דפוס כמו slow_queries_log, על שדה הזמן של כל אוסף
await self.db.service_metrics.create_index("ts", expireAfterSeconds=<retention_1>, name="ttl_cleanup")
await self.db.job_runs.create_index("started_at", expireAfterSeconds=<retention_2>, name="ttl_cleanup")

שם שדה הזמן שונה בין אוספים — וזו מלכודת: slow_queries_log משתמש ב-timestamp (אומת בתיעוד), service_metrics נראה עם ts, ו-job_runs עם started_at/ended_at. שלושה אוספים, שלושה שמות. לא לנחש — לפתוח מסמך מכל אוסף ולראות את שם השדה בפועל.


ההשערה שצריך לבדוק בנפרד (לא מאומתת)

היום אירעה תקלת latency: bookmarks.get_file_bookmarks לקח 152 שניות, ובאותו חלון גם collections.get_tags_metadata ו-api_ui_prefs. ה-JSON של ההתראה הראה שכל הבקשות האיטיות היו על אותו ObjectId (6a9054dd...), ו-db_pool_utilization: 13% — כלומר המסד לא היה רווי. זה מצביע על עיבוד נקודתי של פריט אחד, לא בהכרח על האוספים הגדולים.

מה לבדוק: האם שאילתה כלשהי — של bookmarks, collections, או אחרת — סורקת את service_metrics/job_runs בלי אינדקס מתאים. אם כן, ה-TTL גם ישפר latency (פחות מסמכים לסרוק). אם לא — ה-TTL עדיין נכון מטעמי אחסון, אבל לא יפתור את ה-latency, וזה באג נפרד.

לא להניח שהשניים קשורים. לאמת עם explain() על השאילתות האיטיות.


בדיקות

  1. אחרי הוספת ה-TTL, כתיבת מסמך חדש לכל אוסף → האינדקס קיים (getIndexes() מראה expireAfterSeconds).
  2. מסמך עם שדה זמן ישן מה-retention → נמחק בסבב ה-TTL של מונגו (עד 60ש' לאחר התפוגה).
  3. מסמך טרי → לא נמחק.
  4. יצירת האינדקס נכשלת (הרשאה, קונפליקט) → המערכת ממשיכה, לוג + emit_event, לא קורסת — כמו ensure_lock_indexes.
  5. אם סעיף 1 בבדיקות מצא קורא לאחור: לוודא שהחלון שהוא צריך קצר מה-retention.

מה לא נסגר

  1. מי קורא מהאוספים לאחור — סעיף 1 למעלה, חייב להיענות לפני קביעת retention.
  2. הקשר ל-latency — השערה, טעונה explain().
  3. retention לכל אוסף — החלטת אמיר אחרי שהקוראים ידועים.

לא בסשן

  • שינוי מבנה הרשומות של שני האוספים.
  • שינוי בתדירות הכתיבה (הדלי לדקה, טיק ה-job) — זה מקור הנתונים, לא הבעיה.
  • תיקון ה-latency עצמו אם יתברר שאינו קשור — באג נפרד.

מעדכן:

job_runs 318,797 מסמכים
service_metrics 470,040 מסמכים

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions