Skip to content

Checkpoint before follow-up message - #2684

Merged
amirbiron merged 3 commits into
mainfrom
fix/themes-list-cache
Jan 12, 2026
Merged

Checkpoint before follow-up message#2684
amirbiron merged 3 commits into
mainfrom
fix/themes-list-cache

Conversation

@amirbiron

@amirbironamirbiron commented Jan 12, 2026

Copy link
Copy Markdown
Owner

מה שופץ כדי להאיץ את /api/themes/list
ב־services/shared_theme_service.py הוספתי cache בזיכרון ל־SharedThemeService.get_all_active() עם TTL של 5 דקות, כדי שלא תהיה שאילתת Mongo בכל בקשה.

בנוסף:

איפוס cache אחרי פעולות שינוי (create/update/delete) באמצעות invalidate_cache().
המרת _id ל־str כדי למנוע בעיות סריאליזציה אם זה ObjectId.
ensure_indexes() ליצירת אינדקס compound (best-effort, לא שובר טסטים אם לא נתמך).
הקוד המרכזי (כולל cache + אינדקסים + invalidate):

/workspace/services/shared_theme_service.py
Lines 51-192

def__init__(self, db):
""" Args: db: אובייקט DB בסגנון PyMongo (חייב להכיל shared_themes collection) """self.db=dbself.collection=getattr(db, "shared_themes", None)
# ==========================# In-memory cache (active themes list)# ==========================self._active_themes_cache: Optional[List[Dict[str, Any]]] =Noneself._active_themes_expires_at: Optional[datetime] =Noneself._cache_ttl_seconds=300# 5 minutes# Optional: best-effort index creation (safe if unsupported)self.ensure_indexes()
definvalidate_cache(self) ->None:
"""איפוס cache (יש לקרוא אחרי create/update/delete)."""self._active_themes_cache=Noneself._active_themes_expires_at=Nonedefensure_indexes(self) ->None:
"""יוצר אינדקסים בסיסיים לשיפור ביצועים (best-effort)."""ifself.collectionisNone:
returntry:
create_index=getattr(self.collection, "create_index", None)
ifnotcallable(create_index):
return# Compound index for is_active + order + created_atcreate_index([("is_active", 1), ("order", 1), ("created_at", -1)])
exceptExceptionase:
# לא שוברים את האפליקציה/טסטים בגלל אינדקסיםlogger.debug("SharedThemeService.ensure_indexes failed: %s", e)
defget_all_active(self) ->List[Dict[str, Any]]:
"""קבלת כל הערכות הפעילות (מטא-דאטה בלבד)."""ifself.collectionisNone:
return []
now=datetime.now(timezone.utc)
# Cache hitif (
self._active_themes_cacheisnotNoneandself._active_themes_expires_atisnotNoneandself._active_themes_expires_at>now
):
returnself._active_themes_cachetry:
cursor=self.collection.find(
{"is_active": True},
{
"_id": 1,
"name": 1,
"description": 1,
"is_featured": 1,
"created_at": 1,
"order": 1,
},
).sort([("order", 1), ("created_at", -1)])
themes: List[Dict[str, Any]] = []
fordocincursor:
created_at=doc.get("created_at")
theme_id=doc.get("_id")
themes.append(
{
# ⚠️ JSON safety: ObjectId לא תמיד סיריאליזבילי, אז ממירים ל-str"id": str(theme_id) iftheme_idisnotNoneelseNone,
"name": doc.get("name"),
"description": doc.get("description", ""),
"is_featured": bool(doc.get("is_featured", False)),
"created_at": created_at.isoformat() ifisinstance(created_at, datetime) elseNone,
"type": "shared",
}
)
# Save to cacheself._active_themes_cache=themesself._active_themes_expires_at=now+timedelta(seconds=self._cache_ttl_seconds)
returnthemesexceptExceptionase:
logger.exception("SharedThemeService.get_all_active failed: %s", e)
return []

Note

Speeds up fetching shared themes and reduces DB load by caching and indexing the active themes list.

  • Adds a 5‑minute in‑memory cache for SharedThemeService.get_all_active() with versioned invalidation to avoid races and returns defensive copies
  • Converts Mongo _id to str for JSON safety in get_all_active
  • Calls invalidate_cache() after create, update, and delete
  • Introduces ensure_indexes() to create a compound index on shared_themes (is_active, order, created_at) best‑effort
  • Minor import update to use timedelta; no external API changes

Files: services/shared_theme_service.py

Written by Cursor Bugbot for commit 3317c07. This will update automatically on new commits. Configure here.

Co-authored-by: amirbiron <amirbiron@gmail.com>
@chatgpt-codex-connector

Copy link
Copy Markdown

You have reached your Codex usage limits for code reviews. You can see your limits in the Codex usage dashboard.

@github-actions

github-actionsBot commented Jan 12, 2026

Copy link
Copy Markdown
Contributor

🧯 Dangerous deletes guard report

Policy: see .cursorrules — dangerous deletions are blocked unless wrapped safely.

Summary:

  • Flagged findings (blocking): 0
    0
  • Excluded matches (not blocking): 15
  • Total matches (all files): 125

Flagged findings (file:line:snippet):
(none)

Excluded matches (by path pattern)
./Dockerfile:42: rm -rf /var/lib/apt/lists/*
./Dockerfile:121: rm -rf /var/lib/apt/lists/*
./webapp/static/js/md_preview.bundle.js.map:4: "sourcesContent": ["// Markdown-it plugin to render GitHub-style task lists; see\n//\n// https://github.com/blog/1375-task-lists-in-gfm-issues-pulls-comments\n// https://github.com/blog/1825-t … [truncated]
./README.md:842:find . -name "__pycache__" -exec rm -rf {} +
./docs/DOCUMENTATION_GUIDE.md:453:rm -rf _build
./docs/Makefile:24:	rm -rf $(BUILDDIR)
./node_modules/mermaid/dist/chunks/mermaid.core/chunk-KS23V3DP.mjs.map:4: "sourcesContent": ["{\n \"name\": \"mermaid\",\n \"version\": \"11.12.0\",\n \"description\": \"Markdown-ish syntax for generating flowcharts, mindmaps, sequence … [truncated]
./node_modules/mermaid/dist/chunks/mermaid.esm.min/chunk-4HFYJGYH.mjs.map:4: "sourcesContent": ["{\n \"name\": \"mermaid\",\n \"version\": \"11.12.0\",\n \"description\": \"Markdown-ish syntax for generating flowcharts, mindmaps, sequen … [truncated]
./node_modules/mermaid/dist/chunks/mermaid.esm.min/chunk-4HFYJGYH.mjs:1:var r={name:"mermaid",version:"11.12.0",description:"Markdown-ish syntax for generating flowcharts, mindmaps, sequence diagrams, class diagrams, gantt charts, git graph … [truncated]
./node_modules/mermaid/dist/chunks/mermaid.esm/chunk-2M32CCKP.mjs.map:4: "sourcesContent": ["{\n \"name\": \"mermaid\",\n \"version\": \"11.12.0\",\n \"description\": \"Markdown-ish syntax for generating flowcharts, mindmaps, sequence d … [truncated]
./node_modules/mermaid/dist/mermaid.min.js:1524:`,"getStyles"),c1e=RQe});var h1e={};dr(h1e,{diagram:()=>NQe});var NQe,f1e=N(()=>{"use strict";$ge();a1e();l1e();u1e();NQe={parser:Fge,db:n1e,renderer:o1e,styles:c1e}});var m1e,g1e=N(()=>{"use … [truncated]
./node_modules/mermaid/dist/mermaid.js.map:4: "sourcesContent": ["/**\n* Default values for dimensions\n*/\nconst defaultIconDimensions = Object.freeze({\n\tleft: 0,\n\ttop: 0,\n\twidth: 16,\n\theight: 16\n});\n/**\n* Default values for tr … [truncated]
./node_modules/mermaid/dist/mermaid.min.js.map:4: "sourcesContent": ["/**\n* Default values for dimensions\n*/\nconst defaultIconDimensions = Object.freeze({\n\tleft: 0,\n\ttop: 0,\n\twidth: 16,\n\theight: 16\n});\n/**\n* Default values fo … [truncated]
./node_modules/katex/package.json:153: "build": "rimraf dist/ && mkdirp dist && cp README.md dist && rollup -c --failAfterWarnings && webpack && node update-sri.js package dist/README.md",
./node_modules/katex/src/fonts/Makefile:139:	rm -rf pfa ff otf ttf woff woff2

@github-actions

github-actionsBot commented Jan 12, 2026

Copy link
Copy Markdown
Contributor

⏱️ Performance report

(No performance test durations collected. Mark tests with @pytest.mark.performance.)

@github-actions

github-actionsBot commented Jan 12, 2026

Copy link
Copy Markdown
Contributor

📖 Documentation Preview

The documentation has been built successfully!

To view locally:

  1. Download the artifacts
  2. Extract the zip file
  3. Open index.html in your browser

@sentry

sentryBot commented Jan 12, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 67.64706% with 11 lines in your changes missing coverage. Please review.

Files with missing linesPatch %Lines
services/shared_theme_service.py67.64%7 Missing and 4 partials ⚠️

📢 Thoughts on this report? Let us know!

Comment threadservices/shared_theme_service.py Outdated
Prevent cached shared themes list from being mutated by callers by returning copies on both cache hits and misses.
@amirbiron
amirbiron marked this pull request as draft January 12, 2026 20:55
@amirbiron
amirbiron marked this pull request as ready for review January 12, 2026 20:55
@chatgpt-codex-connector

Copy link
Copy Markdown

You have reached your Codex usage limits for code reviews. You can see your limits in the Codex usage dashboard.

Comment threadservices/shared_theme_service.py Outdated
Comment threadservices/shared_theme_service.py Outdated
Use local snapshots for cache reads and a cache version counter to prevent invalidate_cache() from being overwritten by concurrent refreshes.
@amirbiron
amirbiron marked this pull request as draft January 12, 2026 21:13
@amirbiron
amirbiron marked this pull request as ready for review January 12, 2026 21:13
@chatgpt-codex-connector

Copy link
Copy Markdown

You have reached your Codex usage limits for code reviews. You can see your limits in the Codex usage dashboard.

@amirbiron
amirbiron merged commit 2c339a0 into mainJan 12, 2026
40 checks passed
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants

@amirbiron@cursoragent