npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@openhi/types

v0.0.23

Published

TypeScript types for FHIR and OpenHI domains. Published as a single npm package from the [OpenHI](https://github.com/codedrifters/openhi) monorepo.

Readme

@openhi/types

TypeScript types for FHIR and OpenHI domains. Published as a single npm package from the OpenHI monorepo.

What’s in this package

FHIR R4 types generated from HL7 FHIR R4 JSON Schemas (e.g. Patient, Bundle, CodeSystem, ValueSet, Resource, DomainResource). Use for EHR and FHIR-aligned APIs. The main entry re-exports all types.

Installation

pnpm add @openhi/types
# or
npm install @openhi/types

Usage

import type { Patient, Bundle, CodeableConcept } from "@openhi/types";
import type { Patient, HumanName, Identifier } from "@openhi/types";

function formatPatientName(patient: Patient): string {
  const name = patient.name?.[0];
  return name ? [name.given?.join(" "), name.family].filter(Boolean).join(" ") : "";
}

Building and testing (monorepo)

From the repository root:

pnpm install
pnpm build --filter @openhi/types
pnpm test --filter @openhi/types

From this package directory (packages/@openhi/types):

pnpm install   # at repo root first if needed
pnpm run build
pnpm run test

Authoring OpenHI StructureDefinitions (FSH)

Status: experimental — experiment/fhir-types-codegen, issue #830. See ADR 2026-04-20-01.

OpenHI-owned FHIR types — extensions, control-plane resources (User, Tenant, Workspace, Membership, RoleAssignment, Role), and future data-plane profiles — are authored as FSH and compiled to StructureDefinition JSON by Sushi. The same generator that consumes hl7.fhir.r4.core also consumes OpenHI SDs, so every OpenHI-authored type flows through one pipeline (ADR §2).

See fsh/README.md for detailed authoring conventions — which FSH keyword to use for each shape, the SUSHI Resource: parent constraint, and the PascalCase Id: invariant the IR builder relies on.

Canonical URL scheme

Every OpenHI-authored StructureDefinition resolves to:

https://openhi.org/fhir/StructureDefinition/{id}

This is set once in fsh/sushi-config.yaml via canonical: https://openhi.org/fhir — Sushi appends /StructureDefinition/{id} to produce each SD's URL. Individual FSH files only declare Id:.

Repository layout

packages/@openhi/types/
├── fsh/
│   ├── sushi-config.yaml             # canonical URL + Sushi knobs
│   ├── input/fsh/
│   │   ├── *.fsh                     # data-plane extensions (authored)
│   │   └── control-plane/*.fsh       # control-plane resources + terminology
│   └── fsh-generated/                # Sushi output (gitignored)
├── sds/openhi/
│   ├── data-plane/*.json             # staged for generator (gitignored)
│   └── control-plane/*.json          # staged for generator (gitignored)
└── src/
    ├── data/                         # emitted FHIR + extension accessors
    └── control/                      # emitted control-plane resources
                                      # (committed — regenerated on every build;
                                      # the drift check in CI fails if hand-edited)

Authoring an extension

Single-file example — see fsh/input/fsh/PreferredPronouns.fsh:

Extension: PreferredPronouns
Id: preferred-pronouns
Title: "Preferred Pronouns"
Description: "A patient's preferred pronouns (free text)."
Context: Patient
* value[x] only string

The generator emits an accessor module per ADR §5 — getPreferredPronouns(patient) / setPreferredPronouns(patient, "they/them") — rather than a subtype of Patient. Extensions with max: "*" get get / add / remove variants instead. The base Patient type stays wire-faithful.

Authoring a specialization

Specializations — new resources, or refinements of a FHIR base like PersonUser — use FSH's Logical: or Resource: keyword with a Parent: line so Sushi emits derivation: specialization (the Profile: keyword would produce derivation: constraint instead, which the generator skips). Control-plane files live under fsh/input/fsh/control-plane/.

Resource: is for net-new FHIR resources (Membership, Role, RoleAssignment) and only accepts Resource or DomainResource as a parent — a SUSHI constraint, not a FHIR one. To specialize a concrete FHIR resource (e.g. User extending Person) with a different resourceType literal, use Logical: instead:

Logical: User
Parent: Person
Id: User
Title: "User"
Description: "OHI control plane resource with Person shape and resourceType \"User\"."
* currentTenant 1..1 Reference(Organization) "Tenant the user is currently acting in"
* currentWorkspace 1..1 Reference(Organization) "Workspace within the tenant"

The generator treats Logical SDs with a FHIR-resource base as resources-with-resourceType-override: the emitted TypeScript is export type User = Omit<Person, "resourceType"> & { resourceType: "User"; ... } (ADR §2 intersection-type form). Id: User (PascalCase matching the name) is required — Sushi prefixes every snapshot element's path with the id, and the IR builder resolves the root element by path === sd.name. See fsh/README.md for the full guide.

Regenerate

pnpm --filter @openhi/types gen

This runs Sushi (with -s so specialization SDs get a snapshot), partitions the resulting StructureDefinition / CodeSystem / ValueSet JSON into sds/openhi/data-plane/ and sds/openhi/control-plane/, and then runs @openhi/types-generator to write TypeScript types, Zod schemas, and extension accessor modules into both src/data/ and src/control/. The same script runs in pre-compile, so the CI build fails (via the existing repo-mutation check) if any emitted file was hand-edited or an upstream SD change wasn't re-committed. The whole pipeline is under 30 seconds cold and a few hundred milliseconds warm.