Fix bug in unknown URL handling that could cause significant delays in validation (>1min / unknown URL)

This commit is contained in:
Grahame Grieve 2020-11-13 14:36:10 +11:00
parent e85f66fddb
commit 8c0523f3fa
3 changed files with 50 additions and 18 deletions

View File

@ -41,6 +41,7 @@ import org.hl7.fhir.utilities.TextFile;
import org.hl7.fhir.utilities.Utilities;
import org.hl7.fhir.utilities.VersionUtilities;
import org.hl7.fhir.utilities.json.JSONUtil;
import org.hl7.fhir.utilities.json.JsonTrackingParser;
import org.hl7.fhir.utilities.npm.NpmPackage.NpmPackageFolder;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
@ -549,7 +550,9 @@ public class FilesystemPackageCacheManager extends BasePackageCacheManager imple
@Override
public String getPackageId(String canonicalUrl) throws IOException {
String retVal = super.getPackageId(canonicalUrl);
String retVal = findCanonicalInLocalCache(canonicalUrl);
retVal = super.getPackageId(canonicalUrl);
if (retVal == null) {
retVal = getPackageIdFromBuildList(canonicalUrl);
@ -559,6 +562,21 @@ public class FilesystemPackageCacheManager extends BasePackageCacheManager imple
}
public String findCanonicalInLocalCache(String canonicalUrl) {
try {
for (String pf : listPackages()) {
if (new File(Utilities.path(cacheFolder, pf, "package", "package.json")).exists()) {
JsonObject npm = JsonTrackingParser.parseJsonFile(Utilities.path(cacheFolder, pf, "package", "package.json"));
if (canonicalUrl.equals(JSONUtil.str(npm, "canonical"))) {
return JSONUtil.str(npm, "name");
}
}
}
} catch (IOException e) {
}
return null;
}
// ========================= Package Mgmt API =======================================================================
private String getPackageIdFromBuildList(String canonical) throws IOException {

View File

@ -25,7 +25,7 @@ public class StandAloneValidatorFetcher implements IValidatorResourceFetcher {
void loadPackage(String id, String ver) throws IOException, FHIRException;
}
private BasePackageCacheManager pcm;
private FilesystemPackageCacheManager pcm;
private IWorkerContext context;
private IPackageInstaller installer;
@ -51,19 +51,37 @@ public class StandAloneValidatorFetcher implements IValidatorResourceFetcher {
if (!Utilities.isAbsoluteUrl(url)) {
return false;
}
// if we've got to here, it's a reference to a FHIR URL. We're going to try to resolve it on the fly
// first possibility: it's a reference to a version specific URL http://hl7.org/fhir/X.X/...
VersionURLInfo vu = VersionUtilities.parseVersionUrl(url);
if (vu != null) {
NpmPackage pi = pcm.loadPackage(VersionUtilities.packageForVersion(vu.getVersion()), VersionUtilities.getCurrentVersion(vu.getVersion()));
return pi.hasCanonical(vu.getUrl());
// if we've got to here, it's a reference to a FHIR URL. We're going to try to resolve it on the fly
String pid = null;
String ver = null;
String base = findBaseUrl(url);
if (base == null) {
return false;
}
if (base.equals("http://terminology.hl7.org")) {
pid = "hl7.terminology";
} else if (url.startsWith("http://hl7.org/fhir")) {
pid = pcm.getPackageId(base);
} else {
pid = pcm.findCanonicalInLocalCache(base);
}
ver = url.contains("|") ? url.substring(url.indexOf("|")+1) : null;
if (pid == null) {
return false;
}
if (url.startsWith("http://hl7.org/fhir")) {
// first possibility: it's a reference to a version specific URL http://hl7.org/fhir/X.X/...
VersionURLInfo vu = VersionUtilities.parseVersionUrl(url);
if (vu != null) {
NpmPackage pi = pcm.loadPackage(VersionUtilities.packageForVersion(vu.getVersion()), VersionUtilities.getCurrentVersion(vu.getVersion()));
return pi.hasCanonical(vu.getUrl());
}
}
// ok maybe it's a reference to a package we know
String base = findBaseUrl(url);
String pid = pcm.getPackageId(base);
String ver = url.contains("|") ? url.substring(url.indexOf("|")+1) : null;
if (pid != null) {
if (installer.packageExists(pid, ver)) {
installer.loadPackage(pid, ver);
@ -72,13 +90,8 @@ public class StandAloneValidatorFetcher implements IValidatorResourceFetcher {
}
}
if (!url.startsWith("http://hl7.org/fhir")) {
return true; // we don't bother with those in the standalone validator - we assume they are valid
}
// we assume it's invalid at this point
return false;
// we don't bother with urls outside fhir space in the standalone validator - we assume they are valid
return !url.startsWith("http://hl7.org/fhir");
}
private String findBaseUrl(String url) {

View File

@ -209,6 +209,7 @@ public class ValidationService {
FhirPublication ver = FhirPublication.fromCode(cliContext.getSv());
ValidationEngine validator = new ValidationEngine(definitions, ver, cliContext.getSv(), tt);
System.out.println(" - "+validator.getContext().countAllCaches()+" resources ("+tt.milestone()+")");
validator.loadIg("hl7.terminology", false);
System.out.print(" Terminology server " + cliContext.getTxServer());
String txver = validator.setTerminologyServer(cliContext.getTxServer(), cliContext.getTxLog(), ver);
System.out.println(" - Version "+txver+" ("+tt.milestone()+")");