CIMPL Class Library (aka Objective FHIR)

Note: This documentation is in draft form.


Table of Contents


Introduction

CIMPL (Clinical Information Modeling Profiling Language) is a specially-designed language for defining clinical information models. It is simple and compact, with tools to produce Fast Healthcare Interoperability Resources (FHIR) profiles, extensions and implementation guides (IG). Because it is a language, written in text statements, CIMPL encourages distributed, team-based development using conventional source-code control tools such as Github. CIMPL provides tooling that enables you to define a model once, and publish that model to multiple versions of FHIR.

Purpose of this Document

This document presents an overview of the CIMPL class library (also known as Objective FHIR, or OBF), a set of pre-mapped datatypes and classes that can be used as the basis for a clinical model. Use of OBF with CIMPL is optional, but recommended. Using only the OBF datatypes with CIMPL is also possible and appropriate for some projects.

Intended Audience

The CIMPL Class Library Guide is targeted to modelers with some familiarity with CIMPL. Experience with object-oriented modeling, concepts such as class inheritance, is assumed. Familiarity with FHIR is helpful as the tutorial references FHIR artifacts (such as Resources, Elements, etc.)

Prerequisite

This guide assumes you have:

Overview

Objective FHIR ("OBF") is an object-oriented abstraction of FHIR. It provides modelers a way to define a detailed clinical information model by subclassing, extending, and constraining a pre-existing class library. These classes can then be translated automatically into FHIR profiles, FHIR Implementation Guides, data dictionaries, schemas, and other assets, using a choice of the three major FHIR versions: DSTU 2, STU 3, and R4.

OBF serves as the base class library for the Clinical Information Modeling and Profiling Language (CIMPL). Use of OBF with CIMPL is optional, but recommended. "blank slate" use of CIMPL is also possible and appropriate for some projects.

(TO DO: Move discussion of Blank Slate approach to here)

Philosophy

OBF classes resemble FHIR R4, but differ in carefully considered ways that increase consistency and reusability of the resulting models and profiles. Objective FHIR allows data structures of all sorts to be reused. This means that individual data elements and frequently-occurring structures can be defined once and used repeatedly.

Objective FHIR addresses one of the most frequent criticisms of FHIR, namely, its lack of consistency. FHIR not only uses different names for equivalent things in different resources, but sometimes, entirely different modeling approaches. This is the result of having resources managed by separate HL7 work groups. OBF creates a layer that smooths over many of these differences, not for aesthetic or theoretical reasons, but to make the whole framework easier to learn, enable greater code reuse, and most importantly, to make the resulting clinical models more interoperable.

OBF also insulates modelers from differences between FHIR versions. The OBF classes are based on FHIR R4, but the same content is mapped to DSTU 2 and STU 3. This means you can model once and publish the same content across multiple FHIR versions.

Meta-Model

Objective FHIR has been developed using the Clinical Information Modeling and Profiling Language (CIMPL). CIMPL is a powerful, FHIR-aware, high-level language for creating clinical models. Expressing the model in CIMPL means that Objective FHIR models can be automatically turned into FHIR Profiles, Implementation Guides, data dictionaries, and other useful artifacts, across multiple FHIR versions.

Conceptually, nothing prevents the same model from be expressed in other formalisms, some of which are mentioned in the Appendix. However, OBF with CIMPL is a complete, proven, ready-made solution that has created rich FHIR content, such as the mCODE Implementation Guide.

Mapping to FHIR

One of the significant benefits of the OBF framework, compared with starting from scratch, is that mapping to FHIR has already been done for you. In most cases, any model you create will be mapped to FHIR without additional effort. The only exceptions are when you create a new class that doesn't inherit from a pre-mapped OBF class (rare), override a previous mapping (very rare), or add an extension to a pre-mapped class that requires mapping to a nested extension (even more rare).

Coverage

Not all FHIR R4 resources are covered by Objective FHIR. We are working to expand the coverage. The model documentation is the best source to determine if OBF covers your needs. If you need additional class coverage for your project, please contact the project team.

Subclassing

To continue the scenario above, suppose you want a more specific concept of OccurrencePeriod applied to a surgical procedure. In this case, we can subclass:

Element:  SurgicalProcedureOccurrencePeriod
Parent:  OccurrencePeriod
Description: The period of time for a surgery, from the first incision time to the last incision close time, as defined by https://manual.jointcommission.org/releases/archive/TJC2010B/DataElem0127.html.

The structure and content of OccurrenceTime is inherited by the new class (cardinalities, data type, the fact that the start time must be less than the end time, etc.), so repeating that information is unnecessary. Don't repeat yourself (DRY) is a major benefit of inheritance. The DRY principle is stated as "Every piece of knowledge must have a single, unambiguous, authoritative representation within a system".

Subclassing, Part 2

The previous example is trivial, but almost everything you do in OBF will involve creating new classes from existing ones. Here's a more involved example:

Entry:             GenomicsReport
Parent:            DiagnosticReport
Description:       "Genetic analysis summary report. The report may include one or more tests, with two distinct test types... (truncated)"
Property:          SpecimenType 0..1
Property:          RegionStudied 0..*
                   Code from https://www.ncbi.nlm.nih.gov/gtr (preferred)
                   Category 1..1
                   Category = DS#GE "Genetics"
                   Observation
                      includes GeneticVariantFound 0..* 
                      includes GeneticVariantTested 0..*
                   SpecimenType from GeneticSpecimenTypeVS (extensible)

Although the purpose of this guide is not to teach CIMPL, this is worth pulling apart:

After the keyword section, there is a series of constraint statements. Without delving into details, these statements say:

We now have a general-purpose genomics report. We can use this class in the form of a FHIR profile, or use it as a parent for defining more specific genomics reports, perhaps AncestryDotComGenomicsReport.

Comparison Between Profiling Tools

In FHIR terms, subclassing is akin to profiling profiles, which can be achieved in a number of tools, notably Forge and Trifolia. Both these tools are extremely well-done, and supported by commercial entities.

Forge and Trifolia are essentially graphical user interfaces on top of StructureDefinitions, the low-level "assembly language" of FHIR. By contrast, CIMPL is like a high-level programming language. Experience has shown that creating and maintaining a complex project is much easier when you use a language, compared to a visual editor. That's why programming languages are almost always text-based, while visual programming has had comparatively little uptake. Even Unified Modeling Language (UML) - a model-diagramming standard that has been around for decades - is fraught with portability problems, despite having its own exchange format, XMI. As stated by Thomas Beale, "Architects these days tend to limit their use of UML to package diagrams and a few illustrative class diagrams, while developers tend to go straight to code or use tools that pretty-print extracted textual forms of software such as swagger and apiary." (emphasis added). CIMPL takes the latter approach, producing a variety of explanatory and implementable assets generated from CIMPL code, rather than vice versa.

When clinical modeling projects grow to a certain size, activities increasingly revolve around repeatedly revisiting, revising, refactoring, and renaming. As a text language, CIMPL allows you to do global search and replace, which will become your new BFF. Using text also enables meaningful source code control. CIMPL files can be hosted in Github, which gives model developers the ability distribute work across multiple branches, compare changes (with meaningful diffs), and automatically merge contributions, allowing projects to scale in ways that visual editors can't support.

Key Concepts

Data Types

The primitive types used in OBF are those defined in CIMPL, which correspond one-to-one with FHIR primitives, except for the way CIMPL handles coded types.

Complex data types in OBF are also the same as FHIR R4. They are found in the obf.datatype namespace. Since complex types like Quantity are ubiquitous, you will almost certainly need to import the obf.datatype into your namespace. This is done using the Uses keyword.

Naming

Attribute names in OBF may differ from FHIR names. When they do so, it is usually to make the meaning of the attribute more explicit. OBF names are meant to be meaningful outside of the context of a single class.

For example, the FHIR attribute Encounter.period is not entirely self-explanatory, especially when period is considered alone, outside of the context provided by Encounter. To be more reusable, OBF uses the name OccurrencePeriod. Coupled with a different event, such as a procedure, the renamed attribute's meaning is more clear. Although an attribute name is rarely a sufficient definition, OBF moves the needle in that direction.

OBF Actors

Name Description
SubjectOfRecord Identifies the person whose clinical record contains the information. The SubjectOfRecord is often the same as the Patient or Subject, but in some cases, the subject of information (called the FocalSubject) may be different than the SubjectOfRecord.
InformationSource The originator or source of the information or request: a practitioner, patient, related person, organization, an algorithm, device, etc.
Author The actor who created the item and it responsible for the content (regardless of the information source or who recorded it). If only the author is given, it is assumed the author is the information source and the recorder.
FocalSubject The person or entity that the information in this resource relates to, if different than the person of record.
Participant An actor (usually a Practitioner, Patient, or Organization but potentially a device or other entity) that participates in a healthcare task or activity. The participant is not necessarily the performer of the action.
Performer The actor that carried out the observation or action.

Note: Currently, OBF doesn't include the information recorder among the key actors. The recorder is the actor who physically enters the information, as opposed to creating or being responsible for the information. Author is occasionally mapped to a FHIR attribute named recorder when it is apparent that the resource designers assumed the author and recorder are the same.

OBF Event Times

Name Description
CreationDateTime The point in time when an ancillary item (such as a report or image) was created.
OccurrenceTimeOrPeriod The time or period when the event occurred.
StatementDateTime The time when the documentation of an event, action, or situation was created.
RelevantTime The time or time period that the statement addresses, not necessarily when the information is gathered.
LastUpdated The last time a record was updated.

Building Blocks

OBF classes fall into one of four categories, which are the building blocks of CIMPL:

Building Block Description Inherits from Analogous FHIR Type
Element The lowest-level building block, representing a property-value pair. Element Property or simple extension
Group A building block comprised of other building blocks, specifically, other Groups, Elements, and Entries. Group Backbone element or complex extension
Entry A building block representing a group of related information, complete enough to support stand-alone interpretation. Entry or Abstract Resource or Profile
Abstract A special type of Entry that cannot be instantiated, and will not be present in the target mapping. Abstract none

Class Hierarchy

In this section, we describe the overall organization and some key classes in Objective FHIR. A pared-down view of the OBF hierarchy is shown below. For full details of each class, please refer to the OBF Reference Model Specification.

The Objective FHIR Class Hierarchy (partial)

The purpose of the hierarchy is two-fold:

  1. To define properties uniformly across multiple classes. For example, almost every FHIR resource should have an author, but many don't, and those that do use a variety of different names. It shouldn't be left up to individual resources, managed by different work groups, to each define their own versions of "author". Inevitably, they will define it differently, or forget entirely, as FHIR R4 shows. Inheriting from a common parent prevents that.
  2. To provide a set of ready-made classes that users can extend. An example is QuantitativeLaboratoryObservation, based on Observation.

FHIR's approach to uniformity is to define certain patterns, such as the request pattern. However, FHIR stops short of actually implementing these patterns across resources. Implementations can't assume all requests have the same core properties, and can't write generic methods for processing requests. Instead, each type of request must be implemented as a one-off.

Resource, Domain Resource, Metadata

At the top of the OBF hierarchy are the classes Resource and DomainResource. They involve the Metadata group. These classes align with FHIR.

Information Item

InformationItem includes definitional items, value set definitions, questionnaire, research study, entities such as locations and organizations, people, financial information, etc. While InformationItem has no attributes itself, it serves as a conceptual grouper for things that exist in the clinical world that are not statements about a patient's health or healthcare.

EntityOrRole

This branch of the hierarchy, which splits into Entity and Role, represent the potential actors in healthcare scenarios.

Clinical Statement

ClinicalStatement provides properties and behaviors common to entries in a medical record. This class also allows for common representation of simple data provenance elements: SubjectOfRecord, CareContext (Encounter or EpisodeOfCare), and StatementDateTime.

Below ClinicalStatement are two classes, SituationStatement and ActionStatement:

Future

Current work is focused on using the classes defined in Objective FHIR directly in implementations, leveraging automatically generated Javascript classes and methods that, at runtime, translate FHIR resources to and from the logical model classes. This would allow implementers to use object oriented programming in much more powerful ways than available in native FHIR, with its flat class structure and complex extension representations.

Appendix: Relationship to Other Initiatives

Conceptually, the models in Objective FHIR could be expressed in modeling frameworks other than CIMPL. Some of the potential frameworks include:

Objective FHIR is an open source project, and we welcome contributions.