Introduktion

Formål

Formålet med dette dokument er at beskrive systemarkitekturen for NXRG.

Læsevejledning

Nærværende dokument er tiltænkt udviklere og IT-arkitekter med interesse i NXRG og dens opbygning.

Definitioner og referencer


NSPNational Service Platform
NXRGNXP XDS Registry
IHEIntegrating the Healthcare Enterprise (se https://www.ihe.net/)

Overblik over NXRG

I det følgende gives et overblik over NXRG. Først beskrives NXRG i forhold til dennes samarbejdende services og interne arkitektur (modulopdeling etc.)

Efterfølgende beskrives og begrundes den underliggende datamodel.

Løsningsoverblik

I nedenstående dokument vises overblik over NXRG. Diagrammet viser både løsningens snitflader og eksterne services, som denne samarbejder med. Derudover vises den NXRGs intern lagdelte opbygning (herunder specificering af ansvarsfordelingen i de forskellige lag i applikation).

Samarbejdende services

NXRG samarbejder med følgende komponenter i NSP infrastrukturen:

NXRG er opbygget i en lagdelt arkitektur. I ovenstående diagram er pakkenavne specificeret og giver en kobling til den konkrete sourcekode, der realiserer NXRG (se i øvrigt NXRG - Guide til Udviklere).

Snitflader

De udbudte snitflader er realiseret som SOAP webservices (dk.nsp.nxrg.ws). ITI-XX snitfladerne er specificeret i IHE XDS revision 17 fra juli 2020.

Se følgende:

Til at realisere disse ITI-XX snitflader anvendes tredjeparts biblioteker fra IPF Open eHealth Integration Platform til implementations- og hjælpeklasser (herunder mapning af XML baseret model til domænemodel).

Forretningslag

Forretningsregler i relation til de udbudte ITI-XX services er implementeret udfra specifikationen af IHE XDS (dk.nsp.nxrg.service). For ITI-18 er det besluttet ikke at understøtte samtlige querytyper, der fremgår af specifikationen, men at nøjes med følende:

Kald af ITI-18 med andre querytyper vil resultere i en fejlkode fra NXRG (se NXRG - Guide til Anvendere).

Validering af forespørgler og svar

Forespørgsler og svar valideres efter reglerne beskrevet i IHE XDS specifikationen. Mere præcist udføres validering som beskrevet i følgende afsnit:

Validerings opsætning

Open eHealth frameworket, der anvendes af både OpenText og NXRG, stiller muligheden for validering af request og responses til rådighed. Det er denne validering, som i stor udstrækning anvendes som validerings mekanisme i NXRG.

Både NXRG og Open Text har det som konfiguration, om sådanne valideringer skal udføres i forbindelse med forespørgsel og svar (request/response) og for de forskellige typer kald (ITI-42, ITI-61, ITI-57 og ITI-18).

Følgende tabel viser, hvordan denne konfiguration af validering er sat op for nuværende NXRG og tidligere anvendte Open Text:


NXRG genereltOpen Text - Test 1Open Text - Test 2Open Text - Produktion

RequestResponseRequestResponseRequestResponseRequestResponse
ITI-42

Disabled
Disabled
Disabled
ITI-61

Disabled
Disabled
Disabled
ITI-57







ITI-18

Disabled
DisabledDisabledDisabled
Sammenligning af patientId'er

Ved validering af forespørgsler skal der sammenlignes patientId'er. Ifølge specifikationen skal denne sammenligning tage højde for sammensmeltning af patientId'er (This comparison shall take into consideration patient identity merges as described in ITI TF-2a: 3.8.4.2.4.). I NXRG er det antaget, at denne form for sammensmeltning ikke forekommer, og sammenligning af patientId'er er derfor implementeret ved simpel strengsammenligning.

 Validering af ITI-18 fremsøgning response

Da Open Text var registry, var der ikke request (input) validering på oprettelses kalende (ITI-42 og ITI-61). Derfor er der herfra fejlbehæftet metadata, som ikke overholder IHE standarden. Når der laves en fremsøgning (ITI-18), og bare eet af disse dokumenter er imellem, vil kaldet gå i fejl, og ingen af dokumenterne blive returneret. 

For at undgå denne situation er, er der i NXRG lavet sådan, at hvert dokuments metadata, der returneres fra fremsøgningen, valideres for sig selv. De dokumenter, som fejler i valideringen, returneres ikke i resultatsættet. Der indsættes istedet for disse en fejl linie i svaret, ligesom dokumentet logges til applikations loggen. Dokumentet identificeres her ved entryUuid.  Er der sådanne frasorteringer i fremsøgning sættes status til Partial success, og hvis alle fremsøgte dokumenter frasorteres sættes status til Failure.


Databaselag

NXRG har behov for at persistere data i en database. NXRGs datamodel er realiseret udfra følgende principper:

For en detaljeret beskrivelse af databasemodellen se afsnittet nedenfor.

XDSCleanup service

De data, der opbevares i NXRG, skal slettes efter noget tid. Hvor lang tid der er tale om, kommer an på typen af data. Til at afgøre denne klassifikation anvendes metadata-attributten typeCode (den består af to komponenter: en typeCode-kode og en typeCode-scheme) på DocumentEntry.

Foreløbigt gælder følgende regler:

Sletning varetages af den separate service XDSCleanup. Der henvises til dokumentationen for denne service for en beskrivelse af reglerne for, hvordan og hvornår sletning af dokumentmetadata finder sted.

Eksterne services

Der er i dag eksterne services, der tilgår OpenText Registry direkte (dvs udenom de i forgående afsnit skitserede NSP services).

Det drejer sig om følgende:

De fleste andre eksterne services (f.eks. PLSP, Bookplan, Laboratoriesvarportalen) udbyder data ved selv at udstille XDS Registry+XDS Repository snitflader, som Dokumentdelingsservicen så integrerer med. Ændringer i det nationale registry vil ikke berøre disse typer.

KIH Repository

KIH databasen (repository) indeholder dokumenter af typerne PHMR og QRD dvs hjemmemålinger og spørgeskemabesvarelser. KIH Repository anvender det nationale registry til at få indexeret disse dokumenter og gøre dem søgbare via Dokumentdelingsservicen.

KIH databasen kalder således ITI-42 på det nationale registry. Der er to muligheder i fremtiden:

  1. KIH kalder direkte på NXRG ITI-42: Denne løsning er tilsvarende det, der sker i dag
  2. KIH kalder DROS ITI-42: DROS ventes at komme til at indeholde valideringer, der vil øge kvaliteten af de metadata, der i sidste ende havner i det nationale registry. Ved at lade KIH anvende denne snitflade vil KIH metadata blive underlagt samme valideringer. NB ITI-42 på DROS findes både i en DGWS og en ikke-DGWS (IP whitelisting eller SDN aftale) udgave. For KIHs vedkommende vil det være relevant at kalde ikke-DGWS snitfladen for at undgå snitfladeændringer.

Inden driftsstart for NXRG skal det afklares, hvilket af de to punkter ovenfor, der ønskes.

Derudover skal der udarbejdes en plan i samarbejde med Medcom om, hvordan det skal foregå.

Afvigelser fra IHE XDS standarden

I forhold til NXRG, så er det ikke hele IHE XDS specifikationen, der implementeres. I de følgende afsnit dokumenteres evt. fravalg og beslutninger ved de enkelte services.

ITI-18: Registry Stored Query

I forhold til fremsøgning, så er det besluttet, at følgende query typer skal understøttes:

Dog forholder det sig sådan, at "FindDocumentsByReferenceId" ikke understøttes af DDS'en og dermed kan den i praksis ikke kaldes. Der anses ikke for nuværende behov for at ændre dette.


Når man laver en fremsøgning med ITI-18, kan man få to typer af objekter tilbage, baseret på den retur type man sætter i kaldet. 

En måde at fremsøge meget store datamængder på, kan derfor laves med først en fremsøgning retur type ObjektRef og efterfølgende anvende disse værdier til at lave en GetDocuments med retur typen LeafClass.

DDS'en understøtter dog ikke "ObjectRef" retur typen, og der anses ikke for nuværende behov for at ændre dette. En detalje ved returnering af objekt referencer er, at man ikke vil kunne lave spærringer på dokumenter alene på disse. Men det vil kunne ske efterfølgende når id'erne anvendes i en GetDocuments og metadata faktisk hentes frem.

ITI-57: Update Document Set

Specifikationen beskriver i afsnit "3.57.4.1.3.4 Patient ID Reconciliation", hvordan det skal håndteres, hvis patient-id opdateres som en del af et kald til ITI-57. I forhold til NXRG, så har vi valgt, at denne ikke skal understøtte dette, hvorfor et forsøg på ITI-57 kald, hvor patient id opdateres vil resultere i en fejl til anvenderen.

Patient ID Reconciliation vil resultere i øget kompleksitet i NXRG, og anvendere vil kunne opnå det samme ved f.eks. at deprecate eksisterende data på en patient, og dernæst oprette data på en anden.

Derudover vil anvendelsen af NXRGs ITI-57 service ikke foregå direkte men via DROS - Guide til anvendere. I forhold til auditlogning og diverse tjek, så er de fleste NSP anvender services tænkt til en brug, hvor der er netop én patient i kontekst ad gangen.

Vi vurderer, at skift af patient ID vil skabe øget unødvendig kompleksitet i de anvenderrettede services.

Andet væsentlige at notere for design af NXRG

ITI-57 Update metadata

Dette kald tillades ikke for OnDemand dokumenter. Det anvendte biblioteks fra Open eHealth afviser typen OnDemand i forbindelse med opdatering af metadata. Det fungerer sådan for både Open Text registry og NXRG.

ITI-61 replace document

Dette kald opfører forskelligt for Stable og OnDemand dokumenter. Ved replace af Stable dokument deprecates de gamle dokument. Dette sker ikke for onDemand dokumenter. Der er i ovenstående specifikationen ikke nævnt noget med status ændring for OnDemand  Det fungerer sådan for både Open Text registry og NXRG.

Databasemodel

Følgende overblik viser, hvorledes datamodellen i NXGR er opbygget. Datamodellen er opbygget med udgangspunkt i følgende overordnede principper:

  1. Understøtte MVP: NXRG er startet som et Minimal Viable Product med intentionen om senere at kunne skifte til et andet mere modent produkt. Dette betyder, at modellen ikke skal være mere kompliceret, end højst nødvendigt.
  2. Kunne understøtte udvidelser af NXRG: Selvom kravene (MVP) fra starten er begrænsede, så giver det mening at overveje, at det skal være muligt at udvide NXRG f.eks. med flere ITI-18 query typer. Datamodellen skal i denne sammenhæng være robust over for denne slags ændringer (dvs det skal være velforstået, hvad sådanne udvidelser betyder i forhold til databasemodellen).
  3. Understøtte migrering: Da en væsentlig del af MVP indeholder migrering af data fra OpenText Registry til NXRG, så skal databasemodellen være lavet på en måde, således at migreringen er understøttet.
  4. Driftsvenlig: Det skal være muligt for driften at foretage opgaver i forbindelse med support og drift (f.eks. oprydningsjob)

I det følgende beskriver vi datamodellen for NXRG og beskriver, hvorledes ovenstående principper er respekteret. Datamodellen præsenteres først i overbliksform i nedenstående E/R-diagram, og de enkelte tabeller beskrives derefter.

Hver entitet i diagrammet svarer til en tabel. 

De vigtigste entiteter er Association, DocumentEntry, Folder og SubmissionSet, som er NXRG's repræsentation af de tilsvarende begreber fra IHE-specifikationen. I det følgende kaldes disse fire tabeller for objekttabeller. En række i en objekttabel svarer til et tilsvarende objekt, f.eks. svarer en række i Association-tabellen til et Association-objekt, en række i DocumentEntry-tabellen til et DocumentEntry-objekt, osv. Disse tabeller indeholder de attributter som der er brug for, for at NXRG kan realisere sine snitflader. Tabellerne er dog ikke fulstændige modeller af de objekter, de repræsenterer, da det er ganske omfattende at udarbejde og vedligeholde en sådan datamodel. De fulde objekter gemmes i stedet som xml i en tilhørende *Content-tabel (i det følgende kaldet en indholdstabel).

Objekttabellerne indeholder de attributter der er nødvendige for at understøtte søgning gennem ITI18-snitfladen, samt for at tjekke forretningsregler i ITI42-, ITI57- og ITI61-snitfladerne. Indholdstabellerne indeholder selve objekterne i et xml-format, der er nemt at parse og serialisere, men besværligt at søge i.

Alle tabellerne har felterne creation_time og last_update_time, der indeholder tidspuntk for oprettelse henholdsvis ændring.

Association

FeltnavnBeskrivelseOptionalUnik nøgleDatatype
idIntern, unik nøgle.nejxint(11)
entryuuidUuid, der identificerer Association-objektet.nej
varchar(64)
association_type
nej
varchar(32)
source_associationid på source, hvis denne er en Association.

int(11)
sourceuuid_documententryEntryuuid på source, hvis denne er et DocumentEntry.

varchar(64)
sourceuuid_folderEntryuuid på source, hvis denne er en Folder.

varchar(64)
sourceuuid_submissionsetEntryuuid på source, hvis denne er et SubmissionSet.

varchar(64)
target_associationid på target, hvis denne er en Association.

int(11)
targetuuid_documententryEntryuuid på target, hvis denne er et DocumentEntry.

varchar(64)
targetuuid_folderEntryuuid på target, hvis denne er en Folder.

varchar(64)
targetuuid_submissionsetEntryuuid på target, hvis denne er et SubmissionSet.

varchar(64)
associationcontentidReference til række i associationcontent-tabellen.nejxint(11)
migration_pidLink til oprindelig migreringsdata - default 0nej
int(11)

AssociationContent

FeltnavnBeskrivelseOptionalUnik nøgleDatatype
idIntern, unik nøgle.nejxint(11)
xmlDet rå objekt i ebxml 3.0-format.

blob

Author (documententry_author)

FeltnavnBeskrivelseOptionalUnik nøgleDatatype
idIntern, unik nøgle.nejxint(11)
documententry_entryuuidReference til række i documententry-tabellen.nej
int(64)
family_nameEfternavn fra Author-strukturen.nej
varchar(64)
given_nameFornavn fra Author-strukturen.

varchar(64)
further_given_namesØvrige fornavne fra Author-strukturen.

varchar(64)

Code (documententry_eventcode og documententry_confidentialitycode)

FeltnavnBeskrivelseOptionalUnik nøgleDatatype
idIntern, unik nøgle.nejxint(11)
documententry_entryuuidReference til række i documententry-tabellen.nej
int(64)
codenameName-delen af Code-strukturen.nej
varchar(64)
schemenameScheme-delen af Code-strukturen.nej
varchar(64)

DocumentEntryContent

FeltnavnBeskrivelseOptionalUnik nøgleDatatype
idIntern, unik nøgle.nejxint(11)
xmlDet rå objekt i ebxml 3.0-format.

blob

DocumentEntries

FeltnavnBeskrivelseOptionalUnik nøgleDatatype
idIntern, unik nøgle.nejxint(11)
entryuuidEntryUuid på DocumentEntry-objektet. Unik identifikation af den versionen af objektet.nejxvarchar(64)
logicaluuid

LogicalUuid på DocumentEntry-objektet. Identificerer DocumentEntry-objektet på tværs af versioner.

For version 1 er EntryUuid og LogicalUuid identiske, for andre versioner er de forskellige.

nej
varchar(64)
versionVersionsnummer på DocumentEntry-objektet. Antager værdierne 1, 2, 3, ...nej
int(11)
patientidId-delen af PatientId-strukturen.nej
varchar(32)
patientid_assigningauthorityidAssigningAuthorityId-delen af PatientId-strukturen.nej
varchar(32)
patientid_assigningauthoritytypeAssigningAuthorityType-delen af PatientId-strukturen.nej
varchar(16)
availabilitystatusObjektets status (Approved, Deprecated, etc.)nej
varchar(64)
documententrytypeObjektets typpe (Stable eller OnDemand)nej
varchar(64)
uniqueidUniqueId på objektet (NB: ikke nødvendigvis unik for DocumentEntries).nej
varchar(128)
classcode_codenameNavn for ClassCode.nej
varchar(64)
classcode_schemenameScheme for ClassCode.nej
varchar(64)
typecode_codenameNavn for TypeCode.nej
varchar(64)
typecode_schemenameScheme for TypeCode.nej
varchar(64)
practicesettingcode_codenameNavn for PracticeSettingCode.nej
varchar(64)
practicesettingcode_schemenameScheme for PracticeSettingCode.nej
varchar(64)
creationtimeOprettelsestidspunkt som angivet af anvenderen.

datetime(6)
servicestarttimeStarttidspunkt som angivet af anvenderen.

datetime(6)
servicestoptimeSluttidspunkt som angivet af anvenderen.

datetime(6)
healthcarefacilitytypecode_codenameNavn for HealthcareFacilityTypeCode.nej
varchar(64)
healthcarefacilitytypecode_schemenameScheme for HealthcareFacilityTypeCode.nej
varchar(64)
formatcode_codenameNavn for FormatCode.nej
varchar(64)
formatcode_schemenameScheme for FormatCode.nej
varchar(64)
documententrycontentidReference til række i documententrycontent-tabellen.nejxint(11)
migration_pidLink til oprindelig migreringsdata - default 0nej
int(11)

Folder

FeltnavnBeskrivelseOptionalUnik nøgleDatatype
idIntern, unik nøgle.nejxint(11)
entryuuidEntryUuid på Folder-objektet. Unik identifikation af den versionen af objektet.nejxvarchar(64)
logicaluuid

LogicalUuid på Folder-objektet. Identificerer Folder-objektet på tværs af versioner.

For version 1 er EntryUuid og LogicalUuid identiske, for andre versioner er de forskellige.

nej
varchar(64)
versionVersionsnummer på Folder-objektet. Antager værdierne 1, 2, 3, ...nej
int(11)
patientidId-delen af PatientId-strukturen.nej
varchar(32)
patientid_assigningauthorityidAssigningAuthorityId-delen af PatientId-strukturen.nej
varchar(32)
patientid_assigningauthoritytypeAssigningAuthorityType-delen af PatientId-strukturen.nej
varchar(16)
availabilitystatusObjektets status (Approved, Deprecated, etc.)nej
varchar(64)
uniqueidUniqueId på objektet (NB: ikke nødvendigvis unik for DocumentEntries).nej
varchar(64)
lastupdatetimeSeneste opdateringstidspunkt for Folder-objektet.nej
datetime(6)
foldercontentidReference til række i foldercontent-tabellen.nejxint(11)

FolderContent

FeltnavnBeskrivelseOptionalUnik nøgleDatatype
idIntern, unik nøgle.nejxint(11)
xmlDet rå objekt i ebxml 3.0-format.

blob

ReferenceId (documententry_referenceid)

FeltnavnBeskrivelseOptionalUnik nøgleDatatype
idIntern, unik nøgle.nejxint(11)
documententry_entryuuidReference til række i documententry-tabellen.nej
int(64)
reference_idNøgle på ReferenceId'et.nej
varchar(64)
assigningauthority_idId fra AssigningAuthority-strukturen.

varchar(64)
assigningauthority_typeType fra AssigningAuthority-strukturen.

varchar(64)
typecodeTypeCode på ReferenceId'et.nej
varchar(64)
homecommunityid_id

Id fra HomeCommunityId-strukturen.



varchar(64)
homecommunityid_typeType fra HomeCommunityId-strukturen.

varchar(64)

SubmissionSet

FeltnavnBeskrivelseOptionalUnik nøgleDatatype
idIntern, unik nøgle.nejxint(11)
entryuuidUuid, der identificerer SubmissionSet-objektet.nejxvarchar(64)
patientidId-delen af PatientId-strukturen.nej
varchar(32)
patientid_assigningauthorityidAssigningAuthorityId-delen af PatientId-strukturen.nej
varchar(32)
patientid_assigningauthoritytypeAssigningAuthorityType-delen af PatientId-strukturen.nej
varchar(16)
uniqueidUniqueId på objektet.nejxvarchar(64)
migration_uniqueid_fixSikring af uniqueness på migreringstidspunktet. Se afsnit nedenfor med findings. Default 0nej
int(11)
submissionsetcontentidReference til række i submissionsetcontent-tabellen.nejxint(11)

SubmissionSetContent

FeltnavnBeskrivelseOptionalUnik nøgleDatatype
idIntern, unik nøgle.nejxint(11)
xmlDet rå objekt i ebxml 3.0-format.

blob

Deleted_Documententries

FeltnavnBeskrivelseOptionalUnik nøgleDatatype
idIntern, unik nøgle.nejxint(11)
entryuuidEntryUuid på slettet DocumentEntry.nej
varchar(64)
uniqueidUniqueId på slettet DocumentEntry.nej
varchar(64)
deletion_statusStatus på sletningen. Kan være DELETED_FROM_REGISTRY, DELETED_FROM_REPOSITORY, DELETION_FROM_REPOSITORY_FAILED.nej
varchar(64)
deletion_attemptsAntal gange hvor sletning fra repository er gået galt.nej
int(11)
creation_timeTidspunkt for indsættelse af rækken.nej
datetime(6)

Migrering af data

Den oprindelige data migrering fra openText registry er ikke længere aktuel, og indholdet er flyttet til "Yderligere dokumentation - Migration"

På tidspunktet for NXRG tilblivelse blev der udvalgt en række felter fra kaldets metadata (XMl baseret RIM format), som var interessante som søgbare felter. Disse felter, gemmes som selvstændige felter i tabeller som documententries og referenceid. Der opstår siden behov for at få flere af disse felter trukket ud af XML formatet. Dvs. der i princippet skal køres en migrering af eksisterende metadata for at trække disse felter ud. Dette er lavet som en selvstændig service. Source koden ligger sammen med resten af NXRG, men servicen starter op selvstændig og aktiveres ved at tilgå et specifik endpoint. Detaljerne er beskrevet i "NXRG driftvejledning for migrering af søgbare felteer".


So ovenstående figur viser, består felt migreringen af 3 trin:

  1. udvidelse af databasemodel. Her tilføjes de søgbare felt databsen og NXRG justeres sådan at nye dokument registreringer vil gemme feltet som et søgbart felt.
  2. migrering af data. Denne kan foregå af flere omgange da kørslen kan være tidskrævende. Servicen konfigureres med en batch størrelse, som der det antal dokumenter, der håndteres i en enkelt kørsel.
  3. anvendelse af det søgbare felt. Når alt data er migreret kan det nye felt tages i anvendelse. Dvs først her kan ny funktionatlitet der gør brug af feltet udvikles.