Repository navigation
OMOP samples - #107
OMOP samples#107
Conversation
|
On the "Table 1" layout discussion — I dug into why the vertical (journal-style) version needs so much more Malloy than the horizontal nested one, and tested an alternative. Sharing in case it's useful (all of this is run against the Synthea COVID data in this PR and reproduces the vertical table cell-for-cell). Why the vertical version is hard: it needs two things Malloy has no native primitive for — (1) wide→long / UNPIVOT to stack Sex/Race/Ethnicity/Age-band into one column, and (2) mixed row formats in one column ( A simpler alternative — write each section as a plain block query that emits the same columns, and let SQL do only the stacking via Honest tradeoff: this drops to the The real takeaway / possible feature: the fact that the clean version requires either an obscure array-unnest or a SQL escape hatch is good evidence for a language feature — a native Separate heads-up (unrelated to layout): on the repo's pinned |
|
Thanks @jswir for the investigation about table-1 and detailed explanation. I reflected your thoughts in the PR itself to capture that nuance until such time as Malloy has better solution for this. |
Signed-off-by: Ofer Mendelevitch <ofermend@gmail.com>
Add baseline characteristics, cohort outcomes/follow-up, comorbidity burden, and healthcare utilization notebooks. Switch the data source to the Synthea COVID-19 dataset (omop_synthea_covid.malloy), update the shared omop.malloy model and existing notebooks accordingly, and remove the standalone measurement notebook and build_parquet.py script. Signed-off-by: Ofer Mendelevitch <ofermend@gmail.com>
Signed-off-by: Ofer Mendelevitch <ofermend@gmail.com>
Signed-off-by: Ofer Mendelevitch <ofermend@gmail.com>
Signed-off-by: Ofer Mendelevitch <ofermend@gmail.com>
Signed-off-by: Ofer Mendelevitch <ofermend@gmail.com>
584d4c0 to
b84a7af
Compare
Signed-off-by: Ofer Mendelevitch <ofermend@gmail.com>
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Signed-off-by: Ofer Mendelevitch <ofermend@gmail.com>
mtoy-googly-moogly
left a comment
There was a problem hiding this comment.
Really like this sample — the OMOP model and the symmetric-aggregate / vocabulary-join story are great, and the package bump is clean this time (exact pins, no stray deps). One blocker around CI, though.
The OMOP data is gitignored and fetched on-demand, but the test harness isn't told to skip these notebooks — so this will turn main red on merge.
Every omop/*.malloynb does import 'omop.malloy' → omop_synthea_covid.malloy → duckdb.table('omop/data/*.parquet'). Those parquet files aren't committed (they come from setup.sh's ~840 MB download). The DuckDB test suite (tests/duckdb.spec.ts) globs every top-level dir not in EXCEPT_LIST and compiles each .malloynb; omop isn't excluded, so all ~12 notebooks fail at compile with failed-to-fetch-table-schema (IO Error: No files found that match the pattern "omop/data/concept.parquet"). I reproduced this locally.
The fork-PR run masks it (it dies earlier at the GCloud-auth step because fork PRs don't get secrets), but on push-to-main secrets are present, the full suite runs, and it'll fail on these notebooks. It also breaks the repo's stated invariant that the DuckDB suite runs with no setup.
Fix — pick one (there's precedent: apijson.malloynb is in EXCEPT_LIST because it needs the network):
- Add
'omop'toEXCEPT_LISTintests/duckdb.spec.ts(and the bigquery spec) so the suite skips it. Simplest; downside is nothing validates these notebooks in CI. - Add a separate opt-in CI job that runs
omop/scripts/setup.shand then compiles onlyomop/. Real coverage, at the cost of the 840 MB download per run. - Commit the parquet (presumably why it was gitignored — likely too big).
My preference is 1, optionally plus 2 as a dedicated job. Happy to wire up whichever you pick.
Signed-off-by: Ofer Mendelevitch <ofermend@gmail.com>
What this adds
The model captures some OMOP-specific querying challenges Malloy handles well:
The specific dataset has no laboratory results (measurement/observation tables are empty) and unpopulated drug dosing fields, so lab/vital and prescription-length analyses are out of scope. Noted in the README.