openEHR to ISO 13606-1, ISO 21090 mapping

Introduction

This page provides information on which a technical solution to bidirectional openEHR / ISO 13606 conversion can be based. Since ISO 13606 uses the ISO 21090 pre-standard for data types, this mapping necessarily involves an openEHR datatype <-> ISO 21090 mapping as well. Key points to note:

  • there is currently no profile of 21090 (data types) for use in 13606; this means that 13606 currently uses the 'vanilla' 21090 schema and semantics. However many of these don't apply, and guidance now needs to be developed for them in the 13606 context.
  • the requirements for round-tripping faithfully between 13606 and openEHR have not yet been defined. This will essentially be up to users.

ISO 13606-1

ISO 13606-1 is the model of an EHR Extract, designed to enable data to be shared between EHR systems. Technically it resembles the openEHR reference model, but in a simplified way. In particular , the ENTRY types of openEHR are mapped to a single ENTRY type in 13606, but this is not the only difference. A mapping algorithm is being developed that shold allow a bidirectional transform between openEHR and 13606. The algorithm uses two types of mapping:

  • pre-defined class and attribute conversions, such as for the 13606 AUDIT_INFO class and the openEHR AUDIT_DETAILS class
  • a generic algorithm that can be applied between ENTRYs

Predefined conversion rules

Common IM structures

openEHR
class

attribute

type

13606
class

attribute

type

description

exceptions / ambiguities

PATHABLE

 

 

RECORD_COMPONENT

 

 

 

 

 

parent (not persisted)

PATHABLE

 

orig_parent_ref

II [0..1]

rule: generate openEHR URI

see mismatches below

LOCATABLE

 

 

RECORD_COMPONENT

 

 

 

 

 

uid

UID_BASED_ID [0..1]

 

rc_id

II [1]

rule: generate openEHR URI

see mismatches below

 

archetype_node_id

String [1]

 

archetype_id

String [0..1]
/dt:II

rule: String id->II

 

 

name

DV_TEXT [1]

 

name

TEXT [1]
/dt:CD>CV

rule: DV_TEXT -> TEXT

what are possible name values?

 

archetype_details

ARCHETYPED [0..1]

 

 

 

 

 

 

feeder_audit

FEEDER_AUDIT [0..1]

 

feeder_audit

AUDIT_INFO [0..1]

rule: follow link & map

 

 

links

Set<LINK> [0..1]

 

links

Set<LINK> [0..1]

rule: 1:1 iteration

 

 

-

 

 

sensitivity

Integer [0..1]
/rc:Sensitivity

 

MISSING IN OPENEHR - could either be on LOCATABLE or on COMPOSITION

 

 

 

 

policy_ids

SET<II>

 

In openEHR, these settings are in the ACCESS_CONTROL object

 

 

 

 

 

 

 

 

AUDIT_DETAILS

 

 

AUDIT_INFO

 

 

 

 

 

system_id

String [1]

 

ehr_system

II [1]

rule: String id->II

which system id is being used here?

 

committer

PARTY_PROXY [1]

 

committer

II [1]

 

which user id is being used here?

 

time_committed

DV_DATE_TIME [1]

 

time_committed

TS [1]

rule:
DV_DATE_TIME->TS

 

 

change_type

DV_CODED_TEXT [1]

 

reason_for_revision

CV [0..1]
/dt:CD.CV

rule: DV_CODED_TEXT->CV

 

 

description

DV_TEXT [0..1]

 

-

 

 

LOST INFORMATION
[low importance]

+VERSION

lifecycle_state

DV_CODED_TEXT [1]

 

version_status

CS [0..1]
/rc:VersionStatus

rule: DV_CODED_TEXT->CS

 

+VERSION

preceding_version_id

OBJECT_VERSION_ID[1]

 

previous_version

II [0..1]

rule:
OBJECT_VERSION_ID->II

 

+VERSION

owner_id

HIER_OBJECT_ID [1]

 

version_set_id

II [0..1]

rule:
HIER_OBJECT_ID->II

 

PARTY_PROXY

 

 

RELATED_PARTY

 

 

 

 

 

external_ref

PARTY_REF [0..1]

 

party

II [0..1]

rule:
OBJECT_REF->II

LOST INFORMATION: namespace, type?
[not important]

PARTY_IDENTIFIED

 

 

 

 

 

 

 

 

name

String [0..1]

Demographics_package
IDENTIFIED_HEALTHCARE
_PROFESSIONAL

name

ENTITY_NAME[*]

rule: String -> ENTITY_NAME synthesis

 

 

identifiers

List<DV_IDENTIFIER> [0..1]

Demographics_package
IDENTIFIED_HEALTHCARE
_PROFESSIONAL

role

HEALTHCARE_
PROFESSIONAL_
ROLE [*]

rule: for each identifier: DV_IDENTIFIER -> HEALTHCARE_
PROFESSIONAL_ ROLE

 

PARTY_RELATED

 

 

RELATED_PARTY

 

 

 

 

 

relationship

DV_CODED_TEXT [1]

 

relationship

TEXT
/dt:CD.CV

rule: DV_CODED_TEXT->TEXT

 

PARTY_SELF

 

 

RELATED_PARTY

 

 

convert to RELATED_PARTY with relationship = self?

 

PARTICIPATION

 

 

FUNCTIONAL_ROLE

 

 

 

 

 

function

DV_TEXT [1]

 

function

CV [0..1]

rule: DV_CODED_TEXT->CV

LOST INFORMATION
openEHR allows not only coded values; non-matches will be lost

 

performer

PARTY_PROXY [1]

 

performer

II [1]

use rule for: PARTY_PROXY.external_ref

LOST INFORMATION
some openEHR Party information will be lost; 13606 only permits single II identifier

 

time

DV_INTERVAL [0..1]

 

-

 

(no mapping available)

LOST INFORMATION

 

mode

DV_CODED_TEXT [1]

 

mode

CS [0..1]

rule: DV_CODED_TEXT->CS

 

( EVENT_CONTEXT)

health_care_facility

PARTY_IDENTIFIED [0..1]

 

healthcare_facility

II [0..1]

use rule for: PARTY_PROXY.external_ref

healthcare facility is in openEHR.EVENT_CONTEXT (since there cannot be 2 HCFs in one ENTRY)

( EVENT_CONTEXT)

setting

DV_CODED_TEXT [1]

 

service_setting

CV [0..1]

rule: DV_CODED_TEXT->CV

service setting is in openEHR.EVENT_CONTEXT (since there cannot be 2 types of service setting in one ENTRY)

Section & Entry structures

openEHR
class

attribute

type

13606
class

attribute

type

description

exceptions / ambiguities

SECTION

 

 

SECTION

 

 

 

 

 

 

 

 

 

 

 

 

ENTRY

 

 

ENTRY

 

 

 

 

 

language

CODE_PHRASE [1]

 

(items)

ELEMENT

generic mapping rule:
map to an ELEMENT object with name attribute set to indicate which source model attribute and value set to a CS; then follow CODE_PHRASE -> CS rule

Can ELEMENT.name be used in this way?

 

encoding

CODE_PHRASE [1]

 

(items)

ELEMENT

generic mapping rule:
map to an ELEMENT object with name attribute set to indicate which source model attribute and value set to a CS; then follow CODE_PHRASE -> CS rule

Can ELEMENT.name be used in this way?

 

subject

PARTY_PROXY [1]

 

subject_of_information

RELATED_PARTY

rule: PARTY_PROXY->RELATED_PARTY

 

 

 

 

 

subject_of_information_category

CS [0..1]

proposed rule:
where subject in openEHR data is a PARTY_RELATED, the relationship can be mapped to this attribute

 

 

provider

PARTY_PROXY [0..1]

 

info_provider

FUNCTIONAL_ROLE

map EVENT_CONTEXT.
health_care_facility -> healthcare_facility,
setting -> setting
PARTY_PROXY.external_ref -> performer,
set function = fixed value 'provider'
mode - not recorded in openEHR

MISSING IN OPENEHR - ENTRY.mode

 

-

 

 

uncertainty_expressed

Boolean [1]

rule:
synthesise to False

Hard to see how this attribute could be a) on all Entries, and b) be a Boolean

CARE_ENTRY

 

 

ENTRY

 

 

 

 

 

protocol

ITEM_STRUCTURE

 

(items)

CLUSTER/ELEMENT

use algorithm 1 below.

 

 

guideline_id

OBJECT_REF

 

-

 

 

INFORMATION LOST (not likely to be present in source in most cases)

ADMIN_ENTRY

 

 

ENTRY

 

 

 

 

 

data

ITEM_STRUCTURE

 

(items)

CLUSTER/ELEMENT

use algorithm 1 below.

 

OBSERVATION

 

 

ENTRY

 

 

 

 

 

data

 

 

(items)

CLUSTER/ELEMENT

use algorithm 1 below.

 

 

state

 

 

(items)

CLUSTER/ELEMENT

use algorithm 1 below.

 

EVALUATION

 

 

ENTRY

 

 

 

 

 

data

ITEM_STRUCTURE

 

(items)

CLUSTER/ELEMENT

use algorithm 1 below.

 

INSTRUCTION

 

 

ENTRY

 

 

 

 

 

narrative

DV_TEXT

 

(items)

ELEMENT

use algorithm 1 below.

 

 

expiry_time

DV_DATE_TIME

 

(items)

ELEMENT

use algorithm 1 below.

 

 

wf_definition

DV_PARSABLE

 

(items)

ELEMENT

use algorithm 1 below.

 

 

activities

List<ACTIVITY>

 

(items)

CLUSTER/ELEMENT

use algorithm 1 below.

 

ACTIVITY

 

 

CLUSTER

 

 

 

 

 

description

ITEM_STRUCTURE

 

(parts)

 

use algorithm 1 below.

 

 

timing

DV_PARSABLE

 

(parts)

ELEMENT

use algorithm 1 below.

 

ACTION

 

 

ENTRY

 

 

 

 

 

time

DV_DATE_TIME

 

(items)

ELEMENT

use algorithm 1 below.

 

 

description

ITEM_STRUCTURE

 

(items)

CLUSTER/ELEMENT

use algorithm 1 below.

 

 

ism_transition

ISM_TRANSITION

 

(items)

CLUSTER

use algorithm 1 below.

 

 

instruction_details

INSTRUCTION_DETAILS

 

(items)

CLUSTER

use algorithm 1 below.

 

ISM_TRANSITION

 

 

CLUSTER

 

 

 

 

 

current_state

DV_CODED_TEXT

 

(parts)

ELEMENT

use algorithm 1 below.

 

 

transition

DV_CODED_TEXT

 

(parts)

ELEMENT

use algorithm 1 below.

 

 

careflow_step

DV_CODED_TEXT

 

(parts)

ELEMENT

use algorithm 1 below.

 

INSTRUCTION_DETAILS

 

 

CLUSTER

 

 

 

 

 

instruction_id

LOCATABLE_REF

 

(parts)

ELEMENT

use algorithm 1 below.

 

 

activity_id

String

 

(parts)

ELEMENT

use algorithm 1 below.

 

 

wf_details

ITEM_STRUCTURE

 

(parts)

CLUSTER/ELEMENT

use algorithm 1 below.

 

 

 

 

 

 

 

 

 

Sub-ENTRY structures

openEHR
class

attribute

type

13606
class

attribute

type

description

exceptions / ambiguities

HISTORY

 

 

CLUSTER

 

 

 

 

 events  (parts)   

EVENT

 

 

CLUSTER

 

 

 

 

 data  (parts)   

 

state

 

 

(parts)

 

 

 

POINT_EVENT

 

 

CLUSTER

 

 

 

 

 

 

 

 

 

 

 

 

INTERVAL_EVENT

 

 

CLUSTER

 

 

 

 

 

 

 

 

 

 

 

 

ITEM_STRUCTURE

 

 

CLUSTER

 

 

 

 

 

 

 

 

 

 

 

 

ITEM_TREE

 

 

CLUSTER

 

 

 

 

 

items

 

 

(parts)

 

 

 

ITEM_TABLE

 

 

CLUSTER

 

 

 

 

 

rows

 

 

(parts)

 

 

 

ITEM_LIST

 

 

CLUSTER

 

 

 

 

 

items

 

 

(parts)

 

 

 

ITEM_SINGLE

 

 

CLUSTER

 

 

 

 

 

item

 

 

(parts)

 

 

 

CLUSTER

items

List<ITEM

CLUSTER

 

 

 

 

 

 

 

 

 

 

 

 

ELEMENT

value

DATA_VALUE [0..1]

ELEMENT

 

 

 

 

 

null_flavour

DV_CODED_TEXT [0..1]

 

 

 

 

 

ENTRY Conversion Algorithm (algorithm #1)

To convert between any openEHR concrete ENTRY type, such as OBSERVATION, a generic approach is required. The principle problem is that to convert an instance of any openEHR ENTRY class like OBSERVATION, EVALUATION, etc, we only have ISO13606 ENTRY as a possible target. The same is true for instances of HISTORY, POINT_EVENT, ITEM_TREE etc - they only possible target is CLUSTER. In ISO13606, every RM class has a 'meaning' attribute to be used in this kind of transformations. The meaning codes are

CodeOriginal Type
OE-01Observation
OE-02Protocol
OE-03Guideline_id
OE-04Data
OE-05Period
OE-06Duration
OE-07Point_event
OE-08Event_data
OE-09Event_state
OE-10Interval_event
OE-11Width
OE-12Sample_count
OE-13Math_function
OE-14State
OE-15Instruction_narrative
OE-16Instruction_expiry_time
OE-17Instruction_wf_definition
OE-18Activity
OE-19Activity_timing
OE-20Activity_description
OE-21Action_description
OE-22Current_state
OE-23Transition
OE-24Careflow_step
OE-25Instruction_details
OE-26Instruction_id
OE-27Activity_id
OE-28Workflow_details
OE-30Evaluation
OE-31Instruction
OE-32Action
OE-33Activity_action_archetype_id

 

Not all openEHR classes are defined as codes, but most of them are. Most notable missing ones: ADMIN_ENTRY, HISTORY, EVENT_CONTEXT.

 

openEHR

ISO13606

COMPOSITION
  +-content
      +-SECTION
          +-items
              +-OBSERVATION
                  +-data
                      +-HISTORY<ITEM_TREE>
                          +-origin
                          |   +-DATE_TIME
                          +-events
                              +-POINT_EVENT<ITEM_TREE>
                                  +-data
                                      +-ITEM_TREE
COMPOSITION
  +-content
      +-SECTION
          +-members
              +-ENTRY (meaning = 'OE-01') -- OBSERVATION
                  +-items
                      +-CLUSTER -- HISTORY
                          +-obs_time
                          |   +IVL<TS>
                          +-items
                              +-CLUSTER {meaning = 'OE-07') -- POINT_EVENT
                                  +-items
                                      +-CLUSTER 

ISO 21090 - Data Types

The 21090 data types are largely derived from HL7v3 data types, and as such contain things not needed by EHR systems. Currently there is no profile for 13606's use of 21090; if it existed it would state which things would not be used in 13606, and for others, how they should be used. Once a profile is developed, it should be used to build a new, simpler XML schema for 13606.

The following table is a list of notes relating to some of the attributes from abstract classes including ANY that need to be dealt with somehow in 13606/openEHR - the QTY data type has been used as the example here. These come either from the standard or from Grahame Grieve, its principal author. These could be used to develop a 13606 profile.

21090 class

attribute

comments

HXIT

 

21090 spec: Because of the way that the types are defined, a number of attributes of the data types have values with a type derived from HXIT. In these cases the HXIT attributes are constrained to null. The only case where the HXIT attributes are allowed within a data type is on items in a collection (DSET, LIST, BAG, HIST).

 

validTimeLow,
validTimeHigh

GG: Intended for when a receiver system assembles a structure, but one of the pieces of data comes from somewhere else and is subject to separate life-cycle management - a piece of foreign data. So your own version management/life cycle stuff doesn't apply, but it's state is of sufficient interest to know this. (it's somewhat unusual, therefore, because most data is either handled in system, or its state is not tracked at all) So yes, the normal cycle is not respected (in the local context), but the data is of sufficient interest to track that state from where is is respected (elsewhere) a little.
RECOMMENDATION: not directly needed in 13606 profile, but if encountered, may be mapped to some higher level EHR structure attributes?

 

controlActRoot,
controlActExtension

The idea is that GUIDs would be generated for specific events - like measuring a person's BP. Or the BP being a certain value at a certain time - by some systems, and then used to refer to those events later on. This is a referent-tracking idea See Ceusters et al.

ANY

 

 

 

nullFlavor

Mostly maps to ELEMENT.nullflavour. Exceptions:

  • on translations of ED, CD, and PQ. But only on CD does it matter. You just swallow that equivalent into the terminology service, so you don't need to map it, only when you convert from DV_CODED_TEXT or whatever, you need to consult the terminology service to decide whether to put a nullFlavor on the translations.
    Use case: if a single coded value is given in multiple different coding systems, some coding system translations may have different coding outcomes, and therefore in CD they get their own nullFlavor.
  • Name and address parts; should be mappable to openEHR ELEMENT.null_flavour based on archetypes; in 13606???
  • on the bounds of intervals - straight forward mapping to INTERVAL.upper_bounded etc

 

updateMode

RECOMMENDATION: eleminate from 13606 profile

 

flavorId

RECOMMENDATION: should not be in model; eleminate from 13606 profile

QTY

 

 

 

expression

Was designed for representing a prescription dose dependent on external factors (e.g. patient peak flow rate, for an asthma drug). Should not really be on QTY.
RECOMMENDATION: remove in all circumstances except prescriptions. HOW TO DETECT THIS???

 

uncertainty, uncertaintyType

Appears also to relate only to specific uses of certain kinds of QTY. Could be mappable to openEHR precision and accuracy in some cases. In openEHR, 'uncertainty' is a concept associated with assessments, diagnoses etc.

 

originalText

TB: this is a contextual idea that assumes a data entry application situation. The problem is that all kinds of ways of entering data are possible: it could be chosen from a dropdown or tree widget, or be a dial widget, calendar picker, or any one of a myriad of modern GUI entry mechanisms. So I don't see how this field can be meaningfully populated in many source systems anyway; I also don't see what to do with the value of the field if it doesn't match teh stringified version of the data item, e.g. what if this field value is '11/10/2009' and the actual value string is '2009-10-11' - then it is purely duplicate information and of no use; what if the value string is '2009-11-10'? We assume then a US-style interface, but otherwise it is still a duplicate.
RECOMMENDATION: probably remove from 13606 profile.

The following table is a map of data types.

openEHR Class

attribute

type

21090 Class

attribute

type

description

exceptions

DV_BOOLEAN

value

Boolean [1]

BL or BL.NONNULL

 

 

 

 

DV_STATE

value

DV_CODED_TEXT [1]

 

 

 

 

 

 

is_terminal

Boolean [1]

 

 

 

 

 

DV_IDENTIFIER

issuer

String [1]

 

 

 

 

 

 

id

String [1]

 

 

 

 

 

 

type

String [1]

 

 

 

 

 

 

assigner

String [1]

 

 

 

 

 

 

 

 

 

 

 

 

 

DV_TEXT

value

String [1]

 

 

 

 

 

 

hyperlink

DV_URI [0..1]

 

 

 

 

 

 

mappings

List<TERM_MAPPING>

 

 

 

 

 

 

encoding

CODE_PHRASE [0..1]

 

 

 

 

 

 

language

CODE_PHRASE [0..1]

 

 

 

 

 

TERM_MAPPING

match

Character [1]

 

 

 

 

 

 

purpose

DV_CODED_TEXT [0..1]

 

 

 

 

 

 

target

CODE_PHRASE [1]

 

 

 

 

 

CODE_PHRASE

terminology_id

TERMINOLOGY_ID [1]

 

 

 

 

 

 

code_string

String [1]

 

 

 

 

 

DV_CODED_TEXT

defining_code

CODE_PHRASE [1]

 

 

 

 

 

DV_PARAGRAPH

items

List<DV_TEXT> [1..*]

 

 

 

 

 

 

 

 

 

 

 

 

 

DV_ORDERED

 

 

 

 

 

 

 

 

normal_status

CODE_PHRASE [0..1]

 

 

 

 

 

 

normal_range

DV_INTERVAL<T> [0..1]

 

 

 

 

 

 

other_reference_ranges

List<REFERENCE_RANGE<T>> [0..1]

 

 

 

 

 

DV_INTERVAL<T>

 

 

 

 

 

 

 

 

lower

T->DV_ORDERED [0..1]

 

 

 

 

 

 

upper

T->DV_ORDERED [0..1]

 

 

 

 

 

 

lower_included

Boolean

 

 

 

 

 

 

upper_included

Boolean

 

 

 

 

 

 

lower_unbounded

Boolean

 

 

 

 

 

 

upper_unbounded

Boolean

 

 

 

 

 

REFERENCE_RANGE<T>

meaning

DV_TEXT [1]

 

 

 

 

 

 

range

DV_INTERVAL <T> [1]

 

 

 

 

 

 DV_QUANTIFIED

magnitude_status

String [0..1]

 

 

 

 

 

DV_ORDINAL

value

Integer [1]

 

 

 

 

 

 

symbol

DV_CODED_TEXT [1]

 

 

 

 

 

 DV_AMOUNT

 

 

 

 

 

 

 

 

accuracy

Real [0..1]

 

 

 

 

 

 

accuracy_is_percent

Boolean [0..1]

 

 

 

 

 

DV_COUNT

 

 

INT?

 

 

 

 

 

magnitude

Integer [1]

 

 

 

 

 

DV_QUANTITY

 

 

REAL?

 

 

 

 

 

magnitude

Double [1]

 

 

 

 

 

 

precision

Integer [0..1]

 

 

 

 

 

 

units

String [1]

 

 

 

 

 

DV_PROPORTION

 

 

RATIO?

 

 

 

 

 

numerator

Real [1]

 

 

 

 

 

 

denominator

Real [1]

 

 

 

 

 

 

type

Integer [1]

 

 

 

 

 

 

precision

Integer [0..1]

 

 

 

openEHR values:
0 = ratio
1 = unitary
2 = percent
3 = fraction

 

DV_DURATION

value

String [1]

 

 

 

ISO 8601

 

DV_ABSOLUTE_QUANTITY

accuracy

DV_AMOUNT [0..1]

 

 

 

 

 

DV_DATE

value

String [1]

TS.DATE

 

 

ISO 8601

 

DV_TIME

value

String [1]

TS

 

 

ISO 8601

 

DV_DATE_TIME

value

String [1]

TS.DATE_TIME

 

 

ISO 8601

 

 

 

 

 

 

 

 

 

DV_TIME_SPECIFICATION

 

 

 

 

 

 

 

 

value

DV_PARSABLE [1]

 

 

 

 

 

DV_PERIODIC_
TIME_SPECIFICATION

 

 

EIVL or PIVL

 

 

HL7 PIVL or EIVL syntax string

 

DV_GENERAL_
TIME_SPECIFICATION

 

 

 

 

 

HL7 GTS syntax string

 

 

 

 

 

 

 

 

 

DV_ENCAPSULATED

 

 

 

 

 

 

 

 

charset

CODE_PHRASE [0..1]

ED or subtype
ED.IMAGE,
ED.DOC,
ED.TEXT,
...

charset

CODE [0..1]

codes: openEHR character sets

 

 

language

CODE_PHRASE [0..1]

 

language

CODE [0..1]

codes: openEHR languages

 

DV_MULTIMEDIA

 

 

 

 

 

 

 

 

alternate_text

String

 

 

 

 

 

 

uri

DV_URI [0..1]

 

reference

TEL.URL [0..1]

 

 

 

data

Array <Octet> [0..1]

 

data

Binary [0..1]

 

 

 

thumbnail

DV_MULTIMEDIA [0..1]

 

thumbnail

ED [0..1]

 

 

 

media_type

CODE_PHRASE [1]

 

mediaType

CODE [0..1]

codes: openEHR media types

 

 

compression_algorithm

CODE_PHRASE [0..1]

 

compression

Compression [0..1]

codes: openEHR compression algorithms

 

 

integrity_check

Array <Octet> [0..1]

 

integrityCheck

Binary [0..1]

 

 

 

integrity_check_algorithm

CODE_PHRASE [0..1]

 

integrityCheckAlgorithm

integrityCheckAlgorithm  [0..1]

codes: openEHR integrity check algorithms

 

 

size

Integer [1]

 

 

 

 

 

DV_PARSABLE

 

 

 

 

 

 

 

 

value

String [1]

 

xml

XML

 

 

 

formalism

String [1]

 

 

 

 

 

DV_URI

value

String [1]

 

 

 

legal W3C URI

 

DV_EHR_URI

 

 

 

 

 

openEHR constrained version

 

 

 

 

 

 

 

 

 

Mismatches

Model mismatches

Some ISO 13606 data attributes do not currently exist in openEHR, and might be candidates for addition to the reference model. We should make two key points clear here. Firstly openEHR is designed as a high-quality health record architecture, rather than a one-size-fits-all interchange standard. Thus, design decisions in 13606 which are typically taken to accommodate data structures from the largest number of possible source systems do not necessarily make sense in openEHR, which is designed as a coherent EHR, and could be considered one possible 'source' system. Of course, its structures are also extremely useful for intersystem interchange. Accordingly, the relevant question to ask here is: can 13606 accommodate what is in openEHR, rather than the other way around. (ISO 13606 has sometimes been used as a design basis for some EHR systems, rather than for its intended purpose as an interchange format; in such circumstances, due to the above reasons, problems may be encountered in such projects).

Secondly, ISO13606 is an extract, which means its information instances are constructed by processing existing data (which might be relational, objects, XML, etc) and generating the output. Thus the normalisation (i.e. 'factoring') and structure of data items in the 13606 Extract makes sense (hopefully) for sharing data in a context-free manner (i.e. the receiver of the extract can use it as-is, without needing to refer to the source system), but may not be good design for the source system, and in fact may be quite different from the latter. We can thus think of some 13606 attributes as being 'refactored' attributes - they model data that is likely to be located elsewhere in the source system.

The following is a list of information attributes from ISO 13606 not currently supported in openEHR. Recommendations are made as to what to do about these attributes.

ISO 13606 RECORD_COMPONENT.policy_ids

This attribute is defined as follows in the ISO 13606-1 standard:

This attribute identifies one or more access control policies that specifically pertain to this RECORD_COMPONENT and which need to be communicated to the EHR Recipient to govern future access to it. The identifiers may refer to policy information included in this EHR_EXTRACT as defined in Part 4 of this standard, or to policies held in external policy servers to which the EHR Recipient has access.

From part 4:

In the 13606 Part 1 Reference Model every RECORD_COMPONENT within the EHR_EXTRACT includes an optional Policy_ID attribute to permit references to such policies to be made at any level of granularity within the EHR containment hierarchy. Every RECORD_COMPONENT may therefore reference any number of access policies or consent declarations that define the intended necessary privileges and profiles of principals (users, agents, software, devices, delegated actors etc) for future access to it.
It must be remembered that some policies may apply to particular RECORD_COMPONENTs within an EHR, whilst others may apply to the EHR as a whole.

This attribute is a good example of a refactored attribute. The intention in ISO 13606 is to mark each data node with the list of policies that apply to it. However, in an EHR system, the same information  model is very unlikely to be used, for at least one very basic reason: if the policies relating to a given data item or document were to change, changes would be required to the document itself. Instead, source systems are much more likely to have a policy server that references data items using whatever internal identification system is available.

Recommendation

This is the case for openEHR systems. The 13606 policy_ids attribute would therefore by populated by extracting the list of policy identifiers (where this makes sense) from the openEHR source system EHR ACCESS_CONTROL object and/or policy service. For conversion in the 13606 -> openEHR direction, the policy_ids found in the 13606 data would have to be matched to policies either in a service in the receiving system, or in a shared policy service. This would rely at least on the presence of a widely standardised policy identification scheme.

ISO 13606 RECORD_COMPONENT.sensitivity

This attribute is defined as follows in ISO 13606-1

The sensitivity of this RECORD_COMPONENT, represented using the code set for this attribute defined in Part 4 of this standard.

Part 4 contains the following:

In addition to the generic representation of EHR access policy information (Annex A), this standard therefore also defines a specification for a minimum basis for communicating the sensitivity of EHR data within an EHR_EXTRACT, by specifying the sensitivity of the RECORD_COMPONENTs within it according to the classification defined in clause 6.1 of this part standard. This classification corresponds to the various sub-domains of EHR data illustrated in Figure 3.
In practice any given EHR system might have other mechanisms for indicating the sensitivity of EHR data or some equivalent concept. This standard does not require EHR systems to store data according to the sensitivity levels defined in clause 6.1, but to be able to map to this classification on generating an EHR_EXTRACT.

This data item, and access policies in general have been discussed by the openEHR ARB in 2006. At the time it was thought that there might not be a single 'sensitivity' for a given data item, such as a document added to the EHR by an obstetrician indicating a woman's pregnancy. The patient in question may be happy for the GP to see this information, but not want it seen at all by her employer (which might be possible for large employers with their own health plans).

Recommendation

xxx

ISO 13606 ENTRY.mode

This attribute does exist in openEHR where the PARTICIPATION class is used. However, in the ENTRY class, the attributes subject and provider are 'hard-modelled', and do not use the generic PARTICIPATION value, since the function and performer are implicit. This does however mean that the mode attribute is also not available for the two principal participants.

Recommendation

This attribute is a candidate for addition to openEHR.

Data mismatches

This category of differences is where the models do map more or less directly, but are used in different ways, resulting in data instances that may not be populated in the same way.

ISO 13606 RECORD_COMPONENT.rc_id, orig_parent_ref

This attribute is probably the biggest challenge of the ISO 13606 model. ISO 13606-1 says the following.

It is important that each RECORD_COMPONENT be uniquely and consistently identified across multiple EHR_EXTRACTS, so that references to or between them remain valid. Examples of such references are semantic links, revision and attestation. The rc_id attribute is of data type Instance Identifier (II), which incorporates an ISO OID; II is currently considered internationally to be the most appropriate data type for persistent identifiers that are required to be globally unique. It is unlikely that contemporary EHR systems will have existing primary keys or internal identifiers that correspond directly to globally-unique II instances. However, an EHR Provider system that has been issued with an organisational OID might use its internal references to construct unique local extensions to that OID and thereby construct globally-unique rc_id values.
Alternatively, it might create completely new rc_ids and retain a record of the mapping of these to each internal identifier, so that any future EHR_EXTRACTS it generates will use consistent rc_id values. It is also unlikely that an EHR Recipient system will be able to use received rc_id values as its internal primary keys for the data, since every database uses a slightly different approach to generating and using such keys. The EHR Recipient might therefore also need to keep a record of the mapping of imported rc_id values to its primary keys, so that future references to those RECORD_COMPONENTS can be appropriately matched, and it can create EHR_EXTRACTs that reapply those rc_id values to the exported data. An alternative approach is for EHR systems to explicitly store the rc_id values along with the clinical data, and treat this as part of the "payload" data and not attempt to use these also as primary keys. It should also be noted that the rc_id does not function as a primary key equivalent within an EHR_EXTRACT i.e. duplicate values of rc_id are permitted if each instance does indeed refer to the same piece of clinical data within the EHR Provider system. [emphasis added]

The key requirement here is:

  • Extract nodes (i.e. RECORD_COMPONENT instances) must be uniquely and consistently identified across multiple EHR_EXTRACTs (rather than just within a given extract).

Two strategies for populating rc_id are proposed:

  • use an organisation OID + locally constructed internal identifiers for the nodes in the Extract
  • create rc_id values (probably GUIDs) on the fly and make both source and target systems keep a record of them.

The second approach implies a serious impost in data management overhead, since it requires an entirely new GUID-based indexing capability to be added to all systems sharing data using 13606, with concomitant costs, even though they have no use for such a capability within the system, or for other sharing methods, such as HL7v2. As a result, the only approach that can realistically be used in EHR systems, including those based on openEHR, is the first. It is assumed for both the rc_id and the orig_parent_ref attributes.

Recommendation

To implement the first approach above in openEHR, ids of the form used in openEHR URIs are used, i.e. COMPOSITION.uid + node path, since COMPOSITION.uid is globally unique (other approaches could be used involving a system identifier as well). COMPOSITION.uid is of type OBJECT_VERSION_ID, described as follows in the specification:

The string form of an OBJECT_VERSION_ID stored in its value attribute consists of three segments separated by double colons ("::"), i.e. (EBNF):
    value: object_id '::' creating_system_id '::' version_tree_id
    object_id: UID
    creating_system_id: UID
    version_tree_id: VERSION_TREE_ID

An example is as follows:

F7C5C7B7-75DB-4b39-9A1E-C0BA9BFDBDEC::87284370-2D4B-4e3d-A3F3-F303D2F4F34B::2

Note that the uid (first and second segments can also be of type ISO Oid, or a reverse internet domain name. This 3-part id globally identifies a versioned openEHR Composition in a distributed network where multiple institutions can create their own local updates from an initial common copy e.g. of medications list. To get to an interior node, a path will be required, of the typical form used in openEHR, from the root node down to the node in question. An example of such a path is:

/content[openEHR-EHR-SECTION.vital_signs.v1 and name/value='Vital signs']/items[openEHR-EHR-OBSERVATION.heart_rate-pulse.v1 and name/value='Pulse']/data/
events[at0003 and name/value='Any event']/data/items[at1005]

So the identifier to each node in a structure could be something like:

F7C5C7B7-75DB-4b39-9A1E-C0BA9BFDBDEC::87284370-2D4B-4e3d-A3F3-F303D2F4F34B::2/content[openEHR-EHR-SECTION.vital_signs.v1 and name/value='Vital signs']/
items[openEHR-EHR-OBSERVATION.heart_rate-pulse.v1 and name/value='Pulse']/data/events[at0003 and name/value='Any event']/data/items[at1005]

(Note that 'Pulse' and 'Vital signs' could also be represented by Snomed or other codes).