001package org.hl7.fhir.convertors.misc.searchparam;
002
003import java.io.FileInputStream;
004import java.io.FileOutputStream;
005import java.io.IOException;
006import java.util.ArrayList;
007import java.util.Collections;
008import java.util.Date;
009import java.util.List;
010
011/*
012  Copyright (c) 2011+, HL7, Inc.
013  All rights reserved.
014  
015  Redistribution and use in source and binary forms, with or without modification, 
016  are permitted provided that the following conditions are met:
017    
018   * Redistributions of source code must retain the above copyright notice, this 
019     list of conditions and the following disclaimer.
020   * Redistributions in binary form must reproduce the above copyright notice, 
021     this list of conditions and the following disclaimer in the documentation 
022     and/or other materials provided with the distribution.
023   * Neither the name of HL7 nor the names of its contributors may be used to 
024     endorse or promote products derived from this software without specific 
025     prior written permission.
026  
027  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND 
028  ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 
029  WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 
030  IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, 
031  INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 
032  NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 
033  PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 
034  WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 
035  ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 
036  POSSIBILITY OF SUCH DAMAGE.
037  
038 */
039
040
041import org.hl7.fhir.exceptions.FHIRException;
042import org.hl7.fhir.exceptions.FHIRFormatError;
043import org.hl7.fhir.r5.formats.IParser.OutputStyle;
044import org.hl7.fhir.r5.formats.JsonParser;
045import org.hl7.fhir.r5.model.ConceptMap;
046import org.hl7.fhir.r5.model.ConceptMap.ConceptMapGroupComponent;
047import org.hl7.fhir.r5.model.ConceptMap.SourceElementComponent;
048import org.hl7.fhir.r5.model.Enumerations.ConceptMapRelationship;
049import org.hl7.fhir.r5.model.Enumerations.PublicationStatus;
050import org.hl7.fhir.utilities.CSVReader;
051import org.hl7.fhir.utilities.Utilities;
052
053public class SearchParameterProcessor {
054
055  private static final String ROOT = "C:\\work\\org.hl7.fhir\\org.fhir.interversion\\package";
056  private final List<SPRelationship> list = new ArrayList<>();
057  private final List<String> list4 = new ArrayList<>();
058  private final List<String> list3 = new ArrayList<>();
059  private final List<String> list2 = new ArrayList<>();
060  private final List<String> list2b = new ArrayList<>();
061
062  //  private void generate(String name) throws IOException {
063//    StringBuilder b = new StringBuilder();
064//
065//    String rn = "";
066//    Collections.sort(list);
067//    for (String s : list) {
068//      String rnn = s.substring(0, s.indexOf("."));
069//      if (!rnn.equals(rn)) {
070//        rn = rnn;
071//        b.append(rn+"\r\n");
072//      }
073//      b.append(s+"\r\n");
074//    }
075//    TextFile.stringToFile(b.toString(), name);
076//  }
077//
078  public static void main(String[] args) throws IOException, FHIRException {
079    new SearchParameterProcessor().load();
080  }
081
082  private void load() throws IOException, FHIRException {
083    load4();
084    load3();
085    load2b();
086    load2();
087    loadCsv();
088
089    check4();
090    check3();
091    check2b();
092    check2();
093
094    generate("R3", "R4", "STU3", "R4");
095    generate("R4", "R3", "R4", "STU3");
096    generate("R2", "R4", "DSTU2", "R4");
097    generate("R4", "R2", "R4", "DSTU2");
098    generate("R2", "R3", "DSTU2", "STU3");
099    generate("R3", "R2", "STU3", "DSTU2");
100  }
101
102  private void generate(String src, String dst, String srcURL, String tgtURL) throws IOException {
103    ConceptMap map = new ConceptMap();
104    map.setId("search-parameters-" + src + "-to-" + dst);
105    map.setUrl("http://hl7.org/fhir/interversion/ConceptMap/" + map.getId());
106    map.setName("SearchParameterMap" + src + dst);
107    map.setTitle("Search Parameter Map - " + src + " to " + dst);
108    map.setStatus(PublicationStatus.DRAFT);
109    map.setDate(new Date());
110    map.setExperimental(false);
111    map.setPublisher("HL7");
112    ConceptMapGroupComponent group = map.addGroup();
113    group.setSource("http://hl7.org/fhir/" + srcURL);
114    group.setTarget("http://hl7.org/fhir/" + tgtURL);
115    for (SPRelationship sp : list) {
116      String s = sp.getByCode(src);
117      String d = sp.getByCode(dst);
118      if (!Utilities.noString(s) && !Utilities.noString(d)) {
119        SourceElementComponent e = makeElement(s, group);
120        e.addTarget().setCode(d).setRelationship(ConceptMapRelationship.RELATEDTO);
121      }
122    }
123    new JsonParser().setOutputStyle(OutputStyle.PRETTY).compose(new FileOutputStream(Utilities.path(ROOT, "ConceptMap-" + map.getId() + ".json")), map);
124  }
125
126  private SourceElementComponent makeElement(String code, ConceptMapGroupComponent group) {
127    for (SourceElementComponent e : group.getElement()) {
128      if (e.getCode().equals(code))
129        return e;
130    }
131    return group.addElement().setCode(code);
132  }
133
134  private void check4() {
135    for (String s : list4) {
136      boolean ok = false;
137      for (SPRelationship t : list) {
138        if (s.equals(t.getR4()))
139          ok = true;
140      }
141      if (!ok)
142        System.out.println("R4 missing : " + s);
143    }
144    for (SPRelationship sp : list) {
145      if (!Utilities.noString(sp.getR4())) {
146        boolean ok = list4.contains(sp.getR4());
147        if (!ok)
148          System.out.println("R4 extra : " + sp.getR4());
149      }
150    }
151  }
152
153  private void check3() {
154    for (String s : list3) {
155      boolean ok = false;
156      for (SPRelationship t : list) {
157        if (s.equals(t.getR3()))
158          ok = true;
159      }
160      if (!ok)
161        System.out.println("R3 : " + s);
162    }
163    for (SPRelationship sp : list) {
164      if (!Utilities.noString(sp.getR3())) {
165        boolean ok = list3.contains(sp.getR3());
166        if (!ok)
167          System.out.println("R3 extra : " + sp.getR3());
168      }
169    }
170  }
171
172  private void check2b() {
173    for (String s : list2b) {
174      boolean ok = false;
175      for (SPRelationship t : list) {
176        if (s.equals(t.getR2b()))
177          ok = true;
178      }
179      if (!ok)
180        System.out.println("R2b : " + s);
181    }
182    for (SPRelationship sp : list) {
183      if (!Utilities.noString(sp.getR2b())) {
184        boolean ok = list2b.contains(sp.getR2b());
185        if (!ok)
186          System.out.println("R2b extra : " + sp.getR2b());
187      }
188    }
189  }
190
191  private void check2() {
192    for (String s : list2) {
193      boolean ok = false;
194      for (SPRelationship t : list) {
195        if (s.equals(t.getR2()))
196          ok = true;
197      }
198      if (!ok)
199        System.out.println("R2 : " + s);
200    }
201    for (SPRelationship sp : list) {
202      if (!Utilities.noString(sp.getR2())) {
203        boolean ok = list2.contains(sp.getR2());
204        if (!ok)
205          System.out.println("R2 extra : " + sp.getR2());
206      }
207    }
208  }
209
210  private void load4() throws FHIRFormatError, IOException {
211    org.hl7.fhir.r4.model.Bundle bundle = (org.hl7.fhir.r4.model.Bundle) new org.hl7.fhir.r4.formats.JsonParser().parse(new FileInputStream(Utilities.path("[tmp]", "sp4.json")));
212    for (org.hl7.fhir.r4.model.Bundle.BundleEntryComponent be : bundle.getEntry()) {
213      org.hl7.fhir.r4.model.SearchParameter sp = (org.hl7.fhir.r4.model.SearchParameter) be.getResource();
214      for (org.hl7.fhir.r4.model.CodeType br : sp.getBase()) {
215        if (!Utilities.existsInList(br.asStringValue(), "DomainResource", "Resource"))
216          list4.add(br.asStringValue() + "." + sp.getCode());//+", "+sp.getType().toCode());
217      }
218    }
219    Collections.sort(list4);
220    System.out.println("R4 loaded - " + list4.size() + " parameters");
221  }
222
223  private void load3() throws FHIRFormatError, IOException {
224    org.hl7.fhir.dstu3.model.Bundle bundle = (org.hl7.fhir.dstu3.model.Bundle) new org.hl7.fhir.dstu3.formats.JsonParser().parse(new FileInputStream(Utilities.path("[tmp]", "sp3.json")));
225    for (org.hl7.fhir.dstu3.model.Bundle.BundleEntryComponent be : bundle.getEntry()) {
226      org.hl7.fhir.dstu3.model.SearchParameter sp = (org.hl7.fhir.dstu3.model.SearchParameter) be.getResource();
227      for (org.hl7.fhir.dstu3.model.CodeType br : sp.getBase()) {
228        if (!Utilities.existsInList(br.asStringValue(), "DomainResource", "Resource"))
229          list3.add(br.asStringValue() + "." + sp.getCode());//+", "+sp.getType().toCode());
230      }
231    }
232    Collections.sort(list3);
233    System.out.println("R3 loaded - " + list3.size() + " parameters");
234  }
235
236  private void load2() throws FHIRFormatError, IOException {
237    org.hl7.fhir.dstu2.model.Bundle bundle = (org.hl7.fhir.dstu2.model.Bundle) new org.hl7.fhir.dstu2.formats.JsonParser().parse(new FileInputStream(Utilities.path("[tmp]", "sp2.json")));
238    for (org.hl7.fhir.dstu2.model.Bundle.BundleEntryComponent be : bundle.getEntry()) {
239      org.hl7.fhir.dstu2.model.SearchParameter sp = (org.hl7.fhir.dstu2.model.SearchParameter) be.getResource();
240      String br = sp.getBase();
241      if (!Utilities.existsInList(br, "DomainResource", "Resource"))
242        list2.add(br + "." + sp.getCode());//+", "+sp.getType().toCode());
243    }
244    Collections.sort(list2);
245    System.out.println("R2 loaded - " + list2.size() + " parameters");
246  }
247
248  private void load2b() throws FHIRFormatError, IOException {
249    org.hl7.fhir.dstu2016may.model.Bundle bundle = (org.hl7.fhir.dstu2016may.model.Bundle) new org.hl7.fhir.dstu2016may.formats.JsonParser().parse(new FileInputStream(Utilities.path("[tmp]", "sp2b.json")));
250    for (org.hl7.fhir.dstu2016may.model.Bundle.BundleEntryComponent be : bundle.getEntry()) {
251      org.hl7.fhir.dstu2016may.model.SearchParameter sp = (org.hl7.fhir.dstu2016may.model.SearchParameter) be.getResource();
252      String br = sp.getBase();
253      if (!Utilities.existsInList(br, "DomainResource", "Resource"))
254        list2b.add(br + "." + sp.getCode());//+", "+sp.getType().toCode());
255    }
256    Collections.sort(list2b);
257    System.out.println("R2b loaded - " + list2b.size() + " parameters");
258  }
259
260  private void loadCsv() throws IOException, FHIRException {
261    CSVReader csv = new CSVReader(new FileInputStream("C:\\work\\org.hl7.fhir\\org.fhir.interversion\\work\\search-params.csv"));
262    csv.readHeaders();
263    while (csv.line()) {
264      String r4 = csv.cell("R4");
265      String r3 = csv.cell("R3");
266      String r2b = csv.cell("R2b");
267      String r2 = csv.cell("R2");
268      if (!Utilities.noString(r4) || !Utilities.noString(r3) || !Utilities.noString(r2b) || !Utilities.noString(r2)) {
269        boolean ok = (!Utilities.noString(r4) && r4.contains(".")) ||
270          (!Utilities.noString(r3) && r3.contains(".")) ||
271          (!Utilities.noString(r2b) && r2b.contains(".")) ||
272          (!Utilities.noString(r2) && r2.contains("."));
273        if (ok) {
274          list.add(new SPRelationship(r4, r3, r2b, r2));
275        }
276      }
277    }
278    System.out.println("Map loaded - " + list.size() + " entries");
279  }
280
281
282}