Customizing CDA XSL Transformations Contents Custom XSL in Containers Custom Transforms Using SDA Extensions Debugging You may occasionally need to augment the standard library of CDA XSL transformations. For example, you may need to change part of the logic when transforming a particular CDA section, or you may wish to add support for custom SDA extensions, custom pairs, or custom objects. For more information on custom SDA extensions, pairs, and objects, see the Customizing the SDA section of SDA: InterSystems Clinical Data Format. Instead of editing the standard library of XSLs directly, you can create custom XSLs. This is preferable to direct editing for two reasons. First, overriding a standard root XSL in this manner negates the need to change existing application calls to that transformation. Second, it provides insulation against the effects of upgrades, which replace the standard XSL library and thereby erase your customizations. XSLs in a custom directory are not replaced upon upgrade. Preparing to Customize Transformations: Docker Containers Important: If you plan to customize transformations and InterSystems IRIS for Health is running in a Docker container, the container must point to a durable directory. For more information on durable directories, see Running InterSystems Products in Containers. If your instance is running within a container, you must take the following preparation steps before you start to customize the transformations: In the Management Portal, create a /csp/xslt web application: Log in to the Management Portal as a user with the %HS_Administrator role. Navigate to System Administration > Security > Applications > Web Applications. Click Create New Web Application. In the form, complete the fields as follows: Name — /csp/xslt Namespace — HSLIB Enabled — Enable Application and CSP/ZEN should be selected For CSP File Settings: Serve Files — accept the default Server files timeout — accept the default Physical Path — a directory within your durable directory, such as /container/durable/csp/xslt/. Make sure to include the final trailing slash. Web Settings — accept the defaults Click Save. Open a Terminal session and log in as a user with the %HS_Administrator role. To copy the XSLT files for customization to the physical path specified in the step above: within the HSLIB namespace, run do ##class(HS.HC.Util.Installer.Upgrade.XSLTDirectoryCopy).Update() To see verbose output, you can supply 1 as the single parameter for the Update() method. Creating Custom Transformations To create a custom CDA transformation: Create a Custom subdirectory in the directory where the transformation is located. For example, if you are customizing install-dir/CSP/xslt/SDA3/CDA-to-SDA.xsl, the custom subdirectory should be install-dir/CSP/xslt/SDA3/Custom. Files in a custom folder are not overwritten upon upgrade. In the IDE of your choice, open the transformation you intend to customize so you can copy portions of it. Create an empty custom XSL with the same name as the XSL you intend to customize. For example, if you want to customize CDA-to-SDA.xsl, create an XSL in install-dir/CSP/xslt/SDA3/Custom called CDA-to-SDA.xsl. Add the following initial statements to your custom XSL. The first two (the XML declaration and the XSL stylesheet) can be copied from the original CDA XSL file. <?xml version="1.0" encoding="UTF-8"?> <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:isc="http://extension-functions.intersystems.com" xmlns:hl7="urn:hl7-org:v3" xmlns:sdtc="urn:hl7-org:sdtc" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:exsl="http://exslt.org/common" exclude-result-prefixes="isc hl7 sdtc xsi exsl"> Add a closing tag for the stylesheet. Your customizations will all be placed between the opening and closing xsl:stylesheet tags.</xsl:stylesheet> Add an import statement for the transformation you intend to customize:<xsl:import href="../<filename>"/>where <filename> is the name of the transformation you intend to customize, for example, CDA-to-SDA.xsl. This imports the file you intend to customize so that you can override one or more of its templates. Copy the template you wish to override from the original transformation and paste it into the new file. Customize the template logic as necessary. This overrides the template in the original XSL. As a best practice, add a comment to indicate where the template comes from. For example, if the template originated in install-dir/CSP/xslt/SDA3/CDA-Support-Files/Import/Entry-Modules/Medications.xsl, make a note of it. Save your work. If your installation is deployed in a mirror, repeat the process on all mirror members. Restart your productions to activate your custom XSLs. Extending Transformations SDA can be extended in several ways, as described in the “Customizing the SDA” chapter of SDA: InterSystems Clinical Data Format. These extensions can be incorporated into custom CDA transformations: Custom containers or objects can capture CDA sections that are unsupported Extension classes can add data that belongs in a supported section but is not captured by the SDA Blank templates are included in CDA import and export XSLs to facilitate: Importing a CDA section that is unsupported into a custom container or <CustomObject> Importing CDA data into SDA extension classes or <CustomPairs> in existing SDA sections Exporting a custom container or <CustomObject> into a CDA section that is unsupported Blank templates always contain the word Custom for easy identification.The following gives details on how each of the above customizations are implemented: To import a CDA section that is unsupported into a custom container or <CustomObject>, find the custom template in the XSL you wish to edit. For example, in CDA-to-SDA.xsl, the template is called <xsl:template match="*" mode="ImportCustom-Container">. Copy that template into your custom CDA-to-SDA.xsl file (or the custom version of whichever file you are customizing) and edit the blank custom template to include whatever logic you require. To import CDA data into SDA extension classes or <CustomPairs> in existing SDA sections, find the custom template in the import XSL of the desired section. For example, to import the BodySite element into Procedure, find the custom template within Entry-Modules/Procedure.xsl. In this example, the template is called <xsl:template match="*" mode="ImportCustom-Procedure">. Copy the template into your custom CDA-to-SDA.xsl file (or the custom version of whichever file you are customizing) and edit the blank custom template to include whatever logic you require. To export a custom container or <CustomObject> into a CDA section that is unsupported, find the custom template in the XSL you wish to edit. For example, in SDA-to-C32v25.xsl, the template is called xsl:template match="*" mode="ExportCustom-ClinicalDocument">. Copy that template into your custom SDA-to-C32v25.xsl file (or the custom version of whichever file you are customizing) and edit the blank custom template to include whatever logic you require. Debugging Custom Transformations Debugging custom transformations consists of a set of tools and techniques that can be applied to a variety of situations. For debugging, you can: Use code contained within <DEBUGGING> tags to capture a value during execution of the transformation Use interoperability tools to view the trace of a document within a production (HealthShare Unified Care Record only) Debugging Code <DEBUGGING> tags are a way to perform a step-by-step walkthrough of the transformation. Place the tags in the transformation at the location where you would like to capture a value. The code within the tags can capture the value of a variable, attribute, or XPath.The following are examples of debugging code for different situations. —Capturing the value of a variable— Capturing the value of a variable This example captures the value of a variable, $variable, within an XSL called FileName.xsl: <DEBUGGING-VARIABLE-file-FileName.xsl-TemplateName> $variable = <xsl:value-of select="$variable"/> </DEBUGGING-VARIABLE-file-FileName.xsl-TemplateName> —Capturing the value of an attribute— Capturing the value of an attribute This example captures an XSL path value of the root attribute located in /ClinicalDocument/id: <DEBUGGING-PATHVALUE> CDA source OID = <xsl:value-of select="/hl7:ClinicalDocument/hl7:id/@root"/> </DEBUGGING-PATHVALUE> —Capturing an XPath with Node Positions— Capturing an XPath with Node Positions Capturing an XPath takes advantage of templates. Calling the template currentXPathWithPos returns the current XPath with node positions, with ClinicalDocument/component indicating, for example, the first component element inside ClinicalDocument. The following shows how to capture the XPath of the current position with node positions. <DEBUGGING-PATHXMLWithPos> <xsl:apply-templates select="." mode="currentXPathWithPos"/> </DEBUGGING-PATHXMLWithPos> The result of this call may be: <DEBUGGING-PATHXMLWithPos>/ClinicalDocument/component/structuredBody/component /section/entry/procedure</DEBUGGING-PATHXMLWithPos> —Capturing an XPath without Node Positions— Capturing an XPath without Node Positions Calling the currentXPath template returns the XPath without the node positions. The following example shows how to capture the XPath of the current position without node positions. <DEBUGGING-PATHXMLWithoutPos> <xsl:apply-templates select="." mode="currentXPath"/> </DEBUGGING-PATHXMLWithoutPos> The result of this call may be: <DEBUGGING-PATHXMLWithoutPos>/ClinicalDocument/component/structuredBody/component /section/entry/procedure</DEBUGGING-PATHXMLWithoutPos> The templates currentXPathWithPos and currentXPath are found in install-dir/csp/xslt/SDA3/CDA-Support-Files/System/Common/Functions.xsl. —Capturing an XPath tree— Capturing an XPath tree Calling the copy template returns the current XPath tree. The following example captures the current XPath tree by inserting the current XPath tree in a DEBUGGING tag: <DEBUGGING-PATHXMLTree> <xsl:apply-templates select="." mode="copy"/> </DEBUGGING-PATHXMLTree> The template copy is found in install-dir/csp/xslt/SDA3/CDA-Support-Files/System/Common/Functions.xslThese <DEBUGGING> tags and the values they capture are displayed in the transformations, but they are not displayed in places such as the Clinical Viewer and the View Summary page.<DEBUGGING> tags may short-circuit CDA processing. Accordingly, they should be used during the debugging process only. Interoperability Tools InterSystems products provide interoperability tools that allow you to inspect the transformation process. You can inspect the process at the following points using message traces: HealthShare Unified Care Record: During document retrieval, in the consumer Edge Gateway production (when a CDA in the repository is transformed into SDA) When an incoming SDA is received by the Clinical Viewer InterSystems IRIS for Health and Health Connect: examine the message trace for the relevant business operation. For example, for inbound SDA, look at the message trace for the business operation that handles the transformation for inbound SDA processing. Additionally, you can view the transformation of an outgoing CDA using the View Summary page. Message Traces To view a message trace: Log in to the Management Portal as a user with the %EnsRole.Administrator role. Choose the appropriate namespace: In HealthShare Unified Care Record: To view the trace for document retrieval, choose the namespace for the consumer Edge Gateway. To view the trace for an incoming SDA, choose the namespace for the Access Gateway. In InterSystems IRIS for Health or Health Connect: choose the Foundation namespace whose business hosts handle the transformation. Navigate to Interoperability > Configure > Production. Open your production. Choose the appropriate component. For example, HS.IHE.XDSb.Consumer.Operations might be used for document retrieval. Click the Messages tab in the panel to the right. Click the Go To Message Viewer link. Choose the message representing the transformation. Following the example above, this message would have HS.IHE.XDSb.Consumer.Operations as its source. Click the Trace tab in the panel to the right. Click the View Full trace link. Click the Contents tab in the panel to the right. The Contents tab contains the message trace. View Summary If you are running HealthShare Unified Care Record, you can also compare CDA documents with their SDA counterparts within the Clinical Viewer. To use the Clinical Viewer: Log in to the Management Portal as a user with the %HS.Administrator role. Navigate to HealthShare > <Access_Gateway_Namespace> Patient Search. Enter search information for the patient whose CDA document you wish to view. Select the patient. From the Clinical Viewer, click the View Summary link at the top of the page to arrive at the View Summary page. Here you may view the patient summary as an SDA or as a CDA document, such as a Continuity of Care Document (CCD, HITSP C32), among other options. For more information on using the View Summary page, see the “Viewing and Modifying Patient Reports” chapter in the Unified Care Record Reporting Guide.