Skip to content

Commit

Permalink
One more step in converting opt 1.4
Browse files Browse the repository at this point in the history
  • Loading branch information
pieterbos committed Jan 4, 2021
1 parent cacd7bb commit 9f9e132
Show file tree
Hide file tree
Showing 12 changed files with 363 additions and 7 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,9 @@ public class ADL14ConversionConfiguration {
*/
private boolean applyDiff = true;

/** If true, allow empty node ids where specialisations occur. for OPT conversion */
private boolean allowEmptyNodeIdsForSpecializations = false;


public List<TerminologyUriTemplate> getTerminologyConversionTemplates() {
return terminologyConversionTemplates;
Expand Down Expand Up @@ -57,4 +60,12 @@ public boolean isApplyDiff() {
public void setApplyDiff(boolean applyDiff) {
this.applyDiff = applyDiff;
}

public boolean isAllowEmptyNodeIdsForSpecializations() {
return allowEmptyNodeIdsForSpecializations;
}

public void setAllowEmptyNodeIdsForSpecializations(boolean allowEmptyNodeIdsForSpecializations) {
this.allowEmptyNodeIdsForSpecializations = allowEmptyNodeIdsForSpecializations;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -203,7 +203,6 @@ private void convertTermBindings(Archetype archetype) {
}

private void generateMissingNodeIds(CObject cObject) {

if(!(cObject instanceof CPrimitiveObject) && cObject.getNodeId() == null) {
String path = cObject.getPath();
if(archetype.getParentArchetypeId() != null && flatParentArchetype != null) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -203,6 +203,9 @@ private void convertCTerminologyCode(CTerminologyCode cTerminologyCode) {
}

private Map<String, URI> findOrCreateTermBindings(TerminologyCode termCode) {
if(termCode.getTerminologyId() == null) {
throw new IllegalArgumentException("terminology id cannot be null!");
}
Map<String, URI> termBindings = archetype.getTerminology().getTermBindings().get(termCode.getTerminologyId());

if(termBindings == null) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -101,7 +101,11 @@ private CObject convertRoot(CARCHETYPEROOT cRoot14) {

CArchetypeRoot root = new CArchetypeRoot();
root.setArchetypeRef(overlay.getArchetypeId().getFullId());
setObjectBasics(cRoot14, root);
if(cRoot14.getNodeId() != null && !cRoot14.getNodeId().isEmpty() && !cRoot14.getNodeId().startsWith("at0000")) {
root.setNodeId(cRoot14.getNodeId());
}
root.setRmTypeName(cRoot14.getRmTypeName());
root.setOccurrences(BaseTypesConverter.convertMultiplicity(cRoot14.getOccurrences()));
return root;
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,11 @@
import com.nedap.archie.adl14.aom14.CDVOrdinal;
import com.nedap.archie.adl14.aom14.CDVOrdinalItem;
import com.nedap.archie.adl14.aom14.CDVQuantity;

import com.nedap.archie.adl14.aom14.CDVQuantityAssumedValue;
import com.nedap.archie.adl14.aom14.CDVQuantityItem;
import com.nedap.archie.adl14.treewalkers.Adl14CComplexObjectParser;
import com.nedap.archie.aom.CObject;
import com.nedap.archie.base.terminology.TerminologyCode;
import com.nedap.archie.aom.primitives.CTerminologyCode;

import java.util.LinkedHashMap;
import java.util.Map;
Expand All @@ -24,11 +23,30 @@ public static CObject convertDomainType(CDOMAINTYPE cobject14) {
} else if (cobject14 instanceof CDVSTATE) {

} else if (cobject14 instanceof CCODEPHRASE) {

return convertCodePhrase((CCODEPHRASE) cobject14);
}
return null;
}

private static CObject convertCodePhrase(CCODEPHRASE cobject14) {
CTerminologyCode cTerminologyCode = new CTerminologyCode();

if(cobject14.getTerminologyId() != null) {
cTerminologyCode.addConstraint(cobject14.getTerminologyId().getValue());
} else {
System.out.println("HELP");
}
if(cobject14.getCodeList() != null) {
for(String code:cobject14.getCodeList()) {
cTerminologyCode.addConstraint(code);
}
}
if(cobject14.getAssumedValue() != null) {
cTerminologyCode.setAssumedValue(BaseTypesConverter.convert(cobject14.getAssumedValue()));
}
return cTerminologyCode;
}

private static CObject convertCDVOrdinal(CDVORDINAL ordinal14) {
CDVOrdinal ordinal = new CDVOrdinal();
Map<String, CDVOrdinalItem> items = new LinkedHashMap<>();
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
package com.nedap.archie.opt14;

import com.nedap.archie.aom.Archetype;

public interface FlatArchetypeProvider {

Archetype getFlatArchetype(String archetypeId);
}
108 changes: 108 additions & 0 deletions opt14/src/main/java/com/nedap/archie/opt14/NodeIdFixer.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,108 @@
package com.nedap.archie.opt14;

import com.nedap.archie.aom.Archetype;
import com.nedap.archie.aom.ArchetypeModelObject;
import com.nedap.archie.aom.CAttribute;
import com.nedap.archie.aom.CObject;
import com.nedap.archie.aom.Template;
import com.nedap.archie.aom.TemplateOverlay;
import com.nedap.archie.aom.terminology.ArchetypeTerminology;
import com.nedap.archie.aom.utils.AOMUtils;
import com.nedap.archie.aom.utils.NodeIdUtil;
import com.nedap.archie.archetypevalidator.ErrorType;
import com.nedap.archie.flattener.InMemoryFullArchetypeRepository;
import org.openehr.utils.message.I18n;

public class NodeIdFixer {

private Archetype archetype;
private Archetype flatParent;

public void fixNodeIds(Archetype archetype, FlatArchetypeProvider repo) {
this.archetype = archetype;
if(archetype.getParentArchetypeId() != null) {
this.flatParent = repo.getFlatArchetype(archetype.getParentArchetypeId());
}
fixRootNodeId(archetype);
//fixNodeId(archetype.getDefinition());

if(archetype instanceof Template) {
Template template = (Template) archetype;

for(TemplateOverlay overlay:template.getTemplateOverlays()) {
this.archetype = overlay;
if(archetype.getParentArchetypeId() != null) {
this.flatParent = repo.getFlatArchetype(overlay.getParentArchetypeId());
}
fixRootNodeId(overlay);
//fixNodeId(overlay.getDefinition());
}
}
}

private void fixRootNodeId(Archetype archetype) {
int specDepth = flatParent.specializationDepth()+1;
CObject cObject = archetype.getDefinition();
if(cObject.isRootNode() && AOMUtils.getSpecializationDepthFromCode(cObject.getNodeId()) != specDepth) {
//create id1.1.1.1.1.....1 one
String newNodeId = "at0000";
for(int i = 0; i < specDepth; i++) {
newNodeId += ".1";
}
cObject.setNodeId(newNodeId);
}
}

private void fixNodeId(CObject cObject) {
if(flatParent == null) {
return;
}


if (cObject.isRootNode() || !cObject.getParent().isSecondOrderConstrained()) {
if (AOMUtils.getSpecializationDepthFromCode(cObject.getNodeId()) <= flatParent.specializationDepth()
|| new NodeIdUtil(cObject.getNodeId()).isRedefined()) {
if (!AOMUtils.isPhantomPathAtLevel(cObject.getPathSegments(), flatParent.specializationDepth())) {
String flatPath = AOMUtils.pathAtSpecializationLevel(cObject.getPathSegments(), flatParent.specializationDepth());
CObject parentCObject = getCObject(flatParent.itemAtPath(flatPath));

if (parentCObject != null) {
if (cObject.isProhibited()) {
if (!parentCObject.getNodeId().equals(cObject.getNodeId())) {
// System.out.println("fixing node id " + cObject.getNodeId() + " for archetype " + archetype.getArchetypeId());
String oldNodeId = cObject.getNodeId();
cObject.setNodeId(parentCObject.getNodeId());
ArchetypeTerminology terminology = cObject.getArchetype().getTerminology();
for(String language:terminology.getTermDefinitions().keySet()) {
terminology.getTermDefinitions().get(language).remove(oldNodeId);
}
}
}
}
}
}
}

for(CAttribute attribute:cObject.getAttributes()) {
fixNodeId(attribute);
}
}

private void fixNodeId(CAttribute cAttribute) {
for(CObject cObject:cAttribute.getChildren()) {
fixNodeId(cObject);
}
}

private CObject getCObject(ArchetypeModelObject archetypeModelObject) {
if(archetypeModelObject instanceof CAttribute) {
CAttribute attribute = (CAttribute) archetypeModelObject;
if(attribute.getChildren().size() == 1) {
return attribute.getChildren().get(0);
}//TODO: add a numeric identifier to the getPath() method in CObject so this can be deleted and actually works in all cases!
} else if(archetypeModelObject instanceof CObject) {
return (CObject) archetypeModelObject;
}
return null;
}
}
141 changes: 141 additions & 0 deletions opt14/src/main/java/com/nedap/archie/opt14/NodeIdSpecializer.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,141 @@
package com.nedap.archie.opt14;

import com.nedap.archie.aom.Archetype;
import com.nedap.archie.aom.ArchetypeModelObject;
import com.nedap.archie.aom.CAttribute;
import com.nedap.archie.aom.CComplexObject;
import com.nedap.archie.aom.CObject;
import com.nedap.archie.aom.CPrimitiveObject;
import com.nedap.archie.aom.Template;
import com.nedap.archie.aom.TemplateOverlay;
import com.nedap.archie.aom.primitives.CString;
import com.nedap.archie.aom.terminology.ArchetypeTerm;
import com.nedap.archie.aom.utils.AOMUtils;
import com.nedap.archie.query.AOMPathQuery;
import com.nedap.archie.query.RMPathQuery;
import com.nedap.archie.rminfo.ArchieRMInfoLookup;

import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.Map;

/**
* Walks the archetype tree, then specializes any node ids it finds with change where required. Can be:
* - different type
* - different text or description
* - different primitive node child (TODO: check how in Differentiator?)
*
*
* TODO: remove simple single constraint name constraints, and put them in the terminology instead first!
*
*/
public class NodeIdSpecializer {

private Archetype archetype;
private Archetype flatParent;

public void specializeNodeIds(Archetype archetype, FlatArchetypeProvider repo) {
if(archetype.getParentArchetypeId() == null) {
return;
}
this.archetype = archetype;
if(archetype.getParentArchetypeId() != null) {
this.flatParent = repo.getFlatArchetype(archetype.getParentArchetypeId());
}
specializeNodeIds(archetype.getDefinition());

if(archetype instanceof Template) {
Template template = (Template) archetype;

for(TemplateOverlay overlay:template.getTemplateOverlays()) {
this.archetype = overlay;
if(archetype.getParentArchetypeId() != null) {
this.flatParent = repo.getFlatArchetype(overlay.getParentArchetypeId());
}

specializeNodeIds(overlay.getDefinition());
}
}
}


private void specializeNodeIds(CObject cObject) {
if(!(cObject instanceof CPrimitiveObject)) {
String flatPath = AOMUtils.pathAtSpecializationLevel(cObject.getPathSegments(), flatParent.specializationDepth());
CObject parentCObject = getCObject(flatParent.itemAtPath(flatPath));

if(parentCObject != null) {
ArchetypeTerm term = archetype.getTerm(cObject, archetype.getOriginalLanguage().getCodeString());
ArchetypeTerm parentTerm = flatParent.getTerm(parentCObject, archetype.getOriginalLanguage().getCodeString());
if( cObject.getNodeId().equalsIgnoreCase(parentCObject.getNodeId())) {
if(parentTerm != null && term != null) {
if (!term.getText().equalsIgnoreCase(parentTerm.getText()) ||
!term.getDescription().equalsIgnoreCase(parentTerm.getDescription())) {
//term changes. We need a new node id
System.out.println("GOT ONE!");
}
}
}

} else {
System.out.println("DID NOT EXPECT THIS");
// throw new RuntimeException("I did not expect the Spanish inquisition!");//TODO: remove or add proper message
}
for(CAttribute attribute:cObject.getAttributes()) {
specializeNodeIds(attribute);
}
}

}

private void specializeNodeIds(CAttribute attribute) {
if(attribute.getRmAttributeName().equalsIgnoreCase("name")) {
//ok a name constraint. If it's a simple constraint, replace it with a terminology entry please.
if(attribute.getChildren().size() == 1 && attribute.getChildren().get(0).getRmTypeName().equalsIgnoreCase("DV_TEXT")) {
CObject cObject = attribute.getChildren().get(0);
Object o = new AOMPathQuery("/value[1]").find((CComplexObject) cObject);
if(o instanceof CString) {
CString nameConstraint = (CString) o;
if (nameConstraint.getConstraint().size() == 1 && !CString.isRegexConstraint(nameConstraint.getConstraint().get(0))) {
//remove the crap out of this attribute.
attribute.setChildren(new ArrayList<>());
ArchetypeTerm term = archetype.getTerm(attribute.getParent(), archetype.getOriginalLanguage().getCodeString());
if (term != null) {
term.setText((nameConstraint.getConstraint().get(0)));
} else {
term = new ArchetypeTerm();
term.setCode(attribute.getParent().getNodeId());
term.setText(nameConstraint.getConstraint().get(0));
term.setDescription(nameConstraint.getConstraint().get(0));
getOrCreateTermDefinitions().put(attribute.getParent().getNodeId(), term);
}
}
}
}
}
for(CObject child:attribute.getChildren()) {
specializeNodeIds(child);
}
}

private Map<String, ArchetypeTerm> getOrCreateTermDefinitions() {
Map<String, ArchetypeTerm> termDefs = archetype.getTerminology().getTermDefinitions().get(archetype.getOriginalLanguage().getCodeString());
if(termDefs == null) {
termDefs = new LinkedHashMap<>();
archetype.getTerminology().getTermDefinitions().put(archetype.getOriginalLanguage().getCodeString(), termDefs);
}
return termDefs;
}

private CObject getCObject(ArchetypeModelObject archetypeModelObject) {
if(archetypeModelObject instanceof CAttribute) {
CAttribute attribute = (CAttribute) archetypeModelObject;
if(attribute.getChildren().size() == 1) {
return attribute.getChildren().get(0);
}//TODO: add a numeric identifier to the getPath() method in CObject so this can be deleted and actually works in all cases!
} else if(archetypeModelObject instanceof CObject) {
return (CObject) archetypeModelObject;
}
return null;
}
}
Loading

0 comments on commit 9f9e132

Please sign in to comment.