Systems were never systems
The 27 top-level rows were disciplines and care settings — Cardiology,
Emergency Medicine, Neonatology, and a stray condition (Sepsis) — not organ
systems. Cardiology is a discipline; Cardiovascular System is a system. So the
facet was mislabelled, and there was no organ-system axis at all.
Both fixes, as asked:
* that tree is now the "Topics" facet, which is what it always was;
* "Systems" is a new flat axis of 16 organ systems, matching how AMBOSS keeps
Systems flat while nesting Disciplines and Symptoms.
Tags can nest (migration e3f4a5b6c7d8)
`question_tags` gains parent_id and sort_order. A tag may sit under one of the
same kind (Surgery > Hand surgery) or under a system, which is how symptoms are
grouped by where they present. 726 symptoms are now filed under the system they
appear in; the remaining 3,536 stay top-level rather than being forced into an
approximate bucket. A false positive the dry run caught: "vision" was matching
"Health Supervision" — the same trap as erythema/erythematosus earlier, fixed
with a word boundary.
Admin can grow the taxonomy without a migration
POST /tags creates a top-level entry or a child; PATCH renames, reorders and
reparents, refusing a cycle; DELETE reparents children to the deleted tag's
parent rather than orphaning them, and can move its questions elsewhere;
POST /tags/{id}/questions attaches questions. Everything appears in every picker
immediately, because they all read the same endpoint.
Article sections were indexed but empty — `_rebuild_section_index` only runs on
save, so articles written before it existed had no rows. Backfilled: 10 articles,
28 sections, now embedded and searchable. Section-scoped question links already
worked (7 of 34 links name a section).
Tests: 10 new backend covering the tree shape, adding top-level and child
entries, kind rules, duplicate refusal, cycle refusal, rename/reparent, question
attachment, delete-reparents-children, delete-with-move, and the moderator gate.
141 backend, 136 frontend green.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017acfNLsJpnkvH3sCZSjMJM
37 lines
1.2 KiB
Python
37 lines
1.2 KiB
Python
"""Project existing article sections into the section index.
|
|
|
|
`_rebuild_section_index` runs when an article is saved, so articles written
|
|
before that existed have no rows — the index was empty and section-level
|
|
retrieval had nothing to search.
|
|
|
|
docker compose exec backend python -m scripts.backfill_section_index
|
|
docker compose exec backend python -m scripts.backfill_section_index --apply
|
|
"""
|
|
import sys
|
|
|
|
from app.database import SessionLocal
|
|
from app.models.article import Article
|
|
from app.routers.articles import _rebuild_section_index
|
|
|
|
|
|
def main():
|
|
apply_changes = "--apply" in sys.argv
|
|
db = SessionLocal()
|
|
try:
|
|
articles = db.query(Article).all()
|
|
sections = sum(len(a.sections or []) for a in articles)
|
|
print(f" articles : {len(articles)}")
|
|
print(f" sections : {sections}")
|
|
if apply_changes:
|
|
for article in articles:
|
|
_rebuild_section_index(db, article)
|
|
db.commit()
|
|
print(" indexed and embedded.")
|
|
else:
|
|
print("\n Re-run with --apply to build the index.")
|
|
finally:
|
|
db.close()
|
|
|
|
|
|
if __name__ == "__main__":
|
|
sys.exit(main())
|