Wednesday, January 12, 2011

Expressions in HL7 Data Types R2 and Computable Clinical Guidelines

The HL7 Structured Documents Workgroup met with Clinical Decision Support today to discuss some of the issues with the HL7 Quality Measurement Format that would need to be addressed in the next release.  Bob (Dolin) gave a quick update on the NQF status.  Apparently the Meaningful Use measures have all been converted to HQMF, including all the value sets in all the Meaningful Use specified vocabularies (ICD-9-CM and SNOMED CT) and are in CMS hands.  We heard that there may be some sort of comment / vetting process as a later phase.

The issue that Bob wanted to address is the way to represent an expression in a computational language in a measure.  HL7 Data types release 2 includes the EXPR data type.  This data type is an extension of a data type of type T which has one new component: expression.  An example representation of this is shown below:

value xsi:type='EXPR_INT'
  ‹expression mediatype='application/javascript'
    foo.value.value - bar.value.value
  /expression
/value

Now, by itself, this isn't completely useful, but when you put it inside an Observation that you are defining, the expression can be used to define how the value is computed.  There are a couple of other things that you need.  One of these is a binding from the variables foo and bar above to specific classes.

The HL7 RIM has a way to create bindings for the derivationExpr component of the act class, but hasn't defined how to create bindings for EXPR_T.  I'd stick with using the same mechanism for derivationExpr.  What could be done is something like the following:

‹observation moodCode='DEF'›
  ‹value xsi:type='EXPR_INT'›  ‹actRelationship typeCode='DRIV'›

    ‹expression mediatype='application/javascript'›
      foo.value.value - bar.value.value
    ‹/expression›
  ‹/value›


    ‹localVariableName›foo‹localVariableName›
    ‹observation›
       ‹value value='1'›

    ‹/observation›
  ‹/actRelationship›
  ‹actRelationship typeCode='DRIV'›

    ‹localVariableName›foo‹localVariableName›
    ‹observation›
      ‹value value='2'›

    ‹/observation›
  ‹/actRelationship›
‹/observation›

What this essentially says is that the outermost definition of the observation has a value.  That value is computed from information contained in two other named classes: foo and bar.  These classes are then defined to be local variables representing the named observation classes. 

So, why is this cool?  Well, it's something only a geek could love.  What it does is provide a mechanism whereby we can bind an HL7 class represented in XML to a programming language like javascript (Bob wanted to use GELLO, but I can hand you a book today on javascript if you really need it.  And you can probably already figure out how to access the classes.

The next piece of this is that it allows certain computations to be defined based on the contents of other stuff.

What is missing from this is the binding rules that tell us how to evaluate the named portion of the expression.  I cheated by using the binding rules for derivationExpr, which are very simple.  Those rules state that the named variables are contained within in derived acts.  I could have used other binding rules, e.g., that the named variables are contained within some other set of named variables.

What I like about this is that it gives me the missing pieces needed to define a Structured Document for a Clinical Guideline.  Those two pieces are what I call level 3 and level 4 of clinical guidelines.

The structured clinical guideline in my head has four levels.  Level 1 contains a header comprised of metadata used to allow the guideline to be found in a repository of guidelines and human readable content as an attachment, e.g., PDF or XHTML.  Level 2 contains the information structured into sections where each section is addressible, coded, and has additional metadata describing it, along with human readable content in a format like XHTML.  Level 3 are the definitions of things that need to be tracked to manage the guideline (e.g., heart rate, ejection fraction ratio, blood preassure, comorbidities, et cetera).  Level 4 is a way to bind to ANY computational langauge, such as javascript (my preferred language for reasons of reduciong complexity).

So we never did get to discuss the idea of how to build this thing in clinical decision support like I had wanted to, because we could hardly get away from the discussion about how what Bob wanted was already in scope of VMR [sort of like swatting flies with a sledgehammer].  But now I know the pieces are there.  It's time to start thinking more about how to put this together.

And see, I don't even need to worry about the Gello, Arden, GLIF, ... debate because any mediaType will do as the computable language.  The standard need not state a preference.

So, it looks like there might be enough to define a quality process that has measurement built in.  One of these days, I'm just gonna have to take a class on that six-sigma thingy-ma-bob.

G'Night all.

   Keith

P.S.  They tell me that there's a foot of snow back home.  I hope you all are enjoying it.

2 comments:

  1. We only defined one standard mapping, for the "Factor" language. Is a javascript mapping really what you want? It's a procedural language, not an expression language, so it's kind of uber-capable for the task. There's a number f other more directly applicable mathematical/expression languages which would be better suited to the task than javascript. Even OCL would be better

    But you have sure established once and for all that you are a geek.

    ReplyDelete
  2. Gah, just what I needed, another YAML.
    Sure Javascript is overkill. Until I tell someone to implement it, in which case, I've actually got something that can work. It's not just about the language, but support for it, training for it, developer familiarity with it, and ability to get an implementation running with it that are what is really important.

    ReplyDelete