Skip to content

For AI Agents ​

Use this page when the consumer is an AI coding assistant or another automated tool that needs operational guidance instead of conceptual package docs.

Pick one release first ​

Choose the FHIR release before choosing schemas or model types. Keep the same release in the type import, schema import, and surrounding workflow.

Use fhir-zod/<release>/<Resource> for concrete resources; use fhir-zod/<release> for shared datatypes and release-level exports.

ts
import { PatientSchema, type Patient } from "fhir-zod/r4/Patient";

Do not mix releases unless the code is explicitly translating between them.

Validate unknown JSON ​

Use safeParse when input is untrusted and validation failure should stay in normal control flow.

ts
import { PatientSchema } from "fhir-zod/r4/Patient";

const payload: unknown = await fetch("/api/patient/example").then((response) =>
  response.json(),
);

const result = PatientSchema.safeParse(payload);

if (!result.success) {
  console.error(result.error.issues);
} else {
  console.log(result.data.resourceType);
}

Validate Bundle resources ​

BundleSchema validates the Bundle envelope and recursively validates known entry resources through the release-specific resourceType dispatcher.

ts
import { BundleSchema, type Bundle } from "fhir-zod/r4/Bundle";

const bundle: Bundle = {
  resourceType: "Bundle",
  type: "collection",
  entry: [
    {
      resource: {
        resourceType: "Patient",
        id: "example",
      },
    },
  ],
};

BundleSchema.parse(bundle);

Do not assume ​

  • Structural validation is not full FHIR semantics, terminology validation, or profile validation.
  • Reference.reference does not prove the referenced resource exists.
  • R5, R4B, R4, and STU3 should not be mixed unless the code is translating deliberately.
  • *SchemaInternal symbols are generated implementation details, not public API.

When validation fails ​

Prefer safeParse for repair and retry loops. Inspect result.error.issues, keep the issue paths, and preserve those paths in logs or follow-up prompts so fixes can be targeted to the failing fields.

ts
import { ObservationSchema } from "fhir-zod/r4/Observation";

const payload: unknown = await fetch("/api/observation/example").then(
  (response) => response.json(),
);

const result = ObservationSchema.safeParse(payload);

if (!result.success) {
  const issues = result.error.issues.map((issue) => ({
    code: issue.code,
    message: issue.message,
    path: issue.path,
  }));

  console.error(issues);
}

Use parse only when invalid input should throw immediately and the caller does not need to recover in normal control flow.