Merge pull request #730 from dotasek/simpleworkercontextbuilder

Refactor to use builder pattern in SimpleWorkerContext and ValidationEngine
This commit is contained in:
dotasek 2022-02-07 09:19:00 -05:00 committed by GitHub
commit df33e3cdd6
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
32 changed files with 332 additions and 7747 deletions

View File

@ -4,4 +4,4 @@
## Other code changes
* no changes
* Use builders for SimpleWorkerContext and ValidationEngine to enforce initialization order for caches and capabilities

View File

@ -18,10 +18,9 @@ public class OIDBasedValueSetImporter {
protected void init() throws FHIRException, IOException {
FilesystemPackageCacheManager pcm = new FilesystemPackageCacheManager(true, ToolsVersion.TOOLS_VERSION);
NpmPackage npm = pcm.loadPackage("hl7.fhir.r5.core", "current");
SimpleWorkerContext ctxt = SimpleWorkerContext.fromPackage(npm);
ctxt.setAllowLoadingDuplicates(true);
ctxt.loadFromPackage(pcm.loadPackage("hl7.terminology"), null);
context = ctxt;
SimpleWorkerContext context = new SimpleWorkerContext.SimpleWorkerContextBuilder().withAllowLoadingDuplicates(true).fromPackage(npm);
context.loadFromPackage(pcm.loadPackage("hl7.terminology"), null);
this.context = context;
}
protected String fixVersionforSystem(String url, String csver) {

View File

@ -12,7 +12,6 @@ import org.hl7.fhir.dstu3.utils.ResourceUtilities;
import org.hl7.fhir.dstu3.utils.client.EFhirClientException;
import org.hl7.fhir.dstu3.utils.client.ResourceFormat;
import org.hl7.fhir.utilities.ToolingClientLogger;
import org.hl7.fhir.utilities.TxInterceptor;
import java.io.IOException;
import java.util.ArrayList;
@ -163,7 +162,6 @@ public class FhirRequestBuilder {
return okHttpClient.newBuilder()
.addInterceptor(new RetryInterceptor(retryCount))
.addInterceptor(TxInterceptor.getInstance())
.connectTimeout(timeout, timeoutUnit)
.writeTimeout(timeout, timeoutUnit)
.readTimeout(timeout, timeoutUnit)

View File

@ -11,12 +11,8 @@ import org.hl7.fhir.r4.model.Resource;
import org.hl7.fhir.r4.utils.ResourceUtilities;
import org.hl7.fhir.r4.utils.client.EFhirClientException;
import org.hl7.fhir.r4.utils.client.ResourceFormat;
import org.hl7.fhir.utilities.ToolingClientLogger;
import org.hl7.fhir.utilities.TxInterceptor;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.concurrent.TimeUnit;
@ -165,7 +161,6 @@ public class FhirRequestBuilder {
OkHttpClient.Builder builder = okHttpClient.newBuilder();
if (logger != null) builder.addInterceptor(logger);
builder.addInterceptor(new RetryInterceptor(retryCount));
builder.addInterceptor(TxInterceptor.getInstance());
return builder.connectTimeout(timeout, timeoutUnit)
.addInterceptor(new RetryInterceptor(retryCount))

View File

@ -163,7 +163,7 @@ public abstract class BaseWorkerContext extends I18nBase implements IWorkerConte
public class MetadataResourceVersionComparator<T extends CanonicalResource> implements Comparator<T> {
private List<T> list;
final private List<T> list;
public MetadataResourceVersionComparator(List<T> list) {
this.list = list;
@ -197,26 +197,26 @@ public abstract class BaseWorkerContext extends I18nBase implements IWorkerConte
private boolean isTxCaching;
@Getter
private int serverQueryCount = 0;
private Set<String> cached = new HashSet<>();
private final Set<String> cached = new HashSet<>();
private Map<String, Map<String, ResourceProxy>> allResourcesById = new HashMap<String, Map<String, ResourceProxy>>();
// all maps are to the full URI
private CanonicalResourceManager<CodeSystem> codeSystems = new CanonicalResourceManager<CodeSystem>(false);
private Set<String> supportedCodeSystems = new HashSet<String>();
private Set<String> unsupportedCodeSystems = new HashSet<String>(); // know that the terminology server doesn't support them
private final Set<String> supportedCodeSystems = new HashSet<String>();
private final Set<String> unsupportedCodeSystems = new HashSet<String>(); // know that the terminology server doesn't support them
private CanonicalResourceManager<ValueSet> valueSets = new CanonicalResourceManager<ValueSet>(false);
private CanonicalResourceManager<ConceptMap> maps = new CanonicalResourceManager<ConceptMap>(false);
protected CanonicalResourceManager<StructureMap> transforms = new CanonicalResourceManager<StructureMap>(false);
private CanonicalResourceManager<StructureDefinition> structures = new CanonicalResourceManager<StructureDefinition>(false);
private CanonicalResourceManager<Measure> measures = new CanonicalResourceManager<Measure>(false);
private CanonicalResourceManager<Library> libraries = new CanonicalResourceManager<Library>(false);
private final CanonicalResourceManager<Measure> measures = new CanonicalResourceManager<Measure>(false);
private final CanonicalResourceManager<Library> libraries = new CanonicalResourceManager<Library>(false);
private CanonicalResourceManager<ImplementationGuide> guides = new CanonicalResourceManager<ImplementationGuide>(false);
private CanonicalResourceManager<CapabilityStatement> capstmts = new CanonicalResourceManager<CapabilityStatement>(false);
private CanonicalResourceManager<SearchParameter> searchParameters = new CanonicalResourceManager<SearchParameter>(false);
private CanonicalResourceManager<Questionnaire> questionnaires = new CanonicalResourceManager<Questionnaire>(false);
private CanonicalResourceManager<OperationDefinition> operations = new CanonicalResourceManager<OperationDefinition>(false);
private CanonicalResourceManager<PlanDefinition> plans = new CanonicalResourceManager<PlanDefinition>(false);
private CanonicalResourceManager<NamingSystem> systems = new CanonicalResourceManager<NamingSystem>(false);
private final CanonicalResourceManager<CapabilityStatement> capstmts = new CanonicalResourceManager<CapabilityStatement>(false);
private final CanonicalResourceManager<SearchParameter> searchParameters = new CanonicalResourceManager<SearchParameter>(false);
private final CanonicalResourceManager<Questionnaire> questionnaires = new CanonicalResourceManager<Questionnaire>(false);
private final CanonicalResourceManager<OperationDefinition> operations = new CanonicalResourceManager<OperationDefinition>(false);
private final CanonicalResourceManager<PlanDefinition> plans = new CanonicalResourceManager<PlanDefinition>(false);
private final CanonicalResourceManager<NamingSystem> systems = new CanonicalResourceManager<NamingSystem>(false);
private UcumService ucumService;
protected Map<String, byte[]> binaries = new HashMap<String, byte[]>();
@ -228,7 +228,7 @@ public abstract class BaseWorkerContext extends I18nBase implements IWorkerConte
private boolean allowLoadingDuplicates;
protected TerminologyClient txClient;
private Set<String> codeSystemsUsed = new HashSet<>();
private final Set<String> codeSystemsUsed = new HashSet<>();
protected ToolingClientLogger txLog;
private TerminologyCapabilities txcaps;
private boolean canRunWithoutTerminology;
@ -245,19 +245,17 @@ public abstract class BaseWorkerContext extends I18nBase implements IWorkerConte
private ICanonicalResourceLocator locator;
protected String userAgent;
public BaseWorkerContext() throws FileNotFoundException, IOException, FHIRException {
txCache = new TerminologyCache(lock, null);
protected BaseWorkerContext() throws FileNotFoundException, IOException, FHIRException {
setValidationMessageLanguage(getLocale());
clock = new TimeTracker();
}
public BaseWorkerContext(Locale locale) throws FileNotFoundException, IOException, FHIRException {
txCache = new TerminologyCache(lock, null);
protected BaseWorkerContext(Locale locale) throws FileNotFoundException, IOException, FHIRException {
setValidationMessageLanguage(locale);
clock = new TimeTracker();
}
public BaseWorkerContext(CanonicalResourceManager<CodeSystem> codeSystems, CanonicalResourceManager<ValueSet> valueSets, CanonicalResourceManager<ConceptMap> maps, CanonicalResourceManager<StructureDefinition> profiles,
protected BaseWorkerContext(CanonicalResourceManager<CodeSystem> codeSystems, CanonicalResourceManager<ValueSet> valueSets, CanonicalResourceManager<ConceptMap> maps, CanonicalResourceManager<StructureDefinition> profiles,
CanonicalResourceManager<ImplementationGuide> guides) throws FileNotFoundException, IOException, FHIRException {
this();
this.codeSystems = codeSystems;
@ -1255,8 +1253,8 @@ public abstract class BaseWorkerContext extends I18nBase implements IWorkerConte
// --------------------------------------------------------------------------------------------------------------------------------------------------------
public void initTS(String cachePath) throws IOException {
if (!new File(cachePath).exists()) {
protected void initTS(String cachePath) throws IOException {
if (cachePath != null && !new File(cachePath).exists()) {
Utilities.createDirectory(cachePath);
}
txCache = new TerminologyCache(lock, cachePath);
@ -2245,7 +2243,7 @@ public abstract class BaseWorkerContext extends I18nBase implements IWorkerConte
return userAgent;
}
public void setUserAgent(String userAgent) {
protected void setUserAgent(String userAgent) {
this.userAgent = userAgent;
if (txClient != null)
txClient.setUserAgent(userAgent);

View File

@ -47,6 +47,9 @@ import java.util.Set;
import java.util.zip.ZipEntry;
import java.util.zip.ZipInputStream;
import lombok.AccessLevel;
import lombok.AllArgsConstructor;
import lombok.With;
import org.apache.commons.io.IOUtils;
import org.hl7.fhir.exceptions.DefinitionException;
import org.hl7.fhir.exceptions.FHIRException;
@ -94,8 +97,8 @@ public class SimpleWorkerContext extends BaseWorkerContext implements IWorkerCon
public static class PackageResourceLoader extends CanonicalResourceProxy {
private String filename;
private IContextResourceLoader loader;
private final String filename;
private final IContextResourceLoader loader;
public PackageResourceLoader(PackageResourceInformation pri, IContextResourceLoader loader) {
super(pri.getType(), pri.getId(), pri.getUrl(),pri.getVersion());
@ -138,24 +141,24 @@ public class SimpleWorkerContext extends BaseWorkerContext implements IWorkerCon
private IValidatorFactory validatorFactory;
private boolean ignoreProfileErrors;
private boolean progress;
private List<String> loadedPackages = new ArrayList<String>();
private final List<String> loadedPackages = new ArrayList<>();
private boolean canNoTS;
private XVerExtensionManager xverManager;
public SimpleWorkerContext() throws FileNotFoundException, IOException, FHIRException {
private SimpleWorkerContext() throws IOException, FHIRException {
super();
}
public SimpleWorkerContext(Locale locale) throws FileNotFoundException, IOException, FHIRException {
private SimpleWorkerContext(Locale locale) throws IOException, FHIRException {
super(locale);
}
public SimpleWorkerContext(SimpleWorkerContext other) throws FileNotFoundException, IOException, FHIRException {
private SimpleWorkerContext(SimpleWorkerContext other) throws IOException, FHIRException {
super();
copy(other);
}
public SimpleWorkerContext(SimpleWorkerContext other, Locale locale) throws FileNotFoundException, IOException, FHIRException {
private SimpleWorkerContext(SimpleWorkerContext other, Locale locale) throws IOException, FHIRException {
super(locale);
copy(other);
}
@ -176,91 +179,126 @@ public class SimpleWorkerContext extends BaseWorkerContext implements IWorkerCon
}
// -- Initializations
/**
* Load the working context from the validation pack
*
* @param path
* filename of the validation pack
* @return
* @throws IOException
* @throws FileNotFoundException
* @throws FHIRException
* @throws Exception
*/
public static SimpleWorkerContext fromPack(String path) throws FileNotFoundException, IOException, FHIRException {
SimpleWorkerContext res = new SimpleWorkerContext();
res.loadFromPack(path, null);
return res;
}
@AllArgsConstructor(access = AccessLevel.PRIVATE)
public static class SimpleWorkerContextBuilder {
public static SimpleWorkerContext fromPackage(NpmPackage pi, boolean allowDuplicates) throws FileNotFoundException, IOException, FHIRException {
SimpleWorkerContext res = new SimpleWorkerContext();
res.setAllowLoadingDuplicates(allowDuplicates);
res.loadFromPackage(pi, null);
return res;
}
public static SimpleWorkerContext fromPackage(NpmPackage pi) throws FileNotFoundException, IOException, FHIRException {
SimpleWorkerContext res = new SimpleWorkerContext();
res.loadFromPackage(pi, null);
return res;
}
@With
private final String terminologyCachePath;
@With
private final boolean cacheTerminologyClientErrors;
@With
private final boolean alwaysUseTerminologyServer;
@With
private final boolean readOnlyCache;
public static SimpleWorkerContext fromPackage(NpmPackage pi, IContextResourceLoader loader) throws FileNotFoundException, IOException, FHIRException {
SimpleWorkerContext res = new SimpleWorkerContext();
res.setAllowLoadingDuplicates(true);
res.version = pi.getNpm().get("version").getAsString();
res.loadFromPackage(pi, loader);
res.finishLoading();
return res;
}
@With
private final Locale locale;
public static SimpleWorkerContext fromPack(String path, boolean allowDuplicates) throws FileNotFoundException, IOException, FHIRException {
SimpleWorkerContext res = new SimpleWorkerContext();
res.setAllowLoadingDuplicates(allowDuplicates);
res.loadFromPack(path, null);
return res;
}
@With
private final String userAgent;
public static SimpleWorkerContext fromPack(String path, IContextResourceLoader loader) throws FileNotFoundException, IOException, FHIRException {
SimpleWorkerContext res = new SimpleWorkerContext();
res.loadFromPack(path, loader);
return res;
}
@With
private final boolean allowLoadingDuplicates;
public static SimpleWorkerContext fromClassPath() throws IOException, FHIRException {
SimpleWorkerContext res = new SimpleWorkerContext();
res.loadFromStream(SimpleWorkerContext.class.getResourceAsStream("validation.json.zip"), null);
return res;
}
public SimpleWorkerContextBuilder() {
cacheTerminologyClientErrors = false;
alwaysUseTerminologyServer = false;
readOnlyCache = false;
terminologyCachePath = null;
locale = null;
userAgent = null;
allowLoadingDuplicates = false;
}
public static SimpleWorkerContext fromClassPath(String name) throws IOException, FHIRException {
return fromClassPath(name, false);
}
public static SimpleWorkerContext fromClassPath(String name, boolean allowDuplicates) throws IOException, FHIRException {
InputStream s = SimpleWorkerContext.class.getResourceAsStream("/" + name);
SimpleWorkerContext res = new SimpleWorkerContext();
res.setAllowLoadingDuplicates(allowDuplicates);
res.loadFromStream(s, null);
return res;
}
public static SimpleWorkerContext fromDefinitions(Map<String, byte[]> source, IContextResourceLoader loader, PackageVersion pi) throws FileNotFoundException, IOException, FHIRException {
SimpleWorkerContext res = new SimpleWorkerContext();
for (String name : source.keySet()) {
try {
res.loadDefinitionItem(name, new ByteArrayInputStream(source.get(name)), loader, null, pi);
} catch (Exception e) {
System.out.println("Error loading "+name+": "+e.getMessage());
throw new FHIRException("Error loading "+name+": "+e.getMessage(), e);
private SimpleWorkerContext getSimpleWorkerContextInstance() throws IOException {
if (locale != null) {
return new SimpleWorkerContext(locale);
} else {
return new SimpleWorkerContext();
}
}
return res;
}
public static SimpleWorkerContext fromNothing() throws FileNotFoundException, FHIRException, IOException {
SimpleWorkerContext res = new SimpleWorkerContext();
return res;
public SimpleWorkerContext build() throws IOException {
SimpleWorkerContext context = getSimpleWorkerContextInstance();
return build(context);
}
private SimpleWorkerContext build(SimpleWorkerContext context) throws IOException {
context.initTS(terminologyCachePath);
context.setUserAgent(userAgent);
return context;
}
public SimpleWorkerContext fromPackage(NpmPackage pi) throws IOException, FHIRException {
SimpleWorkerContext context = getSimpleWorkerContextInstance();
context.setAllowLoadingDuplicates(allowLoadingDuplicates);
context.loadFromPackage(pi, null);
return build(context);
}
public SimpleWorkerContext fromPackage(NpmPackage pi, IContextResourceLoader loader) throws IOException, FHIRException {
SimpleWorkerContext context = getSimpleWorkerContextInstance();
context.setAllowLoadingDuplicates(true);
context.version = pi.getNpm().get("version").getAsString();
context.loadFromPackage(pi, loader);
context.finishLoading();
return build(context);
}
/**
* Load the working context from the validation pack
*
* @param path
* filename of the validation pack
* @return
* @throws IOException
* @throws FileNotFoundException
* @throws FHIRException
* @throws Exception
*/
public SimpleWorkerContext fromPack(String path) throws IOException, FHIRException {
SimpleWorkerContext context = getSimpleWorkerContextInstance();
context.setAllowLoadingDuplicates(allowLoadingDuplicates);
context.loadFromPack(path, null);
return build(context);
}
public SimpleWorkerContext fromPack(String path, IContextResourceLoader loader) throws IOException, FHIRException {
SimpleWorkerContext context = getSimpleWorkerContextInstance();
context.loadFromPack(path, loader);
return build(context);
}
public SimpleWorkerContext fromClassPath() throws IOException, FHIRException {
SimpleWorkerContext context = getSimpleWorkerContextInstance();
context.loadFromStream(SimpleWorkerContext.class.getResourceAsStream("validation.json.zip"), null);
return build(context);
}
public SimpleWorkerContext fromClassPath(String name) throws IOException, FHIRException {
SimpleWorkerContext context = getSimpleWorkerContextInstance();
InputStream s = SimpleWorkerContext.class.getResourceAsStream("/" + name);
context.setAllowLoadingDuplicates(allowLoadingDuplicates);
context.loadFromStream(s, null);
return build(context);
}
public SimpleWorkerContext fromDefinitions(Map<String, byte[]> source, IContextResourceLoader loader, PackageVersion pi) throws IOException, FHIRException {
SimpleWorkerContext context = getSimpleWorkerContextInstance();
for (String name : source.keySet()) {
try {
context.loadDefinitionItem(name, new ByteArrayInputStream(source.get(name)), loader, null, pi);
} catch (Exception e) {
System.out.println("Error loading "+name+": "+e.getMessage());
throw new FHIRException("Error loading "+name+": "+e.getMessage(), e);
}
}
return build(context);
}
public SimpleWorkerContext fromNothing() throws FHIRException, IOException {
return build();
}
}
private void loadDefinitionItem(String name, InputStream stream, IContextResourceLoader loader, ILoadFilter filter, PackageVersion pi) throws IOException, FHIRException {
@ -299,11 +337,11 @@ public class SimpleWorkerContext extends BaseWorkerContext implements IWorkerCon
}
}
public void loadFromFile(InputStream stream, String name, IContextResourceLoader loader) throws IOException, FHIRException {
public void loadFromFile(InputStream stream, String name, IContextResourceLoader loader) throws FHIRException {
loadFromFile(stream, name, loader, null);
}
public void loadFromFile(InputStream stream, String name, IContextResourceLoader loader, ILoadFilter filter) throws IOException, FHIRException {
public void loadFromFile(InputStream stream, String name, IContextResourceLoader loader, ILoadFilter filter) throws FHIRException {
Resource f;
try {
if (loader != null)
@ -371,13 +409,13 @@ public class SimpleWorkerContext extends BaseWorkerContext implements IWorkerCon
}
}
private void loadFromPack(String path, IContextResourceLoader loader) throws FileNotFoundException, IOException, FHIRException {
private void loadFromPack(String path, IContextResourceLoader loader) throws IOException, FHIRException {
loadFromStream(new CSFileInputStream(path), loader);
}
@Override
public int loadFromPackage(NpmPackage pi, IContextResourceLoader loader) throws FileNotFoundException, IOException, FHIRException {
public int loadFromPackage(NpmPackage pi, IContextResourceLoader loader) throws IOException, FHIRException {
return loadFromPackageInt(pi, loader, loader == null ? defaultTypesToLoad() : loader.getTypes());
}
@ -390,15 +428,15 @@ public class SimpleWorkerContext extends BaseWorkerContext implements IWorkerCon
}
@Override
public int loadFromPackage(NpmPackage pi, IContextResourceLoader loader, String[] types) throws FileNotFoundException, IOException, FHIRException {
public int loadFromPackage(NpmPackage pi, IContextResourceLoader loader, String[] types) throws IOException, FHIRException {
return loadFromPackageInt(pi, loader, types);
}
@Override
public int loadFromPackageAndDependencies(NpmPackage pi, IContextResourceLoader loader, BasePackageCacheManager pcm) throws FileNotFoundException, IOException, FHIRException {
public int loadFromPackageAndDependencies(NpmPackage pi, IContextResourceLoader loader, BasePackageCacheManager pcm) throws IOException, FHIRException {
return loadFromPackageAndDependenciesInt(pi, loader, pcm, pi.name()+"#"+pi.version());
}
public int loadFromPackageAndDependenciesInt(NpmPackage pi, IContextResourceLoader loader, BasePackageCacheManager pcm, String path) throws FileNotFoundException, IOException, FHIRException {
public int loadFromPackageAndDependenciesInt(NpmPackage pi, IContextResourceLoader loader, BasePackageCacheManager pcm, String path) throws IOException, FHIRException {
int t = 0;
for (String e : pi.dependencies()) {
@ -415,7 +453,7 @@ public class SimpleWorkerContext extends BaseWorkerContext implements IWorkerCon
}
public int loadFromPackageInt(NpmPackage pi, IContextResourceLoader loader, String... types) throws FileNotFoundException, IOException, FHIRException {
public int loadFromPackageInt(NpmPackage pi, IContextResourceLoader loader, String... types) throws IOException, FHIRException {
int t = 0;
if (progress) {
System.out.println("Load Package "+pi.name()+"#"+pi.version());
@ -644,19 +682,19 @@ public class SimpleWorkerContext extends BaseWorkerContext implements IWorkerCon
}
public void loadBinariesFromFolder(String folder) throws FileNotFoundException, Exception {
public void loadBinariesFromFolder(String folder) throws IOException {
for (String n : new File(folder).list()) {
loadBytes(n, new FileInputStream(Utilities.path(folder, n)));
}
}
public void loadBinariesFromFolder(NpmPackage pi) throws FileNotFoundException, Exception {
public void loadBinariesFromFolder(NpmPackage pi) throws IOException {
for (String n : pi.list("other")) {
loadBytes(n, pi.load("other", n));
}
}
public void loadFromFolder(String folder) throws FileNotFoundException, Exception {
public void loadFromFolder(String folder) throws IOException {
for (String n : new File(folder).list()) {
if (n.endsWith(".json"))
loadFromFile(Utilities.path(folder, n), new JsonParser());
@ -665,7 +703,7 @@ public class SimpleWorkerContext extends BaseWorkerContext implements IWorkerCon
}
}
private void loadFromFile(String filename, IParser p) throws FileNotFoundException, Exception {
private void loadFromFile(String filename, IParser p) {
Resource r;
try {
r = p.parse(new FileInputStream(filename));
@ -744,12 +782,12 @@ public class SimpleWorkerContext extends BaseWorkerContext implements IWorkerCon
}
@Override
public void generateSnapshot(StructureDefinition p) throws DefinitionException, FHIRException {
public void generateSnapshot(StructureDefinition p) throws FHIRException {
generateSnapshot(p, false);
}
@Override
public void generateSnapshot(StructureDefinition p, boolean logical) throws DefinitionException, FHIRException {
public void generateSnapshot(StructureDefinition p, boolean logical) throws FHIRException {
if ((!p.hasSnapshot() || isProfileNeedsRegenerate(p) ) && (logical || p.getKind() != StructureDefinitionKind.LOGICAL)) {
if (!p.hasBaseDefinition())
throw new DefinitionException(formatMessage(I18nConstants.PROFILE___HAS_NO_BASE_AND_NO_SNAPSHOT, p.getName(), p.getUrl()));

View File

@ -1,33 +1,33 @@
package org.hl7.fhir.r5.elementmodel;
/*
Copyright (c) 2011+, HL7, Inc.
All rights reserved.
Redistribution and use in source and binary forms, with or without modification,
are permitted provided that the following conditions are met:
* Redistributions of source code must retain the above copyright notice, this
list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above copyright notice,
this list of conditions and the following disclaimer in the documentation
and/or other materials provided with the distribution.
* Neither the name of HL7 nor the names of its contributors may be used to
endorse or promote products derived from this software without specific
prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
POSSIBILITY OF SUCH DAMAGE.
*/
/*
Copyright (c) 2011+, HL7, Inc.
All rights reserved.
Redistribution and use in source and binary forms, with or without modification,
are permitted provided that the following conditions are met:
* Redistributions of source code must retain the above copyright notice, this
list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above copyright notice,
this list of conditions and the following disclaimer in the documentation
and/or other materials provided with the distribution.
* Neither the name of HL7 nor the names of its contributors may be used to
endorse or promote products derived from this software without specific
prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
POSSIBILITY OF SUCH DAMAGE.
*/
@ -52,7 +52,7 @@ import com.google.gson.JsonObject;
public class Tester {
public static void main(String[] args) throws Exception {
IWorkerContext context = SimpleWorkerContext.fromPack(Utilities.path("C:\\work\\org.hl7.fhir\\build\\publish", "validation-min.xml.zip"));
IWorkerContext context = new SimpleWorkerContext.SimpleWorkerContextBuilder().fromPack(Utilities.path("C:\\work\\org.hl7.fhir\\build\\publish", "validation-min.xml.zip"));
int t = 0;
int ok = 0;
for (String f : new File("C:\\work\\org.hl7.fhir\\build\\publish").list()) {

View File

@ -1,7 +1,9 @@
package org.hl7.fhir.r5.test.utils;
import java.nio.file.Paths;
import java.lang.String;
public class TestConstants {
public static final java.lang.String TX_CACHE = Paths.get("src","test","resources", "txCache").toAbsolutePath().toString();
public static final String TX_CACHE = Paths.get("src","test","resources", "txCache").toAbsolutePath().toString();
public static final String USER_AGENT = "fhir/r5-test-cases";
}

View File

@ -105,18 +105,14 @@ public class TestingUtilities extends BaseTestingUtilities {
}
public static SimpleWorkerContext getWorkerContext(NpmPackage npmPackage) throws Exception {
SimpleWorkerContext swc = SimpleWorkerContext.fromPackage(npmPackage);
swc.initTS(TestConstants.TX_CACHE);
SimpleWorkerContext swc = new SimpleWorkerContext.SimpleWorkerContextBuilder().withUserAgent(TestConstants.USER_AGENT).withTerminologyCachePath(TestConstants.TX_CACHE).fromPackage(npmPackage);
TerminologyCache.setCacheErrors(true);
swc.setUserAgent("fhir/r5-test-cases");
return swc;
}
public static SimpleWorkerContext getWorkerContext(NpmPackage npmPackage, IWorkerContext.IContextResourceLoader loader) throws Exception {
SimpleWorkerContext swc = SimpleWorkerContext.fromPackage(npmPackage, loader);
swc.initTS(TestConstants.TX_CACHE);
SimpleWorkerContext swc = new SimpleWorkerContext.SimpleWorkerContextBuilder().withUserAgent(TestConstants.USER_AGENT).withTerminologyCachePath(TestConstants.TX_CACHE).fromPackage(npmPackage, loader);
TerminologyCache.setCacheErrors(true);
swc.setUserAgent("fhir/r5-test-cases");
return swc;
}

View File

@ -11,7 +11,6 @@ import org.hl7.fhir.r5.model.Resource;
import org.hl7.fhir.r5.utils.ResourceUtilities;
import org.hl7.fhir.r5.utils.client.EFhirClientException;
import org.hl7.fhir.r5.utils.client.ResourceFormat;
import org.hl7.fhir.utilities.TxInterceptor;
import java.io.IOException;
import java.util.List;
@ -162,7 +161,6 @@ public class FhirRequestBuilder {
OkHttpClient.Builder builder = okHttpClient.newBuilder();
if (logger != null) builder.addInterceptor(logger);
builder.addInterceptor(new RetryInterceptor(retryCount));
builder.addInterceptor(TxInterceptor.getInstance());
return builder.connectTimeout(timeout, timeoutUnit)
.writeTimeout(timeout, timeoutUnit)
.readTimeout(timeout, timeoutUnit)

View File

@ -23,7 +23,7 @@ public class ValidationTestConvertor {
* @throws FileNotFoundException
*/
public static void main(String[] args) throws FileNotFoundException, IOException, FHIRException {
SimpleWorkerContext context = SimpleWorkerContext.fromPack("C:\\work\\org.hl7.fhir\\build\\publish\\validation-min.xml.zip");
SimpleWorkerContext context = new SimpleWorkerContext.SimpleWorkerContextBuilder().fromPack("C:\\work\\org.hl7.fhir\\build\\publish\\validation-min.xml.zip");
for (File f : new File("C:\\work\\org.hl7.fhir\\build\\tests\\validation-examples").listFiles()) {
if (f.getAbsolutePath().endsWith(".xml")) {
File t = new File(Utilities.changeFileExt(f.getAbsolutePath(), ".ttl"));

View File

@ -1,49 +0,0 @@
package org.hl7.fhir.utilities;
import okhttp3.Interceptor;
import okhttp3.Response;
import java.io.IOException;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;
/**
* An {@link Interceptor} for {@link okhttp3.OkHttpClient} that tracks visits to specific urls
*/
public class TxInterceptor implements Interceptor {
private String getKey(String method, String url) {
return method + " " + url;
}
private static TxInterceptor instance;
public static TxInterceptor getInstance() {
if (instance == null) {
instance = new TxInterceptor();
}
return instance;
}
final Map<String, Integer> queriedUrls;
private TxInterceptor() {
queriedUrls = new HashMap<>();
}
@Override
public Response intercept(Interceptor.Chain chain) throws IOException {
Response response = chain.proceed(chain.request());
final String key = getKey(response.request().method(), response.request().url().toString());
final int count = queriedUrls.containsKey(key) ? queriedUrls.get(key) : 1;
queriedUrls.put(key, count+1);
System.out.print("");
return response;
}
}

View File

@ -58,7 +58,7 @@ public class CacheVerificationLogger implements ToolingClientLogger {
return true;
} else {
if (requests != 0) {
System.err.println("Unexpected TX server request during test. If a new test has been added, you may need to " +
System.err.println(requests + " unexpected TX server requests logged. If a new test has been added, you may need to " +
"rebuild the TX Cache for the test using the 'mvn test -D" + FHIR_TXCACHE_REBUILD + "=true' option");
return false;
} else {

View File

@ -137,7 +137,7 @@ public class NativeHostServices {
* @throws Exception
*/
public void init(String pack) throws Exception {
validator = new ValidationEngine(pack);
validator = new ValidationEngine.ValidationEngineBuilder().fromSource(pack);
validator.getContext().setAllowLoadingDuplicates(true);
igLoader = new IgLoader(validator.getPcm(), validator.getContext(), validator.getVersion(), validator.isDebug());
}

View File

@ -1,11 +1,9 @@
package org.hl7.fhir.validation;
import lombok.Getter;
import lombok.Setter;
import lombok.*;
import lombok.experimental.Accessors;
import org.fhir.ucum.UcumEssenceService;
import org.fhir.ucum.UcumException;
import org.hl7.fhir.convertors.factory.VersionConvertorFactory_10_50;
import org.hl7.fhir.convertors.factory.VersionConvertorFactory_14_50;
import org.hl7.fhir.convertors.factory.VersionConvertorFactory_30_50;
@ -183,60 +181,106 @@ public class ValidationEngine implements IValidatorResourceFetcher, IValidationP
*/
@Getter @Setter private Map<String, ValidationControl> validationControl = new HashMap<>();
public ValidationEngine() throws IOException {
setContext(SimpleWorkerContext.fromNothing());
initContext(null);
igLoader = new IgLoader(getPcm(), getContext(), getVersion(), isDebug());
private ValidationEngine() {
}
public ValidationEngine(String src) throws FHIRException, IOException {
loadCoreDefinitions(src, false, null);
igLoader = new IgLoader(getPcm(), getContext(), getVersion(), isDebug());
public static class ValidationEngineBuilder {
@With
private final String terminologyCachePath;
@With
private final String userAgent;
@With
private final String version;
//All three of these may be required to instantiate a txServer
private final String txServer;
private final String txLog;
private final FhirPublication txVersion;
@With
private final TimeTracker timeTracker;
@With
private final boolean canRunWithoutTerminologyServer;
public ValidationEngineBuilder() {
terminologyCachePath = null;
userAgent = null;
version = null;
txServer = null;
txLog = null;
txVersion = null;
timeTracker = null;
canRunWithoutTerminologyServer = false;
}
public ValidationEngineBuilder(String terminologyCachePath, String userAgent, String version, String txServer, String txLog, FhirPublication txVersion, TimeTracker timeTracker, boolean canRunWithoutTerminologyServer) {
this.terminologyCachePath = terminologyCachePath;
this.userAgent = userAgent;
this.version = version;
this.txServer = txServer;
this.txLog = txLog;
this.txVersion = txVersion;
this.timeTracker = timeTracker;
this.canRunWithoutTerminologyServer = canRunWithoutTerminologyServer;
}
public ValidationEngineBuilder withTxServer(String txServer, String txLog, FhirPublication txVersion) {
return new ValidationEngineBuilder(terminologyCachePath, userAgent, version, txServer, txLog, txVersion,timeTracker, canRunWithoutTerminologyServer);
}
public ValidationEngine fromNothing() throws IOException {
ValidationEngine engine = new ValidationEngine();
SimpleWorkerContext.SimpleWorkerContextBuilder contextBuilder = new SimpleWorkerContext.SimpleWorkerContextBuilder();
if (terminologyCachePath != null)
contextBuilder = contextBuilder.withTerminologyCachePath(terminologyCachePath);
engine.setContext(contextBuilder.build());
engine.initContext(timeTracker);
engine.setIgLoader(new IgLoader(engine.getPcm(), engine.getContext(), engine.getVersion(), engine.isDebug()));
return engine;
}
public ValidationEngine fromSource(String src) throws IOException, URISyntaxException {
ValidationEngine engine = new ValidationEngine();
engine.loadCoreDefinitions(src, false, terminologyCachePath, userAgent, timeTracker);
engine.getContext().setCanRunWithoutTerminology(canRunWithoutTerminologyServer);
if (txServer != null) {
engine.setTerminologyServer(txServer, txLog, txVersion);
}
engine.setVersion(version);
engine.setIgLoader(new IgLoader(engine.getPcm(), engine.getContext(), engine.getVersion(), engine.isDebug()));
return engine;
}
}
public ValidationEngine(String src, String txsrvr, String txLog, FhirPublication version, boolean canRunWithoutTerminologyServer, String vString, String userAgent) throws FHIRException, IOException, URISyntaxException {
this(src, txsrvr, txLog, null, version, canRunWithoutTerminologyServer, vString, userAgent);
}
public ValidationEngine(String src, String txsrvr, String txLog, String txCachePath, FhirPublication version, boolean canRunWithoutTerminologyServer, String vString, String userAgent) throws FHIRException, IOException, URISyntaxException {
loadCoreDefinitions(src, false, null);
getContext().setUserAgent(userAgent);
getContext().setCanRunWithoutTerminology(canRunWithoutTerminologyServer);
setTerminologyServer(txsrvr, txLog, txCachePath, version);
setVersion(vString);
igLoader = new IgLoader(getPcm(), getContext(), getVersion(), isDebug());
}
public ValidationEngine(String src, String txsrvr, String txLog, FhirPublication version, String vString, String userAgent) throws FHIRException, IOException, URISyntaxException {
this(src, txsrvr, txLog, null, version, vString, userAgent);
}
public ValidationEngine(String src, String txsrvr, String txLog, String txCachePath, FhirPublication version, String vString, String userAgent) throws FHIRException, IOException, URISyntaxException {
loadCoreDefinitions(src, false, null);
getContext().setUserAgent(userAgent);
setTerminologyServer(txsrvr, txLog, txCachePath, version);
setVersion(vString);
igLoader = new IgLoader(getPcm(), getContext(), getVersion(), isDebug());
}
public ValidationEngine(String src, String vString, TimeTracker tt, String userAgent) throws FHIRException, IOException, URISyntaxException {
loadCoreDefinitions(src, false, tt);
getContext().setUserAgent(userAgent);
setVersion(vString);
igLoader = new IgLoader(getPcm(), getContext(), getVersion(), isDebug());
}
private void loadCoreDefinitions(String src, boolean recursive, TimeTracker tt) throws FHIRException, IOException {
private void loadCoreDefinitions(String src, boolean recursive, String terminologyCachePath, String userAgent, TimeTracker tt) throws FHIRException, IOException {
NpmPackage npm = getPcm().loadPackage(src, null);
if (npm != null) {
version = npm.fhirVersion();
context = SimpleWorkerContext.fromPackage(npm, ValidatorUtils.loaderForVersion(version));
SimpleWorkerContext.SimpleWorkerContextBuilder contextBuilder = new SimpleWorkerContext.SimpleWorkerContextBuilder();
if (terminologyCachePath != null)
contextBuilder = contextBuilder.withTerminologyCachePath(terminologyCachePath);
if (userAgent != null) {
contextBuilder.withUserAgent(userAgent);
}
context = contextBuilder.fromPackage(npm, ValidatorUtils.loaderForVersion(version));
} else {
Map<String, byte[]> source = igLoader.loadIgSource(src, recursive, true);
if (version == null) {
version = getVersionFromPack(source);
}
context = SimpleWorkerContext.fromDefinitions(source, ValidatorUtils.loaderForVersion(version), new PackageVersion(src));
SimpleWorkerContext.SimpleWorkerContextBuilder contextBuilder = new SimpleWorkerContext.SimpleWorkerContextBuilder();
if (terminologyCachePath != null)
contextBuilder = contextBuilder.withTerminologyCachePath(terminologyCachePath);
if (userAgent != null) {
contextBuilder.withUserAgent(userAgent);
}
context = contextBuilder.fromDefinitions(source, ValidatorUtils.loaderForVersion(version), new PackageVersion(src));
ValidatorUtils.grabNatives(getBinaries(), source, "http://hl7.org/fhir");
}
// ucum-essence.xml should be in the class path. if it's not, ask about how to sort this out
@ -251,7 +295,7 @@ public class ValidationEngine implements IValidatorResourceFetcher, IValidationP
initContext(tt);
}
public void initContext(TimeTracker tt) throws IOException {
protected void initContext(TimeTracker tt) throws IOException {
context.setCanNoTS(true);
context.setCacheId(UUID.randomUUID().toString());
context.setAllowLoadingDuplicates(true); // because of Forge
@ -300,10 +344,6 @@ public class ValidationEngine implements IValidatorResourceFetcher, IValidationP
return "n/a: No Terminology Server";
} else {
try {
//FIXME this can fail for a different reason than connectToTSServer
if (txCachePath != null) {
context.initTS(txCachePath);
}
return context.connectToTSServer(TerminologyClientFactory.makeClient(url, context.getUserAgent(), version), log);
} catch (Exception e) {
if (context.isCanRunWithoutTerminology()) {
@ -710,12 +750,8 @@ public class ValidationEngine implements IValidatorResourceFetcher, IValidationP
throw new FHIRException("Source/Target version not supported: " + version + " -> " + targetVer);
}
public String setTerminologyServer(String src, String log, FhirPublication version) throws FHIRException, IOException, URISyntaxException {
return setTerminologyServer(src, log, null, version);
}
public String setTerminologyServer(String src, String log, String txCachePath, FhirPublication version) throws FHIRException, IOException, URISyntaxException {
return connectToTSServer(src, log, txCachePath, version);
public String setTerminologyServer(String src, String log, FhirPublication version) throws FHIRException, URISyntaxException, IOException {
return connectToTSServer(src, log, version);
}
public ValidationEngine setMapLog(String mapLog) throws FileNotFoundException {

View File

@ -91,7 +91,7 @@ public class ValidationService {
VersionSourceInformation versions = new VersionSourceInformation();
IgLoader igLoader = new IgLoader(
new FilesystemPackageCacheManager(true, ToolsVersion.TOOLS_VERSION),
SimpleWorkerContext.fromNothing(),
new SimpleWorkerContext.SimpleWorkerContextBuilder().fromNothing(),
null);
for (String src : cliContext.getIgs()) {
igLoader.scanForIgVersion(src, cliContext.isRecursive(), versions);
@ -317,7 +317,8 @@ public class ValidationService {
System.out.println("No such cached session exists for session id " + sessionId + ", re-instantiating validator.");
}
System.out.print(" Load FHIR v" + cliContext.getSv() + " from " + definitions);
ValidationEngine validator = new ValidationEngine(definitions, cliContext.getSv(), tt, "fhir/validator");
ValidationEngine validator = new ValidationEngine.ValidationEngineBuilder().withVersion(cliContext.getSv()).withTimeTracker(tt).withUserAgent("fhir/validator").fromSource(definitions);
sessionId = sessionCache.cacheSession(validator);
FhirPublication ver = FhirPublication.fromCode(cliContext.getSv());
@ -325,7 +326,7 @@ public class ValidationService {
System.out.println(" - " + validator.getContext().countAllCaches() + " resources (" + tt.milestone() + ")");
igLoader.loadIg(validator.getIgs(), validator.getBinaries(), "hl7.terminology", false);
System.out.print(" Terminology server " + cliContext.getTxServer());
String txver = validator.setTerminologyServer(cliContext.getTxServer(), cliContext.getTxLog(), cliContext.getTxCache(), ver);
String txver = validator.setTerminologyServer(cliContext.getTxServer(), cliContext.getTxLog(), ver);
System.out.println(" - Version " + txver + " (" + tt.milestone() + ")");
validator.setDebug(cliContext.isDoDebug());
for (String src : cliContext.getIgs()) {

View File

@ -87,7 +87,7 @@ public class Common {
public static ValidationEngine getValidationEngine(String version, String txServer, String definitions, String txLog, TimeTracker tt) throws Exception {
System.out.println("Loading (v = " + version + ", tx server -> " + txServer + ")");
ValidationEngine ve = new ValidationEngine(definitions, version, tt, "fhir/validator");
ValidationEngine ve = new ValidationEngine.ValidationEngineBuilder().withVersion(version).withTimeTracker(tt).withUserAgent("fhir/validator").fromSource(definitions);
ve.connectToTSServer(txServer, txLog, FhirPublication.fromCode(version));
return ve;
}

View File

@ -56,7 +56,7 @@ public class FHIRMappingLanguageTests {
@BeforeAll
public static void setUp() throws Exception {
validationEngine = new ValidationEngine("hl7.fhir.r4.core#4.0.1");
validationEngine = new ValidationEngine.ValidationEngineBuilder().fromSource("hl7.fhir.r4.core#4.0.1");
context = validationEngine.getContext();
context.loadFromFile(TestingUtilities.loadTestResourceStream("validator", "cda", "any.xml"), "any.xml", null);
context.loadFromFile(TestingUtilities.loadTestResourceStream("validator", "cda", "ii.xml"), "ii.xml", null);

View File

@ -16,7 +16,7 @@ class SessionCacheTest {
void expiredSession() throws IOException, InterruptedException {
final long EXPIRE_TIME = 5L;
SessionCache cache = new SessionCache(EXPIRE_TIME, TimeUnit.SECONDS);
ValidationEngine testEngine = new ValidationEngine();
ValidationEngine testEngine = new ValidationEngine.ValidationEngineBuilder().fromNothing();
String sessionId = cache.cacheSession(testEngine);
TimeUnit.SECONDS.sleep(EXPIRE_TIME + 1L);
Assertions.assertNull(cache.fetchSessionValidatorEngine(sessionId));
@ -27,7 +27,7 @@ class SessionCacheTest {
void cachedSession() throws IOException {
final long EXPIRE_TIME = 5L;
SessionCache cache = new SessionCache(EXPIRE_TIME, TimeUnit.SECONDS);
ValidationEngine testEngine = new ValidationEngine();
ValidationEngine testEngine = new ValidationEngine.ValidationEngineBuilder().fromNothing();
String sessionId = cache.cacheSession(testEngine);
Assertions.assertEquals(testEngine, cache.fetchSessionValidatorEngine(sessionId));
}
@ -36,7 +36,7 @@ class SessionCacheTest {
@DisplayName("test session exists")
void sessionExists() throws IOException {
SessionCache cache = new SessionCache();
ValidationEngine testEngine = new ValidationEngine();
ValidationEngine testEngine = new ValidationEngine.ValidationEngineBuilder().fromNothing();
String sessionId = cache.cacheSession(testEngine);
Assertions.assertTrue(cache.sessionExists(sessionId));
Assertions.assertFalse(cache.sessionExists(UUID.randomUUID().toString()));

View File

@ -21,7 +21,7 @@ public class LoadIgTests {
final String fhirSpecVersion = "4.0";
final String definitions = VersionUtilities.packageForVersion(fhirSpecVersion) + "#" + VersionUtilities.getCurrentVersion(fhirSpecVersion);
ValidationEngine hl7Validator = new ValidationEngine(definitions);
ValidationEngine hl7Validator = new ValidationEngine.ValidationEngineBuilder().fromSource(definitions);
hl7Validator.setDoNative(false);
hl7Validator.setAnyExtensionsAllowed(true);
hl7Validator.prepare();
@ -52,7 +52,7 @@ public class LoadIgTests {
final String fhirSpecVersion = "4.0";
final String definitions = VersionUtilities.packageForVersion(fhirSpecVersion) + "#" + VersionUtilities.getCurrentVersion(fhirSpecVersion);
ValidationEngine hl7Validator = new ValidationEngine(definitions);
ValidationEngine hl7Validator = new ValidationEngine.ValidationEngineBuilder().fromSource(definitions);
hl7Validator.setDoNative(false);
hl7Validator.setAnyExtensionsAllowed(true);
hl7Validator.prepare();

View File

@ -30,7 +30,7 @@ public class ValidationEngineTests {
public void testCurrentXml() throws Exception {
if (!TestUtilities.silent)
System.out.println("TestCurrentXml: Validate patient-example.xml in Current version");
ValidationEngine ve = TestUtilities.getValidationEngine("hl7.fhir.r4.core#4.0.1", DEF_TX, null, FhirPublication.R4, "4.0.1", "fhir/test-cases");
ValidationEngine ve = TestUtilities.getValidationEngine("hl7.fhir.r4.core#4.0.1", DEF_TX, FhirPublication.R4, "4.0.1");
CacheVerificationLogger logger = new CacheVerificationLogger();
ve.getContext().getTxClient().setLogger(logger);
OperationOutcome op = ve.validate(FhirFormat.XML, TestingUtilities.loadTestResourceStream("validator", "patient-example.xml"), null);
@ -53,7 +53,7 @@ public class ValidationEngineTests {
public void testCurrentJson() throws Exception {
if (!TestUtilities.silent)
System.out.println("TestCurrentJson: Validate patient-example.json in Current version");
ValidationEngine ve = TestUtilities.getValidationEngine("hl7.fhir.r4.core#4.0.1", DEF_TX, null, FhirPublication.R4, "4.0.1", "fhir/test-cases");
ValidationEngine ve = TestUtilities.getValidationEngine("hl7.fhir.r4.core#4.0.1", DEF_TX, FhirPublication.R4, "4.0.1");
CacheVerificationLogger logger = new CacheVerificationLogger();
ve.getContext().getTxClient().setLogger(logger);
OperationOutcome op = ve.validate(FhirFormat.JSON, TestingUtilities.loadTestResourceStream("validator", "patient-example.json"), null);
@ -76,7 +76,7 @@ public class ValidationEngineTests {
}
if (!TestUtilities.silent)
System.out.println("Test140: Validate patient-example.xml in v1.4.0 version");
ValidationEngine ve = TestUtilities.getValidationEngine("hl7.fhir.r2b.core#1.4.0", DEF_TX, null, FhirPublication.DSTU2016May, "1.4.0", "fhir/test-cases");
ValidationEngine ve = TestUtilities.getValidationEngine("hl7.fhir.r2b.core#1.4.0", DEF_TX, FhirPublication.DSTU2016May, "1.4.0");
CacheVerificationLogger logger = new CacheVerificationLogger();
ve.getContext().getTxClient().setLogger(logger);
OperationOutcome op = ve.validate(FhirFormat.XML, TestingUtilities.loadTestResourceStream("validator", "patient140.xml"), null);
@ -103,7 +103,7 @@ public class ValidationEngineTests {
}
if (!org.hl7.fhir.validation.tests.utilities.TestUtilities.silent)
System.out.println("Test102: Validate patient-example.xml in v1.0.2 version");
ValidationEngine ve = TestUtilities.getValidationEngine("hl7.fhir.r2.core#1.0.2", DEF_TX, null, FhirPublication.DSTU2, "1.0.2", "fhir/test-cases");
ValidationEngine ve = TestUtilities.getValidationEngine("hl7.fhir.r2.core#1.0.2", DEF_TX, FhirPublication.DSTU2, "1.0.2");
ve.setNoInvariantChecks(true);
CacheVerificationLogger logger = new CacheVerificationLogger();
ve.getContext().getTxClient().setLogger(logger);
@ -131,7 +131,7 @@ public class ValidationEngineTests {
}
if (!TestUtilities.silent)
System.out.println("TestObs102: Validate patient-example.xml in v1.0.2 version");
ValidationEngine ve = TestUtilities.getValidationEngine("hl7.fhir.r2.core#1.0.2", DEF_TX, null, FhirPublication.DSTU2, "1.0.2", "fhir/test-cases");
ValidationEngine ve = TestUtilities.getValidationEngine("hl7.fhir.r2.core#1.0.2", DEF_TX, FhirPublication.DSTU2, "1.0.2");
ve.setNoInvariantChecks(true);
CacheVerificationLogger logger = new CacheVerificationLogger();
ve.getContext().getTxClient().setLogger(logger);
@ -156,7 +156,7 @@ public class ValidationEngineTests {
public void test301() throws Exception {
if (!TestUtilities.silent)
System.out.println("Test301: Validate observation301.xml against Core");
ValidationEngine ve = TestUtilities.getValidationEngine("hl7.fhir.r3.core#3.0.2", DEF_TX, null, FhirPublication.STU3, "3.0.2", "fhir/test-cases");
ValidationEngine ve = TestUtilities.getValidationEngine("hl7.fhir.r3.core#3.0.2", DEF_TX, FhirPublication.STU3, "3.0.2");
CacheVerificationLogger logger = new CacheVerificationLogger();
ve.getContext().getTxClient().setLogger(logger);
if (!TestUtilities.silent)
@ -178,7 +178,7 @@ public class ValidationEngineTests {
public void test301USCore() throws Exception {
if (!TestUtilities.silent)
System.out.println("Test301USCore: Validate patient300.xml against US-Core");
ValidationEngine ve = TestUtilities.getValidationEngine("hl7.fhir.r3.core#3.0.2", DEF_TX, null, FhirPublication.STU3, "3.0.2", "fhir/test-cases");
ValidationEngine ve = TestUtilities.getValidationEngine("hl7.fhir.r3.core#3.0.2", DEF_TX, FhirPublication.STU3, "3.0.2");
CacheVerificationLogger logger = new CacheVerificationLogger();
ve.getContext().getTxClient().setLogger(logger);
IgLoader igLoader = new IgLoader(ve.getPcm(), ve.getContext(), ve.getVersion(), true);

View File

@ -78,7 +78,6 @@ import com.google.gson.JsonArray;
import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
import static org.junit.jupiter.api.Assertions.assertTrue;
@RunWith(Parameterized.class)
public class ValidationTests implements IEvaluationContext, IValidatorResourceFetcher, IValidationPolicyAdvisor {
@ -145,17 +144,17 @@ public class ValidationTests implements IEvaluationContext, IValidatorResourceFe
version = VersionUtilities.getMajMin(version);
if (!ve.containsKey(version)) {
if (version.startsWith("5.0"))
ve.put(version, TestUtilities.getValidationEngine("hl7.fhir.r5.core#4.5.0", ValidationEngineTests.DEF_TX, txLog, FhirPublication.R5, true, "4.5.0", "fhir/test-cases"));
ve.put(version, TestUtilities.getValidationEngine("hl7.fhir.r5.core#4.5.0", ValidationEngineTests.DEF_TX, txLog, FhirPublication.R5, true, "4.5.0"));
else if (version.startsWith("4.3"))
ve.put(version, TestUtilities.getValidationEngine("hl7.fhir.r4b.core#4.3.0", ValidationEngineTests.DEF_TX, txLog, FhirPublication.R4B, true, "4.3.0", "fhir/test-cases"));
ve.put(version, TestUtilities.getValidationEngine("hl7.fhir.r4b.core#4.3.0", ValidationEngineTests.DEF_TX, txLog, FhirPublication.R4B, true, "4.3.0"));
else if (version.startsWith("4.0"))
ve.put(version, TestUtilities.getValidationEngine("hl7.fhir.r4.core#4.0.1", ValidationEngineTests.DEF_TX, txLog, FhirPublication.R4, true, "4.0.1", "fhir/test-cases"));
ve.put(version, TestUtilities.getValidationEngine("hl7.fhir.r4.core#4.0.1", ValidationEngineTests.DEF_TX, txLog, FhirPublication.R4, true, "4.0.1"));
else if (version.startsWith("3.0"))
ve.put(version, TestUtilities.getValidationEngine("hl7.fhir.r3.core#3.0.2", ValidationEngineTests.DEF_TX, txLog, FhirPublication.STU3, true, "3.0.2", "fhir/test-cases"));
ve.put(version, TestUtilities.getValidationEngine("hl7.fhir.r3.core#3.0.2", ValidationEngineTests.DEF_TX, txLog, FhirPublication.STU3, true, "3.0.2"));
else if (version.startsWith("1.4"))
ve.put(version, TestUtilities.getValidationEngine("hl7.fhir.r2b.core#1.4.0", ValidationEngineTests.DEF_TX, txLog, FhirPublication.DSTU2016May, true, "1.4.0", "fhir/test-cases"));
ve.put(version, TestUtilities.getValidationEngine("hl7.fhir.r2b.core#1.4.0", ValidationEngineTests.DEF_TX, txLog, FhirPublication.DSTU2016May, true, "1.4.0"));
else if (version.startsWith("1.0"))
ve.put(version, TestUtilities.getValidationEngine("hl7.fhir.r2.core#1.0.2", ValidationEngineTests.DEF_TX, txLog, FhirPublication.DSTU2, true, "1.0.2", "fhir/test-cases"));
ve.put(version, TestUtilities.getValidationEngine("hl7.fhir.r2.core#1.0.2", ValidationEngineTests.DEF_TX, txLog, FhirPublication.DSTU2, true, "1.0.2"));
else
throw new Exception("unknown version " + version);
}

View File

@ -6,4 +6,6 @@ public class TestConstants {
public static final java.lang.String TX_CACHE = Paths.get("src","test","resources", "txCache").toAbsolutePath().toString();
public static final java.lang.String TX_CACHE_LOG = Paths.get(System.getProperty("user.dir"), "tx.log.html").toAbsolutePath().toString();
public static final String USER_AGENT = "fhir/test-cases";
}

View File

@ -9,23 +9,30 @@ import java.nio.file.Paths;
public class TestUtilities {
public static boolean silent = false;
// public static String resourceNameToFile(String name) throws IOException {
// return org.hl7.fhir.utilities.Utilities.path(System.getProperty("user.dir"), "src", "test", "resources", name);
// }
public static final ValidationEngine getValidationEngine(java.lang.String src, java.lang.String txsrvr, java.lang.String txLog, FhirPublication version, boolean canRunWithoutTerminologyServer, java.lang.String vString, java.lang.String userAgent) throws Exception {
txLog = TestConstants.TX_CACHE_LOG;
final ValidationEngine validationEngine = new ValidationEngine(src, txsrvr, txLog, Paths.get(TestConstants.TX_CACHE, vString).toString(), version, canRunWithoutTerminologyServer, vString, userAgent);
public static ValidationEngine getValidationEngine(java.lang.String src, java.lang.String txServer, String txLog, FhirPublication version, boolean canRunWithoutTerminologyServer, java.lang.String vString) throws Exception {
final ValidationEngine validationEngine = new ValidationEngine.ValidationEngineBuilder()
.withCanRunWithoutTerminologyServer(canRunWithoutTerminologyServer)
.withVersion(vString)
.withUserAgent(TestConstants.USER_AGENT)
.withTerminologyCachePath(Paths.get(TestConstants.TX_CACHE, vString).toString())
.withTxServer(txServer, txLog, version)
.fromSource(src);
TerminologyCache.setCacheErrors(true);
validationEngine.getContext().setUserAgent("fhir/test-cases");
return validationEngine;
}
public static ValidationEngine getValidationEngine(java.lang.String src, java.lang.String txsrvr, java.lang.String txLog, FhirPublication version, java.lang.String vString, java.lang.String userAgent) throws Exception {
txLog = TestConstants.TX_CACHE_LOG;
final ValidationEngine validationEngine = new ValidationEngine(src, txsrvr, txLog, Paths.get(TestConstants.TX_CACHE, vString).toString(), version, vString, userAgent);
public static ValidationEngine getValidationEngine(java.lang.String src, java.lang.String txServer, FhirPublication version, java.lang.String vString) throws Exception {
final ValidationEngine validationEngine = new ValidationEngine.ValidationEngineBuilder()
.withVersion(vString)
.withUserAgent(TestConstants.USER_AGENT)
.withTerminologyCachePath(Paths.get(TestConstants.TX_CACHE, vString).toString())
.withTxServer(txServer, TestConstants.TX_CACHE_LOG, version)
.fromSource(src);
TerminologyCache.setCacheErrors(true);
validationEngine.getContext().setUserAgent("fhir/test-cases");
return validationEngine;
}
}

View File

@ -1,18 +0,0 @@
-------------------------------------------------------------------------------------
{"hierarchical" : false, "valueSet" :{
"resourceType" : "ValueSet",
"compose" : {
"include" : [{
"system" : "urn:iso:std:iso:4217"
}]
}
}}####
e: {
"error" : "java.lang.NullPointerException"
}
-------------------------------------------------------------------------------------
{"hierarchical" : false, "url": "http://hl7.org/fhir/ValueSet/currencies", "version": "4.0.1"}####
e: {
"error" : "java.lang.NullPointerException"
}
-------------------------------------------------------------------------------------

View File

@ -1,11 +0,0 @@
-------------------------------------------------------------------------------------
{"code" : {
"system" : "urn:ietf:bcp:47",
"code" : "fr-CA"
}, "valueSet" :null, "lang":"en-US", "useServer":"true", "useClient":"true", "guessSystem":"false", "valueSetMode":"ALL_CHECKS", "versionFlexible":"true"}####
v: {
"severity" : "error",
"error" : "Attempt to use Terminology server when no Terminology server is available",
"class" : "SERVER_ERROR"
}
-------------------------------------------------------------------------------------

View File

@ -1,18 +0,0 @@
-------------------------------------------------------------------------------------
{"hierarchical" : false, "valueSet" :{
"resourceType" : "ValueSet",
"compose" : {
"include" : [{
"system" : "urn:ietf:bcp:13"
}]
}
}}####
e: {
"error" : "java.lang.NullPointerException"
}
-------------------------------------------------------------------------------------
{"hierarchical" : false, "url": "http://hl7.org/fhir/ValueSet/mimetypes", "version": "4.0.1"}####
e: {
"error" : "java.lang.NullPointerException"
}
-------------------------------------------------------------------------------------

View File

@ -1,62 +0,0 @@
{
"resourceType" : "CapabilityStatement",
"id" : "FhirServer",
"meta" : {
"tag" : [{
"system" : "http://hl7.org/fhir/v3/ObservationValue",
"code" : "SUBSETTED",
"display" : "Subsetted"
}]
},
"url" : "http://fhir.healthintersections.com.au/open/metadata",
"version" : "4.0.1-2.0.12-SNAPSHOT",
"name" : "FHIR Reference Server Conformance Statement",
"status" : "active",
"date" : "2022-01-10T11:07:19.254Z",
"contact" : [{
"telecom" : [{
"system" : "other",
"value" : "http://healthintersections.com.au/"
}]
}],
"kind" : "instance",
"instantiates" : ["http://hl7.org/fhir/CapabilityStatement/terminology-server"],
"software" : {
"name" : "Reference Server",
"version" : "2.0.12-SNAPSHOT",
"releaseDate" : "2021-12-20T02:28:03.769Z"
},
"fhirVersion" : "4.0.1",
"format" : ["application/fhir+xml",
"application/fhir+json"],
"rest" : [{
"mode" : "server",
"security" : {
"cors" : true
},
"operation" : [{
"name" : "expand",
"definition" : "http://hl7.org/fhir/OperationDefinition/ValueSet-expand"
},
{
"name" : "lookup",
"definition" : "http://hl7.org/fhir/OperationDefinition/ValueSet-lookup"
},
{
"name" : "validate-code",
"definition" : "http://hl7.org/fhir/OperationDefinition/Resource-validate"
},
{
"name" : "translate",
"definition" : "http://hl7.org/fhir/OperationDefinition/ConceptMap-translate"
},
{
"name" : "closure",
"definition" : "http://hl7.org/fhir/OperationDefinition/ConceptMap-closure"
},
{
"name" : "versions",
"definition" : "/OperationDefinition/fso-versions"
}]
}]
}

View File

@ -1,102 +0,0 @@
-------------------------------------------------------------------------------------
{"hierarchical" : false, "valueSet" :{
"resourceType" : "ValueSet",
"compose" : {
"include" : [{
"system" : "http://unitsofmeasure.org",
"concept" : [{
"extension" : [{
"url" : "http://hl7.org/fhir/StructureDefinition/valueset-concept-definition",
"valueString" : "second"
}],
"code" : "s",
"display" : "second",
"designation" : [{
"language" : "zh",
"value" : "秒"
}]
},
{
"extension" : [{
"url" : "http://hl7.org/fhir/StructureDefinition/valueset-concept-definition",
"valueString" : "minute"
}],
"code" : "min",
"display" : "minute",
"designation" : [{
"language" : "zh",
"value" : "分钟"
}]
},
{
"extension" : [{
"url" : "http://hl7.org/fhir/StructureDefinition/valueset-concept-definition",
"valueString" : "hour"
}],
"code" : "h",
"display" : "hour",
"designation" : [{
"language" : "zh",
"value" : "小时"
}]
},
{
"extension" : [{
"url" : "http://hl7.org/fhir/StructureDefinition/valueset-concept-definition",
"valueString" : "day"
}],
"code" : "d",
"display" : "day",
"designation" : [{
"language" : "zh",
"value" : "天"
}]
},
{
"extension" : [{
"url" : "http://hl7.org/fhir/StructureDefinition/valueset-concept-definition",
"valueString" : "week"
}],
"code" : "wk",
"display" : "week",
"designation" : [{
"language" : "zh",
"value" : "星期"
}]
},
{
"extension" : [{
"url" : "http://hl7.org/fhir/StructureDefinition/valueset-concept-definition",
"valueString" : "month"
}],
"code" : "mo",
"display" : "month",
"designation" : [{
"language" : "zh",
"value" : "月"
}]
},
{
"extension" : [{
"url" : "http://hl7.org/fhir/StructureDefinition/valueset-concept-definition",
"valueString" : "year"
}],
"code" : "a",
"display" : "year",
"designation" : [{
"language" : "zh",
"value" : "年"
}]
}]
}]
}
}}####
e: {
"error" : "java.lang.NullPointerException"
}
-------------------------------------------------------------------------------------
{"hierarchical" : false, "url": "http://hl7.org/fhir/ValueSet/units-of-time", "version": "4.0.1"}####
e: {
"error" : "java.lang.NullPointerException"
}
-------------------------------------------------------------------------------------

View File

@ -1,62 +0,0 @@
{
"resourceType" : "CapabilityStatement",
"id" : "FhirServer",
"meta" : {
"tag" : [{
"system" : "http://hl7.org/fhir/v3/ObservationValue",
"code" : "SUBSETTED",
"display" : "Subsetted"
}]
},
"url" : "http://fhir.healthintersections.com.au/open/metadata",
"version" : "4.0.1-2.0.12-SNAPSHOT",
"name" : "FHIR Reference Server Conformance Statement",
"status" : "active",
"date" : "2022-01-10T11:07:19.254Z",
"contact" : [{
"telecom" : [{
"system" : "other",
"value" : "http://healthintersections.com.au/"
}]
}],
"kind" : "instance",
"instantiates" : ["http://hl7.org/fhir/CapabilityStatement/terminology-server"],
"software" : {
"name" : "Reference Server",
"version" : "2.0.12-SNAPSHOT",
"releaseDate" : "2021-12-20T02:28:03.769Z"
},
"fhirVersion" : "4.0.1",
"format" : ["application/fhir+xml",
"application/fhir+json"],
"rest" : [{
"mode" : "server",
"security" : {
"cors" : true
},
"operation" : [{
"name" : "expand",
"definition" : "http://hl7.org/fhir/OperationDefinition/ValueSet-expand"
},
{
"name" : "lookup",
"definition" : "http://hl7.org/fhir/OperationDefinition/ValueSet-lookup"
},
{
"name" : "validate-code",
"definition" : "http://hl7.org/fhir/OperationDefinition/Resource-validate"
},
{
"name" : "translate",
"definition" : "http://hl7.org/fhir/OperationDefinition/ConceptMap-translate"
},
{
"name" : "closure",
"definition" : "http://hl7.org/fhir/OperationDefinition/ConceptMap-closure"
},
{
"name" : "versions",
"definition" : "/OperationDefinition/fso-versions"
}]
}]
}