Workflow & Test files for SERENEDI 2024 – installation instructions at bottom of post
999’s is generally used as a file transmission acknowledgment between Healthcare EDI trading partners. It’s a baseline protocol: “I sent you this file – send me back a 999 telling me that you A) Received it and B) Can parse it.” The recipient then generates the 999 and sends it back to the sender, and the loop is closed.
SERENEDI has the ability to create simple acknowledgments and complex ones using several commands in it’s internal SCORE scripting language. Most of the time, these commands are used in custom solutions with the logic embedded into the custom scripts – but in this case, I’m going to present two standalone, demonstrator SCORE scripts that highlight and illustrate how this works. The simple path uses the default SERENEDI logic to generate a 999 file – the complex path is a more “DIY” 999 generation system that allows you to generate 999 files with custom logic. First, I’ll review how the two paths work, and then at the end I’ll give a zip file that provides a SCORE script along with deployment instructions so that you can observe for yourself in SERENEDI.
Here is the SCORE script for the “simple path” – this code is incorporated in the Blog workflow file above (instructions for installing are at the end of this post):
Simple Path
sapi-SegPoolFromFile -Filename $eventData1
sapi-SegPoolToHKey
sapi-GenerateAck
sapi-AckToSegPool
$new999 = Join-Path (Split-Path (Split-Path $eventData1 -Parent) -Parent) '03_out_999' ([System.IO.Path]::ChangeExtension((Split-Path $eventData1 -Leaf), '.999'))
sapi-SegPoolToFile -Filename $new999
What this does: This logic reads an incoming X12 EDI file (sapi-SegPoolFromFile), and attempts to parse it (sapi-SegPoolToHKey). The third line loads an internal Ack register with a new 999 file that sets the internal identifiers as a response to the incoming file and sets it to ‘A’ (Accept) or ‘R’ (Reject), depending on if the file was succcessfully parsed. If the file wasn’t parsed, it indicates where parsing failed. Finally, it transfers the Ack register to the SegPool register (overwriting the old one) and sends the file out to a new .999 file (with the rest of the filename matching the original file) to the 03_out_999 folder off of the Pipeline folder, ready for transmission to a trading partner.
This is fine for a vast majority of traffic and trading partner relationships.
Complex Path
There’s one specific situation in Healthcare EDI where the simple 999 path as described above is not the best path – unbalanced 835s. An 835 is a remittance file that shows what claims have been paid, and how much, starting with a check amount and going down all the way to claim line paid amounts. The check amount must equal the sum of all the claim payments minus any possible Provider Adjustments, and the service line payments must equal the claim payments – this is what makes an 835 balanced. If a trading partner sends an 835 where that is unbalanced, it means they are sending a fundamentally unreliable financial instrument. Even though money has already shifted by this point, the recipients’ Provider Management System may not be able to process an unbalanced 835s at all, making it worthless for claims reconciliation. In that case, it would be sound policy to reject the file even before it gets to the provider’s enterprise system by transmitting a rejection acknowledgment for this file. Here’s how to implement that policy and reject the 835 upfront.
This makes generating a 999 a complex path because SERENEDI’s parser will be able to parse the file as normal – syntactically, the file is fine. So, to generate a 999 that will reject an incoming unbalanced 835 file, we have to execute the following steps:
- Parse the file and run deep integrity validation checks
- If the checks result in any messages relating to balancing, execute the complex path.
- Otherwise, return a 999 on the simple path.
In the included .zip file, there are three synthetic 835 files that shows how this works:
good_seed_835.txt – The normal 835 synthetic file, six transactions for six checks across hundreds of claims and service lines
neg_seed_835.txt – The same file except with a ‘xxxxxxAMT’ segment on segment 40 to demonstrate a syntax rejection error
bad_seed_835.txt – The normal 835 except with a minor balancing error on one of the last service lines in the file to demonstrate the “complex” path
When run, the complex path produces the following 999 on the “bad_seed_835.txt” example, showing that the basis for rejecting the whole file is a SVC service line segment in the last transaction:
ISA*00* *00* *ZZ*SAMPL_RECVRID..*ZZ*SAMPL_SENDRID..*260722*1314*^*00501*100000000*0*P*:~
GS*FA*RECVR_ID*SENDR_ID*20260722*1314*1*X*005010X231A1~
ST*999*0001*005010X231A1~
AK1*HP*1*005010X221A1~
AK2*835*100000001~
IK5*R*5~
AK2*835*100000002~
IK5*R*5~
AK2*835*100000003~
IK5*R*5~
AK2*835*100000004~
IK5*R*5~
AK2*835*100000005~
IK5*R*5~
AK2*835*100000006~
IK3*SVC*934**8~
IK5*R*5~
AK9*R*6*6*0~
SE*17*0001~
GE*1*1~
IEA*1*100000000~
Complex Path Implementation
- Identify the segment and transaction set belonging to the earliest balancing message
- Generate a “simple path” 999 and translate it to a .NET DataTable
- Surgically alter the DataTable:
- Cull Transaction Set count (SERENEDI will automatically generate if missing)
- Mark all transaction sets as rejected with zero accepteds
- For the transaction set that contains the first errored segment, add in the IK3 mappings so that this 999 can identify the segment with balancing errors
- Translate the altered DataTable back to a 999 file and write it
999 Demonstrator Workflow
Installation:
- Unzip file to C:\serenedi\shared\pipeline. Two new folders as well as a new workflow should be created.
- Run the bootstrap query to register the new triggers:
INSERT INTO BIZ_EVENT (EVENT_DATA3, EVENT_DATA4) SELECT 'INITIALIZE','$\Pipe100_Simple_999.ps1'
To see a demonstration of the simple path, move the synthetic test files from C:\serenedi\shared\pipeline\100_SIMPLE_999\02_done_edi to C:\serenedi\shared\pipeline\100_SIMPLE_999\01_in_edi – this triggers the workflow to generate new events. After a few seconds, you should see new .999 files in 03_out_999 – two 999s that accept the file, and one that rejects due to a syntax error in the “neg_seed_835.txt” file.
To demonstrate the complex path, repeat the exercise with the files in the 101_COMPLEX_999 folder. This time, you will see two rejection 999s – one rejection for bad syntax, one rejection for an unbalanced 835.
