{"id":50989354,"url":"https://github.com/fschutt/officium-rs","last_synced_at":"2026-06-20T00:01:25.930Z","repository":{"id":355297618,"uuid":"1227426934","full_name":"fschutt/officium-rs","owner":"fschutt","description":"Divinum Officium rubric core (1570 → 1960) in pure Rust — calendar, occurrence, precedence, mass-propers resolver","archived":false,"fork":false,"pushed_at":"2026-05-11T11:30:23.000Z","size":5674,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":0,"default_branch":"master","last_synced_at":"2026-05-11T11:38:02.822Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":"https://fschutt.github.io/officium-rs/","language":"Rust","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"other","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/fschutt.png","metadata":{"files":{"readme":"README.md","changelog":"HISTORY.md","contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2026-05-02T17:06:04.000Z","updated_at":"2026-05-11T11:30:31.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/fschutt/officium-rs","commit_stats":null,"previous_names":["fschutt/officium-rs"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/fschutt/officium-rs","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/fschutt%2Fofficium-rs","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/fschutt%2Fofficium-rs/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/fschutt%2Fofficium-rs/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/fschutt%2Fofficium-rs/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/fschutt","download_url":"https://codeload.github.com/fschutt/officium-rs/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/fschutt%2Fofficium-rs/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":34552295,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-06-19T02:00:06.005Z","response_time":61,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2026-06-20T00:01:23.479Z","updated_at":"2026-06-20T00:01:25.917Z","avatar_url":"https://github.com/fschutt.png","language":"Rust","funding_links":[],"categories":[],"sub_categories":[],"readme":"# officium-rs\n\n[![Pages][pages-badge]][demo]\n[![Regression][reg-badge]][reg-actions]\n\n[pages-badge]: https://github.com/fschutt/officium-rs/actions/workflows/pages.yml/badge.svg\n[reg-badge]:   https://github.com/fschutt/officium-rs/actions/workflows/regression.yml/badge.svg\n[demo]:        https://fschutt.github.io/officium-rs/\n[reg-actions]: https://github.com/fschutt/officium-rs/actions/workflows/regression.yml\n\nDivinum Officium rubric core in pure Rust. Computes the Roman-rite\nliturgical calendar and resolves Mass propers for any date under any\nof five rubric layers — Tridentine 1570 → Rubrics 1960 (John XXIII) —\nwith 100% output parity against the upstream Perl implementation\nacross a year-sweep regression (21,900 cells × 5 rubrics).\n\n**Demo:** \u003chttps://fschutt.github.io/officium-rs/\u003e — picks any date,\nany of five rubrics, and renders the full Tridentine Mass in the\nbrowser. Latin Ordinary (Kyrie, Gloria, Credo, Sanctus, Pater Noster,\nAgnus Dei, dialog versicles, inline rubrics) interleaved with the\nday's Propers, all driven by a 907 KB WebAssembly bundle (~700 KB\ngzip-served).\n\n## Status\n\n- ✅ Calendar, occurrence, precedence, mass-propers resolution (Latin)\n- ✅ All five rubrics at **100%** parity for 2026 (the development\n  reference year). Across the full ±50-year sweep (1976–2076 × 5\n  rubrics × 365 days = 184 455 cells) the parity rate is **99.86%**;\n  failures cluster on a handful of edge dates per rubric — see\n  [`docs/REGRESSION_RESULTS.md`](docs/REGRESSION_RESULTS.md) and\n  [`docs/UPSTREAM_WEIRDNESSES.md`](docs/UPSTREAM_WEIRDNESSES.md)\n- ✅ WASM build (907 KB raw / ~700 KB gzip / ~660 KB brotli; bindgen\n  API in [`src/wasm.rs`](src/wasm.rs))\n- ✅ Full Mass renderer in the demo\n- ✅ Multi-year regression CI — runs `year-sweep` against the\n  upstream Perl across N years × 5 rubrics\n  ([workflow][reg-actions])\n- ⏳ `no_std` migration\n- ⏳ Monastic rubric\n- ⏳ Office hours (Vespers, Lauds, …) — only Mass today; see\n  [`docs/BREVIARY_PORT_SCOPE.md`](docs/BREVIARY_PORT_SCOPE.md)\n- ⏳ Translations (English, German, …) — Latin only today\n\n[weird]: UPSTREAM_WEIRDNESSES.md\n\n## Architecture\n\nThe crate exposes a `Corpus` trait + pure functions over it. The\ndefault `BundledCorpus` reads from the JSON corpus shipped under\n`data/` (embedded via `include_str!`); consumers can supply their own\nimpl for custom data sources.\n\nRubric layers covered:\n\n| layer            | year       | enum                                   |\n| ---------------- | ---------- | -------------------------------------- |\n| Tridentine 1570  | 1570–1909  | `Rubric::Tridentine1570`               |\n| Tridentine 1910  | 1910–1938  | `Rubric::Tridentine1910`               |\n| Divino Afflatu   | 1939–1954  | `Rubric::DivinoAfflatu1911`            |\n| Reduced 1955     | 1955–1959  | `Rubric::Reduced1955`                  |\n| Rubrics 1960     | 1960–      | `Rubric::Rubrics1960`                  |\n\n## Usage — native\n\n```rust\nuse officium_rs::{\n    core::{Date, Locale, OfficeInput, Rubric},\n    corpus::BundledCorpus,\n    precedence::compute_office,\n    mass::mass_propers,\n};\n\nlet corpus = BundledCorpus;\nlet input = OfficeInput {\n    date:   Date::new(2026, 5, 2),\n    rubric: Rubric::Rubrics1960,\n    locale: Locale::Latin,\n};\n\nlet office = compute_office(\u0026input, \u0026corpus);\nprintln!(\"winner = {}\", office.winner.render());\n// → \"Sancti/05-02\"\n\nlet mass = mass_propers(\u0026office, \u0026corpus);\nif let Some(intr) = \u0026mass.introitus {\n    println!(\"{}\", intr.latin);\n}\n```\n\n## Usage — WASM (browser)\n\nAfter `wasm-pack build` (or `cargo build --target wasm32-unknown-unknown\n--features wasm --no-default-features` + `wasm-bindgen`):\n\n```html\n\u003cscript type=\"module\"\u003e\n  import init, { compute_office_json } from './pkg/officium_rs.js';\n\n  await init();\n  const json = compute_office_json(2026, 5, 2, 'rubrics-1960');\n  const office = JSON.parse(json);\n  console.log(office.winner);   // \"Sancti/05-02\"\n  console.log(office.color);    // \"White\"\n\u003c/script\u003e\n```\n\nV1 ships the `compute_office_json` resolver only — date + rubric in,\nJSON description of the office out (winner path, color, season, rank,\ncommemorations). Full Mass-propers body assembly over WASM is V2.\n\nSee [`demo/`](demo/) for the live deployment source — vanilla HTML +\nES-module JS, no framework.\n\n## Features\n\n| feature       | what it gives you                                       |\n| ------------- | ------------------------------------------------------- |\n| `regression`  | (default) Rust↔Perl comparator + `year-sweep` binary    |\n| `wasm`        | `wasm-bindgen` surface — see `src/wasm.rs`              |\n\nThe `regression` feature is **native-only** — it shells out to the\nupstream Perl runtime for reference-output diffs. Building for\n`wasm32-unknown-unknown` with `regression` enabled triggers a\n`compile_error!`. Use `--no-default-features --features wasm` for\nWASM builds.\n\n## Regression harness\n\nRun the year-sweep against the upstream Perl source (requires `perl5`\nand the bundled CPAN deps; see `scripts/setup-divinum-officium.sh`):\n\n```sh\ngit submodule update --init --recursive    # pulls vendor/divinum-officium\n\n# Single year, single rubric — local development:\ncargo run --bin year-sweep --release -- \\\n    --year 2026 --rubric 'Rubrics 1960 - 1960'\n\n# Multi-year range — for proving long-window parity:\ncargo run --bin year-sweep --release -- \\\n    --years 2016:2036 --rubric 'Tridentine - 1570' --strict\n```\n\nBoards land under `target/regression/{slug}-{year}/board.html`.\nEvery cell green = parity; the published baseline is at the SHA in\n`scripts/divinum-officium.pin` (April 2026 upstream).\n\nContinuous integration runs the same sweep weekly across all five\nrubrics against a configurable year range — see\n[`.github/workflows/regression.yml`](.github/workflows/regression.yml).\nThe default `workflow_dispatch` window is ±10 years (2016 – 2036);\nwider runs (e.g. `1976:2076` for the full ±50) can be triggered\nmanually. Perl-rendered HTML is cached by upstream-pin SHA so re-runs\nagainst the same upstream commit are fast.\n\n## Provenance\n\nThis crate ports the Divinum Officium Perl implementation\n(\u003chttps://github.com/DivinumOfficium/divinum-officium\u003e) — vendored as a\ngit submodule under `vendor/divinum-officium/` for regression testing.\nAll liturgical content remains under the upstream's terms; this crate\nis the rubric *logic* in Rust.\n\n## License\n\nMIT for the Rust code itself. See [`LICENSE`](LICENSE). The vendored\nupstream Perl tree under `vendor/divinum-officium/` carries its own\nlicense terms; data files derived from that tree are subject to them.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ffschutt%2Fofficium-rs","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Ffschutt%2Fofficium-rs","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ffschutt%2Fofficium-rs/lists"}