web stats
Mirth Community - View Single Post - Mirth Tools: User defined functions
View Single Post
  #10  
Old 04-19-2012, 04:47 AM
narupley's Avatar
narupley narupley is online now
Mirth Employee
 
Join Date: Oct 2010
Posts: 7,116
narupley is on a distinguished road
Default

Quote:
UPDATE: I've created a public GitHub repository to track these example channels, code templates, scripts, or whatever else!

https://github.com/nextgenhealthcare/connect-examples

To start with I only added the ones I wrote, because I didn't want to presume and add code from others without their explicit permission. Pull requests welcome!
Fix the node order of an HL7 v2.x E4X XML object

When you add fields/components/subcomponents out of order in a message, it isn't serialized correctly by Mirth. For example, if you have the following code:

Code:
var nte = <NTE/>;

nte['NTE.1']['NTE.1.1'] = '1';
nte['NTE.3']['NTE.3.1'] = 'comment';
nte['NTE.2']['NTE.2.1'] = 'TX';

msg.appendChild(nte);
then your NTE segment will come out looking like:

Code:
NTE|1||comment|TX
Issue 625 is scheduled to be fixed in 3.0, but in the meantime, here's another way to fix it:

fixHL7NodeOrder takes in a single HL7 v2.x node (it can be the root HL7Message, or a single segment/field/component/etc.), and returns the same node, with all children sorted in ascending order as per the HL7 dot notation. So the following node:

Code:
<NTE>
	<NTE.1>
		<NTE.1.1>1</NTE.1.1>
	</NTE.1>
	<NTE.3>
		<NTE.3.1>comment</NTE.3.1>
	</NTE.3>
	<NTE.2>
		<NTE.2.1>TX</NTE.2.1>
	</NTE.2>
</NTE>
would be changed to:

Code:
<NTE>
	<NTE.1>
		<NTE.1.1>1</NTE.1.1>
	</NTE.1>
	<NTE.2>
		<NTE.2.1>TX</NTE.2.1>
	</NTE.2>
	<NTE.3>
		<NTE.3.1>comment</NTE.3.1>
	</NTE.3>
</NTE>
Here's the code, or you can just import the attached code template. Cheers!

Code:
/*
	Author: Nick Rupley
	Date Modified: 4/18/2012

	fixHL7NodeOrder: Returns a new E4X node where the order of all siblings and descendants have been fixed as per the Mirth HL7 dot notation convention.

	Arguments
	---------
		Required
		--------
		node: The node to be fixed. 
*/

function fixHL7NodeOrder(node) {
	// Create output node
	var newNode = new XML();
	// In case the node is an XMLList of multiple siblings, loop through each sibling
	for each (sibling in node) {
		// Create new sibling node
		var newSibling = new XML('<'+sibling.name().toString()+'/>');
		// Iterate through each child node
		for each (child in sibling.children())
			// If the child has its own children, then recursively fix the node order of the child
			if (child.hasComplexContent())
				newSibling.appendChild(fixHL7NodeOrder(child));
			// If the child doesn't have its own children, then just add the child to the new sibling node
			else
				newSibling.appendChild(child);
		// After recursively fixing all of the child nodes, now we'll fix the current node
		newNode += sortHL7Node(newSibling);
	}
	// Return the fixed node
	return newNode;
}

// Helper function for fixHL7NodeOrder
function sortHL7Node(node) {
	// If the node has no children, then there's nothing to sort
	if (node.hasSimpleContent())
		return node;
	// Create new output node
	var newNode = new XML('<'+node.name().toString()+'/>');
	// Iterate through each child in the node
	for each (child in node.children()) {
		// If the child has a QName, then we can sort on it
		if (child.name()) {
			// Get the current "index" of the child. Id est, if the QName is PID.3.1, then the index is 1
			curChildIndex = parseInt(child.name().toString().substring(child.name().toString().lastIndexOf('.')+1),10);
			// Boolean placeholder
			var inserted = false;
			// Iterate through each child currently in the NEW node
			for (var i = 0; i <= newNode.children().length()-1; i++) {
				// Get the index of the child of the new node
				loopChildIndex = parseInt(newNode.child(i).name().toString().substring(newNode.child(i).name().toString().lastIndexOf('.')+1),10);
				// If the child we want to insert has a lower index then the current child of the new node, then we're going to insert the child 
				// right before the current newNode child
				if (curChildIndex < loopChildIndex) {
					// Insert the child
					newNode.insertChildBefore(newNode.children()[i],child);
					// Set our flag, indicating that an insertion was made
					inserted = true;
					// No need to continue iteration
					break;
				}
			}
			// If no insertion was made, then the index of the child we want to insert is greater than or equal to all of the
			// indices of the children that have already been inserted in newNode. So, we'll just append the child to the end.
			if (!inserted)
				newNode.appendChild(child);
		}
	}
	// Return the sorted HL7 node
	return newNode;
}
Attached Files
File Type: xml fixHL7NodeOrder.xml (3.4 KB, 208 views)

Last edited by narupley; 06-08-2018 at 10:34 AM.
Reply With Quote