Skip to content

Contributing to ReFHIR

Thanks for helping. ReFHIR stores and serves clinical data, so changes are reviewed for correctness and safety first, and for speed second.

  • Found a security problem? Do not open an issue. Follow SECURITY.md.
  • Found a bug or want a feature? Search the issues first, then open one with the template. For anything large, open an issue before writing code so we can agree on the approach.
  • Fixing a typo or a small bug? Send the pull request directly.

Everyone taking part is expected to follow the Code of Conduct.

You need Rust 1.88 (rustup installs it from rust-toolchain.toml). Go 1.23+ and Node 20+ are needed only for the clients, and Docker only for the image and the Postgres TLS tests. The full list is in docs/development.md.

Terminal window
git clone https://github.com/hai-hq/refhir.git
cd refhir
just check # or: cargo fmt --all -- --check && cargo clippy --workspace --all-targets -- -D warnings && cargo test --workspace

CI runs these, so run them first:

Change touches Run
Rust cargo fmt --all, cargo clippy --workspace --all-targets -- -D warnings, cargo test --workspace
Postgres code the Postgres tests, with REFHIR_TEST_POSTGRES_URL set (how)
clients/go cd clients/go && go vet ./... && go test ./...
clients/ts cd clients/ts && npm ci && npm run build && npm test
Markdown python3 scripts/check-doc-links.py

A pull request runs the fast checks: formatting, clippy, build and test, dependency policy, the Helm chart and the docs links. The slower ones run on main: the Postgres and multi-process tests, the release build, the container image, and the SMART Inferno conformance run. If your change touches the database code, the Dockerfile or SMART, run those on your branch first, from the Actions tab (CI → Run workflow, and SMART Inferno smoke → Run workflow), or locally with the instructions in docs/development.md.

Then:

  1. Add a test that fails without your change. Handlers and the engine have unit tests next to them; behavior over HTTP and /sync is covered in crates/server/src/tests.rs, and multi-process behavior in crates/refhir/tests/.
  2. Update the docs if a flag, endpoint, setting or behavior changes. Setting names live in refhir.toml.example, which should document every setting. The website publishes these docs; site/README.md says how to preview or add a page.
  3. Add a line to CHANGELOG.md under Unreleased, in the section that fits (Added, Changed, Fixed, Security). Say what a user notices, not how you did it.
  4. Keep the change focused. A bug fix does not need a refactor alongside it; send that separately.

Write commit messages as a short imperative sentence (“Add /readyz probe”), with detail in the body when the why is not obvious. Squash merging is used, so the pull request title becomes the commit message.

  • Schema changes. Migrations are forward-only and shipped ones are frozen: a database refuses to start if a migration’s checksum changed. Add a new numbered migration to both SQLite and Postgres, and never edit an old one. Read Changing the schema.
  • The /sync protocol and HTTP API. Existing clients depend on them. Add fields rather than change or remove them, and note any break in the changelog.
  • Authorization. Anything that reads or writes a resource must go through scope and compartment enforcement, and anything that touches a record belongs in the audit trail. A new endpoint needs a test that a token without the scope is refused.
  • Secrets. Never commit refhir.toml, tokens, keys or real patient data. Use synthetic data; the examples in fixtures/mock-fhir are safe to copy.

ReFHIR is licensed under the Apache License 2.0. Unless you say otherwise, a contribution you submit is licensed under the same terms, as section 5 of that license provides. Only submit code you wrote, or that you have the right to submit under that license. If you copy anything, say where it came from in the pull request and keep its notices.