refactor(eq2db): base read helpers + dead code removal#151
Merged
Conversation
…moval
Dedup pass over the rearchitected catalogues:
- BaseCatalogue gains _fetchall/_fetchone: one place for the
missing-file guard, Row factory, per-call connection open/close, and
OperationalError graceful degradation (previously only aas._query and
zones.list_expansions handled unbuilt DBs; now every read does, and
connections are explicitly closed instead of leaking to GC).
- 24 copies of the connect/row_factory/exists() boilerplate collapse to
helper calls across spells (5 reads), recipes (5), raids (6 incl. the
ACT trigger/timer reads), zones (list_expansions, expansion_counts)
and aas (_query + total_max_points become thin wrappers).
- Dead code removed (zero references anywhere, code/tests/docs):
ZoneCatalogue.zone_count, Zone.find_by_id,
RaidCatalogue.{find_zone_by_name, list_encounters_for_zone,
list_zones_by_expansion, stats}, plus their now-orphaned SQL blocks
(raids.sql select_zone_cols/select_encounter_cols/find_zone_by_name_ci/
list_encounters_for_zone/list_zones_by_expansion/stats_*;
zones.sql count_zones).
- conftest: the seven duplicated DB_PATH + catalogue.path re-point
pairs become one loop, so the next module can't forget the
catalogue.path half.
Behaviour unchanged on live paths: 1521 tests green, pyright clean,
character spells / spell-scroll / AA-spell endpoints spot-checked.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
VortexUK
added a commit
that referenced
this pull request
Jul 11, 2026
…152) Adversarial review of #144-#151 surfaced three shipped breakages plus regressions and drift; this fixes the lot: Broken pipelines (CONFIRMED crashes, no pytest coverage): - scripts/download_spells.py + scripts/backfill_spell_effects.py still called catalogue.init_db(DB_PATH) against the new no-arg signature (TypeError). Both verified working now (backfill run end-to-end against a fresh temp DB). - scripts/dev/_smoke_test_zones_db.py had five stale module-level zones_db.find_by_name calls (AttributeError). Now runs to completion; it surfaces one pre-existing DATA staleness (bosses_total meta=56 vs 62 actual encounters — curator edits postdate the build stamp). Regressions: - SpellCatalogue.find_by_crc cache went lru_cache(maxsize=4096) → unbounded dict caching misses, fed by client ints via /aa/spell. Restored a 4096 bound with FIFO eviction (+ regression test). - BaseCatalogue._fetchall/_fetchone swallowed ALL OperationalError (incl. 'database is locked') as empty results. Now only the unbuilt-schema class ('no such table/column') degrades — logged at WARNING per CLAUDE.md levels — and real faults propagate again (+ tests for both behaviours). Hazards & drift: - zones model-layer path params: 31 `path: Path = DB_PATH` defaults (bound at import, unre-pointable by conftest, never exercised) become required keywords; ZoneCatalogue.__init__ keeps its default. - :memory: half-support removed from BaseCatalogue.init_db — reads guard on path.exists() so a memory catalogue silently returned empties; docstring now states why it's unsupported. - items.py _str_field/_int_field_zero re-implemented backend/census/_coerce helpers — now delegate to them like spells/recipes already do (_int_field keeps its 0→NULL variant). - New BaseCatalogue._find_exact_then_like: the duplicated exact-then-LIKE name search in spells/recipes now shares one implementation AND runs both queries on one connection (undoing the double-connect the #151 helper conversion introduced). - Log prefixes normalised to CLAUDE.md's [lowercase-with-hyphens]: [spells_db]→[spells-db], [recipes_db]→[recipes-db], [db]→[items-db]. 1524 tests green (3 new), ruff + pyright clean, live /aa/spell and recipe search verified on the dev backend. Co-authored-by: Claude Fable 5 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Dedup + dead-code pass over the rearchitected eq2db catalogues (#144–#150).
Deduplication —
_fetchall/_fetchoneonBaseCatalogueThe single biggest repeated shape left was the read preamble — 24 copies of:
Two base helpers now own the missing-file guard, Row factory, per-call open/close, and
OperationalErrorgraceful degradation. Converted: spells (all 5 reads), recipes (all 5), raids (both revision reads + the 4 ACT trigger/timer reads), zones catalogue-level reads, and aas (_queryandtotal_max_pointsbecome thin wrappers). The zones active-record models keep their own connections — hydration needs the same conn for child fetches.Two behaviour improvements fall out uniformly:
aas._queryandzones.list_expansionscaughtOperationalError; now every read logs + degrades instead of 500ing on a provisioned-but-empty file.with sqlite3.connect(...)which commits but never closes (handle left to GC); the helpers close in afinally.Dead code (zero references anywhere — code, tests, or docs)
ZoneCatalogue.zone_count,Zone.find_by_idRaidCatalogue.find_zone_by_name/list_encounters_for_zone/list_zones_by_expansion/stats— the "for the future web routes" reads from the raids module's PoC era; the strategy routes ended up with their own targeted SQL and nothing ever called these.raids.sql: the zone/encounter column fragments, 3 list queries, 5 stats queries;zones.sql:count_zones).conftest
The seven duplicated
DB_PATH+catalogue.pathre-point pairs collapse into one loop — the next eq2db module can't forget thecatalogue.pathhalf.Verification
1521 tests green, ruff + pyright clean. Live spot-checks on the dev backend across the converted read paths: character spells tab (find_by_ids/upgradeable_crcs),
/api/spell-scroll(recipes find_by_spell),/api/aa/spell/{crc}(find_by_crc + aas caches).🤖 Generated with Claude Code