med-det-samme/docs/fest-dataset.md
Ole-Morten Duesund c4d0ed9c3b FEST offline lookup: dataset contract, cached repository, ranked search
Milestone 8. docs/fest-dataset.md is the interface to the out-of-repo
server job that flattens the M30 Rekvirent extract (FEST, not
Felleskatalogen — decision #8) into slim JSON. The repository
downloads on demand, parses BEFORE overwriting the cache (a failed
refresh can never clobber a working dataset), and serves all searches
from memory. Ranking (prefix > word-prefix > substring) is a pure
object with tests. Every failure mode degrades to manual entry —
autocomplete is a convenience, never a gate.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-10 14:04:05 +02:00

1.8 KiB

FEST slim dataset — contract

The app does offline autocomplete against a slim, pre-flattened JSON file. The job that produces it lives outside this repo: it pulls FEST's open Rekvirent extract (the M30 SOAP/WCF XML dump from DMP), flattens the human-use medication entries, and publishes the JSON behind Caddy or into the Garage bucket. FEST changes slowly; refresh the published file monthly-ish.

Why FEST and not Felleskatalogen: FEST is the open national dataset; Felleskatalogen is licensed editorial content with no open API. Why not live lookups: M30 is a bulk XML dump, not a per-keystroke API — and the phone must work offline.

Where the app loads it from

Innstillinger → FEST-URL (e.g. https://<host>/fest/slim.json). The app downloads on demand, caches to filesDir/fest-slim.json, and reads only the cache afterwards. A staleness nudge appears after ~45 days (dataset updated field), but old data keeps working — autocomplete is a convenience, never a gate.

JSON shape (version 1)

{
  "version": 1,
  "updated": "2026-06-01",
  "entries": [
    {
      "name": "Paracet",
      "strength": "500 mg",
      "unit": "tablett",
      "form": "tablett",
      "atc": "N02BE01",
      "packageSize": 20.0
    }
  ]
}
  • name — preparation name (varenavn), required.
  • strength — display string, may be empty.
  • unit — what one dose counts ("tablett", "ml", "dose"), required.
  • form — FEST's form text, free-form (not this app's MedForm enum; the editor maps it heuristically and lets the user override).
  • atc — ATC code, optional.
  • packageSize — units per package for the most common package, optional.

Unknown extra keys are ignored (ignoreUnknownKeys), so the producer can add fields without breaking older app versions. Bump version only for breaking changes.