001/*- 002 * #%L 003 * HAPI FHIR JPA Server 004 * %% 005 * Copyright (C) 2014 - 2024 Smile CDR, Inc. 006 * %% 007 * Licensed under the Apache License, Version 2.0 (the "License"); 008 * you may not use this file except in compliance with the License. 009 * You may obtain a copy of the License at 010 * 011 * http://www.apache.org/licenses/LICENSE-2.0 012 * 013 * Unless required by applicable law or agreed to in writing, software 014 * distributed under the License is distributed on an "AS IS" BASIS, 015 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 016 * See the License for the specific language governing permissions and 017 * limitations under the License. 018 * #L% 019 */ 020package ca.uhn.fhir.jpa.term.snomedct; 021 022import ca.uhn.fhir.jpa.entity.TermCodeSystemVersion; 023import ca.uhn.fhir.jpa.entity.TermConcept; 024import ca.uhn.fhir.jpa.entity.TermConceptParentChildLink; 025import ca.uhn.fhir.jpa.term.IZipContentsHandlerCsv; 026import org.apache.commons.csv.CSVRecord; 027 028import java.util.*; 029 030public final class SctHandlerRelationship implements IZipContentsHandlerCsv { 031 private final Map<String, TermConcept> myCode2concept; 032 private final TermCodeSystemVersion myCodeSystemVersion; 033 private final Map<String, TermConcept> myRootConcepts; 034 035 public SctHandlerRelationship( 036 TermCodeSystemVersion theCodeSystemVersion, 037 HashMap<String, TermConcept> theRootConcepts, 038 Map<String, TermConcept> theCode2concept) { 039 myCodeSystemVersion = theCodeSystemVersion; 040 myRootConcepts = theRootConcepts; 041 myCode2concept = theCode2concept; 042 } 043 044 @Override 045 public void accept(CSVRecord theRecord) { 046 Set<String> ignoredTypes = new HashSet<String>(); 047 ignoredTypes.add("Method (attribute)"); 048 ignoredTypes.add("Direct device (attribute)"); 049 ignoredTypes.add("Has focus (attribute)"); 050 ignoredTypes.add("Access instrument"); 051 ignoredTypes.add("Procedure site (attribute)"); 052 ignoredTypes.add("Causative agent (attribute)"); 053 ignoredTypes.add("Course (attribute)"); 054 ignoredTypes.add("Finding site (attribute)"); 055 ignoredTypes.add("Has definitional manifestation (attribute)"); 056 057 String sourceId = theRecord.get("sourceId"); 058 String destinationId = theRecord.get("destinationId"); 059 String typeId = theRecord.get("typeId"); 060 boolean active = "1".equals(theRecord.get("active")); 061 062 TermConcept typeConcept = myCode2concept.get(typeId); 063 TermConcept sourceConcept = myCode2concept.get(sourceId); 064 TermConcept targetConcept = myCode2concept.get(destinationId); 065 if (sourceConcept != null && targetConcept != null && typeConcept != null) { 066 if (typeConcept.getDisplay().equals("Is a (attribute)")) { 067 TermConceptParentChildLink.RelationshipTypeEnum relationshipType = 068 TermConceptParentChildLink.RelationshipTypeEnum.ISA; 069 if (!sourceId.equals(destinationId)) { 070 if (active) { 071 TermConceptParentChildLink link = new TermConceptParentChildLink(); 072 link.setChild(sourceConcept); 073 link.setParent(targetConcept); 074 link.setRelationshipType(relationshipType); 075 link.setCodeSystem(myCodeSystemVersion); 076 077 targetConcept.addChild(sourceConcept, relationshipType); 078 } else { 079 // not active, so we're removing any existing links 080 for (TermConceptParentChildLink next : 081 new ArrayList<TermConceptParentChildLink>(targetConcept.getChildren())) { 082 if (next.getRelationshipType() == relationshipType) { 083 if (next.getChild().getCode().equals(sourceConcept.getCode())) { 084 next.getParent().getChildren().remove(next); 085 next.getChild().getParents().remove(next); 086 } 087 } 088 } 089 } 090 } 091 } else if (ignoredTypes.contains(typeConcept.getDisplay())) { 092 // ignore 093 } else { 094 // ourLog.warn("Unknown relationship type: {}/{}", typeId, typeConcept.getDisplay()); 095 } 096 } 097 } 098}