Merge pull request #1805 from hapifhir/do-20241111-server-auth-per-type

Use server type to select server settings in combination with URL
This commit is contained in:
Grahame Grieve 2024-11-12 12:14:03 +10:30 committed by GitHub
commit 097f493099
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
33 changed files with 233 additions and 244 deletions

View File

@ -3,12 +3,7 @@ package org.hl7.fhir.convertors.analytics;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.*;
import javax.xml.parsers.ParserConfigurationException;
@ -241,7 +236,7 @@ public class PackageVisitor {
File co = ManagedFileAccess.file(Utilities.path(cache, pid+"."+manifest.asString("date")+".tgz"));
if (!co.exists()) {
HTTPResult res = ManagedWebAccess.get(repo+"/package.tgz?nocache=" + System.currentTimeMillis());
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), repo+"/package.tgz?nocache=" + System.currentTimeMillis());
res.checkThrowException();
TextFile.bytesToFile(res.getContent(), co);
}
@ -338,7 +333,7 @@ public class PackageVisitor {
System.out.println("Feed "+str);
try {
HTTPResult res = ManagedWebAccess.get(str+"?nocache=" + System.currentTimeMillis());
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), str+"?nocache=" + System.currentTimeMillis());
res.checkThrowException();
Document xml = XMLUtil.parseToDom(res.getContent());
for (Element channel : XMLUtil.getNamedChildren(xml.getDocumentElement(), "channel")) {

View File

@ -4,6 +4,7 @@ import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import javax.xml.parsers.DocumentBuilder;
@ -126,7 +127,7 @@ public class CKMImporter {
private Document loadXml(String address) throws Exception {
HTTPResult res = ManagedWebAccess.get(address, "application/xml");
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), address, "application/xml");
res.checkThrowException();
InputStream xml = new ByteArrayInputStream(res.getContent());

View File

@ -1,6 +1,7 @@
package org.hl7.fhir.convertors.misc;
import java.io.IOException;
import java.util.Arrays;
import java.util.Date;
import java.util.HashSet;
import java.util.Set;
@ -394,7 +395,7 @@ public class ICD11Generator {
private JsonObject fetchJson(String source) throws IOException {
HTTPResult res = ManagedWebAccess.accessor().withHeader("API-Version", "v2").withHeader("Accept-Language", "en").get(source,"application/json");
HTTPResult res = ManagedWebAccess.accessor(Arrays.asList("web")).withHeader("API-Version", "v2").withHeader("Accept-Language", "en").get(source,"application/json");
res.checkThrowException();
return JsonParser.parseObject(res.getContent());
}

View File

@ -31,12 +31,7 @@ package org.hl7.fhir.r4.conformance;
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.*;
import org.hl7.fhir.exceptions.DefinitionException;
import org.hl7.fhir.exceptions.FHIRFormatError;
@ -1384,7 +1379,7 @@ public class ProfileComparer {
if (f.exists())
return TextFile.fileToString(f);
HTTPResult res = ManagedWebAccess.get(source);
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), source);
res.checkThrowException();
String result = TextFile.bytesToString(res.getContent());
TextFile.stringToFile(result, f);

View File

@ -9,6 +9,7 @@ import java.io.OutputStream;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.Arrays;
import java.util.Date;
import java.util.zip.ZipEntry;
import java.util.zip.ZipInputStream;
@ -79,7 +80,7 @@ public class TerminologyCacheManager {
try {
System.out.println("Initialise terminology cache from " + source);
HTTPResult res = ManagedWebAccess.get(source + "?nocache=" + System.currentTimeMillis());
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), source + "?nocache=" + System.currentTimeMillis());
res.checkThrowException();
unzip(new ByteArrayInputStream(res.getContent()), cacheFolder);
} catch (Exception e) {
@ -148,7 +149,7 @@ public class TerminologyCacheManager {
String url = "https://tx.fhir.org/post/tx-cache/" + ghOrg + "/" + ghRepo + "/" + ghBranch + ".zip";
System.out.println("Sending tx-cache to " + url + " (" + Utilities.describeSize(bs.toByteArray().length) + ")");
HTTPResult res = ManagedWebAccess.accessor()
HTTPResult res = ManagedWebAccess.accessor(Arrays.asList("web"))
.withBasicAuth(token.substring(0, token.indexOf(':')), token.substring(token.indexOf(':') + 1))
.put(url, bs.toByteArray(), null, "application/zip");
if (res.getCode() >= 300) {

View File

@ -29,6 +29,9 @@ import org.hl7.fhir.r5.formats.IParser.OutputStyle;
import org.hl7.fhir.utilities.TextFile;
import org.hl7.fhir.utilities.Utilities;
import org.hl7.fhir.utilities.VersionUtilities;
import org.hl7.fhir.utilities.http.HTTPRequest;
import org.hl7.fhir.utilities.http.HTTPResult;
import org.hl7.fhir.utilities.http.ManagedWebAccess;
import org.hl7.fhir.utilities.json.JsonException;
import org.hl7.fhir.utilities.json.model.JsonArray;
import org.hl7.fhir.utilities.json.model.JsonElement;
@ -428,6 +431,20 @@ public class SHCParser extends ParserBase {
private String getVCIIssuer(List<ValidationMessage> errors, String issuer) {
try {
JsonObject vci = org.hl7.fhir.utilities.json.parser.JsonParser.parseObjectFromUrl("https://raw.githubusercontent.com/the-commons-project/vci-directory/main/vci-issuers.json");
/* HTTPResult httpResult = ManagedWebAccess.httpCall(
new HTTPRequest().withMethod(HTTPVerb.GET).withUrl(new URL("https://raw.githubusercontent.com/the-commons-project/vci-directory/main/vci-issuers.json"))
new URL("https://raw.githubusercontent.com/the-commons-project/vci-directory/main/vci-issuers.json")
HTTPRequest.HttpMethod.GET,
null,
null,
null
)
)
*/
//JsonObject vci = org.hl7.fhir.utilities.json.parser.JsonParser.parseObject();
for (JsonObject j : vci.getJsonObjects("participating_issuers")) {
if (issuer.equals(j.asString("iss"))) {
return j.asString("name");

View File

@ -287,7 +287,7 @@ public class SHLParser extends ParserBase {
private HTTPResult fetchFile(String url, String ct) throws IOException {
HTTPResult res = ManagedWebAccess.get(url, ct);
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), url, ct);
res.checkThrowException();
return res;
}
@ -299,7 +299,7 @@ public class SHLParser extends ParserBase {
JsonObject j = new JsonObject();
j.add("recipient", "FHIR Validator");
HTTPResult res = ManagedWebAccess.post(url, org.hl7.fhir.utilities.json.parser.JsonParser.composeBytes(j), "application/json", "application/json");
HTTPResult res = ManagedWebAccess.post(Arrays.asList("web"), url, org.hl7.fhir.utilities.json.parser.JsonParser.composeBytes(j), "application/json", "application/json");
res.checkThrowException();
return res;
}

View File

@ -9,6 +9,7 @@ import java.io.OutputStream;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.Arrays;
import java.util.Date;
import java.util.zip.ZipEntry;
import java.util.zip.ZipInputStream;
@ -78,7 +79,7 @@ public class TerminologyCacheManager {
try {
System.out.println("Initialise terminology cache from "+source);
HTTPResult res = ManagedWebAccess.get(source+"?nocache=" + System.currentTimeMillis());
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), source+"?nocache=" + System.currentTimeMillis());
res.checkThrowException();
unzip(new ByteArrayInputStream(res.getContent()), cacheFolder);
} catch (Exception e) {
@ -148,7 +149,7 @@ public class TerminologyCacheManager {
// post it to
String url = "https://tx.fhir.org/post/tx-cache/"+ghOrg+"/"+ghRepo+"/"+ghBranch+".zip";
System.out.println("Sending tx-cache to "+url+" ("+Utilities.describeSize(bs.toByteArray().length)+")");
HTTPResult res = ManagedWebAccess.accessor()
HTTPResult res = ManagedWebAccess.accessor(Arrays.asList("web"))
.withBasicAuth(token.substring(0, token.indexOf(':')), token.substring(token.indexOf(':') + 1))
.put(url, bs.toByteArray(), null, "application/zip");

View File

@ -9,6 +9,7 @@ import org.hl7.fhir.utilities.settings.ServerDetailsPOJO;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Map;
import java.util.concurrent.TimeUnit;
@ -45,7 +46,7 @@ public class ManagedFhirWebAccessor extends ManagedWebAccessorBase<ManagedFhirWe
public ManagedFhirWebAccessor(String userAgent, List<ServerDetailsPOJO> serverAuthDetails) {
super(userAgent, serverAuthDetails);
super(Arrays.asList("fhir"), userAgent, serverAuthDetails);
this.timeout = 5000;
this.timeoutUnit = TimeUnit.MILLISECONDS;
}
@ -88,7 +89,7 @@ public class ManagedFhirWebAccessor extends ManagedWebAccessorBase<ManagedFhirWe
}
}
} else {
ServerDetailsPOJO settings = ManagedWebAccessUtils.getServer(httpRequest.getUrl().toString(), getServerAuthDetails());
ServerDetailsPOJO settings = ManagedWebAccessUtils.getServer(getServerTypes(), httpRequest.getUrl().toString(), getServerAuthDetails());
if (settings != null) {
switch (settings.getAuthenticationType()) {
case "basic":

View File

@ -52,9 +52,9 @@ import org.hl7.fhir.utilities.settings.ServerDetailsPOJO;
public class ManagedWebAccess {
public interface IWebAccessor {
HTTPResult get(String url, String accept, Map<String, String> headers) throws IOException;
HTTPResult post(String url, byte[] bytes, String contentType, String accept, Map<String, String> headers) throws IOException;
HTTPResult put(String url, byte[] bytes, String contentType, String accept, Map<String, String> headers) throws IOException;
HTTPResult get(Iterable<String> serverTypes, String url, String accept, Map<String, String> headers) throws IOException;
HTTPResult post(Iterable<String> serverTypes, String url, byte[] bytes, String contentType, String accept, Map<String, String> headers) throws IOException;
HTTPResult put(Iterable<String> serverTypes, String url, byte[] bytes, String contentType, String accept, Map<String, String> headers) throws IOException;
}
public interface IFhirWebAccessor {
@ -104,28 +104,28 @@ public class ManagedWebAccess {
ManagedWebAccess.userAgent = userAgent;
}
public static ManagedWebAccessor accessor() {
return new ManagedWebAccessor(userAgent, serverAuthDetails);
public static ManagedWebAccessor accessor(Iterable<String> serverTypes) {
return new ManagedWebAccessor(serverTypes, userAgent, serverAuthDetails);
}
public static ManagedFhirWebAccessor fhirAccessor() {
return new ManagedFhirWebAccessor(userAgent, serverAuthDetails);
}
public static HTTPResult get(String url) throws IOException {
return accessor().get(url);
public static HTTPResult get(Iterable<String> serverTypes, String url) throws IOException {
return accessor(serverTypes).get(url);
}
public static HTTPResult get(String url, String accept) throws IOException {
return accessor().get(url, accept);
public static HTTPResult get(Iterable<String> serverTypes, String url, String accept) throws IOException {
return accessor(serverTypes).get(url, accept);
}
public static HTTPResult post(String url, byte[] content, String contentType, String accept) throws IOException {
return accessor().post(url, content, contentType, accept);
public static HTTPResult post(Iterable<String> serverTypes, String url, byte[] content, String contentType, String accept) throws IOException {
return accessor(serverTypes).post(url, content, contentType, accept);
}
public static HTTPResult put(String url, byte[] content, String contentType, String accept) throws IOException {
return accessor().put(url, content, contentType, accept);
public static HTTPResult put(Iterable<String> serverTypes, String url, byte[] content, String contentType, String accept) throws IOException {
return accessor(serverTypes).put(url, content, contentType, accept);
}
public static HTTPResult httpCall(HTTPRequest httpRequest) throws IOException {
@ -136,15 +136,13 @@ public class ManagedWebAccess {
setAccessPolicy(FhirSettings.isProhibitNetworkAccess() ? WebAccessPolicy.PROHIBITED : WebAccessPolicy.DIRECT);
setUserAgent("hapi-fhir-tooling-client");
serverAuthDetails = new ArrayList<>();
serverAuthDetails.addAll(FhirSettings.getPackageServers());
serverAuthDetails.addAll(FhirSettings.getTerminologyServers());
serverAuthDetails.addAll(FhirSettings.getServers());
}
public static void loadFromFHIRSettings(FhirSettings settings) {
setAccessPolicy(settings.isProhibitNetworkAccess() ? WebAccessPolicy.PROHIBITED : WebAccessPolicy.DIRECT);
setUserAgent("hapi-fhir-tooling-client");
serverAuthDetails = new ArrayList<>();
serverAuthDetails.addAll(settings.getPackageServers());
serverAuthDetails.addAll(settings.getTerminologyServers());
serverAuthDetails.addAll(settings.getServers());
}
}

View File

@ -4,14 +4,21 @@ import org.hl7.fhir.utilities.settings.ServerDetailsPOJO;
public class ManagedWebAccessUtils {
public static ServerDetailsPOJO getServer(String url, Iterable<ServerDetailsPOJO> serverAuthDetails) {
public static ServerDetailsPOJO getServer(Iterable<String> serverTypes, String url, Iterable<ServerDetailsPOJO> serverAuthDetails) {
if (serverAuthDetails != null) {
for (ServerDetailsPOJO t : serverAuthDetails) {
if (url.startsWith(t.getUrl())) {
return t;
for (ServerDetailsPOJO serverDetails : serverAuthDetails) {
for (String serverType : serverTypes) {
if (url.startsWith(serverDetails.getUrl()) && typesMatch(serverType, serverDetails.getType())) {
return serverDetails;
}
}
}
}
return null;
}
private static boolean typesMatch(String criteria, String value) {
return criteria == null || value == null || criteria.equals(value);
}
}

View File

@ -14,8 +14,8 @@ import org.hl7.fhir.utilities.settings.ServerDetailsPOJO;
*/
public class ManagedWebAccessor extends ManagedWebAccessorBase<ManagedWebAccessor> {
public ManagedWebAccessor(String userAgent, List<ServerDetailsPOJO> serverAuthDetails) {
super(userAgent, serverAuthDetails);
public ManagedWebAccessor(Iterable<String> serverTypes, String userAgent, List<ServerDetailsPOJO> serverAuthDetails) {
super(serverTypes, userAgent, serverAuthDetails);
}
private Map<String, String> newHeaders() {
@ -66,7 +66,7 @@ public class ManagedWebAccessor extends ManagedWebAccessorBase<ManagedWebAccesso
}
}
} else {
ServerDetailsPOJO settings = ManagedWebAccessUtils.getServer(url, getServerAuthDetails());
ServerDetailsPOJO settings = ManagedWebAccessUtils.getServer(getServerTypes(), url, getServerAuthDetails());
if (settings != null) {
switch (settings.getAuthenticationType()) {
case "basic" :
@ -101,7 +101,7 @@ public class ManagedWebAccessor extends ManagedWebAccessorBase<ManagedWebAccesso
SimpleHTTPClient client = setupClient(url);
return client.get(url, accept);
case MANAGED:
return ManagedWebAccess.getAccessor().get(url, accept, newHeaders());
return ManagedWebAccess.getAccessor().get(getServerTypes(), url, accept, newHeaders());
case PROHIBITED:
throw new IOException("Access to the internet is not allowed by local security policy");
default:
@ -119,7 +119,7 @@ public class ManagedWebAccessor extends ManagedWebAccessorBase<ManagedWebAccesso
SimpleHTTPClient client = setupClient(url);
return client.post(url, contentType, content, accept);
case MANAGED:
return ManagedWebAccess.getAccessor().post(url, content, contentType, accept, newHeaders());
return ManagedWebAccess.getAccessor().post(getServerTypes(), url, content, contentType, accept, newHeaders());
case PROHIBITED:
throw new IOException("Access to the internet is not allowed by local security policy");
default:
@ -137,7 +137,7 @@ public class ManagedWebAccessor extends ManagedWebAccessorBase<ManagedWebAccesso
SimpleHTTPClient client = setupClient(url);
return client.put(url, contentType, content, accept);
case MANAGED:
return ManagedWebAccess.getAccessor().put(url, content, contentType, accept, newHeaders());
return ManagedWebAccess.getAccessor().put(getServerTypes(), url, content, contentType, accept, newHeaders());
case PROHIBITED:
throw new IOException("Access to the internet is not allowed by local security policy");
default:

View File

@ -8,6 +8,9 @@ import java.util.List;
import java.util.Map;
public abstract class ManagedWebAccessorBase<B extends ManagedWebAccessorBase<B>> {
@Getter
private final Iterable<String> serverTypes;
@Getter
private final String userAgent;
@Getter
@ -24,7 +27,8 @@ public abstract class ManagedWebAccessorBase<B extends ManagedWebAccessorBase<B>
@Getter
private final Map<String, String> headers = new HashMap<>();
public ManagedWebAccessorBase(String userAgent, List<ServerDetailsPOJO> serverAuthDetails) {
public ManagedWebAccessorBase(Iterable<String> serverTypes, String userAgent, List<ServerDetailsPOJO> serverAuthDetails) {
this.serverTypes = serverTypes;
this.userAgent = userAgent;
this.serverAuthDetails = serverAuthDetails;
}

View File

@ -2,34 +2,34 @@ package org.hl7.fhir.utilities.json;
import java.io.File;
/*
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.
*/
@ -37,6 +37,7 @@ import java.io.IOException;
import java.io.InputStream;
import java.math.BigDecimal;
import java.nio.charset.StandardCharsets;
import java.util.Arrays;
import java.util.Map;
import java.util.Stack;
@ -724,13 +725,13 @@ public class JsonTrackingParser {
}
public static JsonObject fetchJson(String source) throws IOException {
HTTPResult res = ManagedWebAccess.get(source+"?nocache=" + System.currentTimeMillis(), "application/json, application/fhir+json");
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), source+"?nocache=" + System.currentTimeMillis(), "application/json, application/fhir+json");
res.checkThrowException();
return parseJson(res.getContent());
}
public static JsonArray fetchJsonArray(String source) throws IOException {
HTTPResult res = ManagedWebAccess.get(source+"?nocache=" + System.currentTimeMillis(), "application/json, application/fhir+json");
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"),source+"?nocache=" + System.currentTimeMillis(), "application/json, application/fhir+json");
res.checkThrowException();
return parseJsonArray(res.getContent());
}

View File

@ -6,6 +6,7 @@ import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.nio.charset.StandardCharsets;
import java.util.Arrays;
import java.util.List;
import org.hl7.fhir.utilities.TextFile;
@ -692,7 +693,7 @@ public class JsonParser {
private static byte[] fetch(String source) throws IOException {
String murl = source.contains("?") ? source+"&nocache=" + System.currentTimeMillis() : source+"?nocache=" + System.currentTimeMillis();
HTTPResult res = ManagedWebAccess.get(murl, "application/json, application/fhir+json");
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), murl, "application/json, application/fhir+json");
res.checkThrowException();
return res.getContent();
}

View File

@ -729,7 +729,7 @@ public class FilesystemPackageCacheManager extends BasePackageCacheManager imple
private InputStream fetchFromUrlSpecific(String source, boolean optional) throws FHIRException {
try {
HTTPResult res = ManagedWebAccess.get(source);
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), source);
res.checkThrowException();
return new ByteArrayInputStream(res.getContent());
} catch (Exception e) {
@ -862,8 +862,7 @@ public class FilesystemPackageCacheManager extends BasePackageCacheManager imple
}
private void loadFromBuildServer() throws IOException {
HTTPResult res = ManagedWebAccess.get("https://build.fhir.org/ig/qas.json?nocache=" + System.currentTimeMillis());
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), "https://build.fhir.org/ig/qas.json?nocache=" + System.currentTimeMillis());
res.checkThrowException();
buildInfo = (JsonArray) JsonParser.parse(TextFile.bytesToString(res.getContent()));

View File

@ -44,15 +44,7 @@ import java.io.OutputStream;
import java.nio.charset.StandardCharsets;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.UUID;
import java.util.*;
import java.util.zip.Deflater;
import java.util.zip.ZipEntry;
import java.util.zip.ZipInputStream;
@ -1480,7 +1472,7 @@ public class NpmPackage {
}
public static NpmPackage fromUrl(String source) throws IOException {
HTTPResult res = ManagedWebAccess.get(source+"?nocache=" + System.currentTimeMillis());
HTTPResult res = ManagedWebAccess.get(Arrays.asList("npm-package", "fhir-package"), source+"?nocache=" + System.currentTimeMillis());
res.checkThrowException();
return fromPackage(new ByteArrayInputStream(res.getContent()));
}

View File

@ -8,11 +8,7 @@ import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.time.Instant;
import java.time.format.DateTimeParseException;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Date;
import java.util.List;
import java.util.Set;
import java.util.*;
import javax.annotation.Nullable;
@ -175,11 +171,13 @@ public class PackageClient {
}
private InputStream fetchUrl(String source, String accept) throws IOException {
ManagedWebAccessor webAccessor = ManagedWebAccess.accessor();
ManagedWebAccessor webAccessor = ManagedWebAccess.accessor(Arrays.asList("web"));
if (server.getAuthenticationMode() == HTTPAuthenticationMode.TOKEN) {
webAccessor.withToken(server.getToken());
} else if (server.getAuthenticationMode() == HTTPAuthenticationMode.BASIC) {
webAccessor.withBasicAuth(server.getUsername(), server.getPassword());
} else if (server.getAuthenticationMode() == HTTPAuthenticationMode.APIKEY) {
webAccessor.withApiKey(server.getApiKey());
}
HTTPResult res = webAccessor.get(source, accept);
res.checkThrowException();

View File

@ -7,7 +7,6 @@ import java.util.stream.Collectors;
import javax.annotation.Nullable;
import org.hl7.fhir.utilities.http.HTTPAuthenticationMode;
import org.hl7.fhir.utilities.http.SimpleHTTPClient;
import org.hl7.fhir.utilities.settings.FhirSettings;
import org.hl7.fhir.utilities.settings.ServerDetailsPOJO;
@ -27,10 +26,11 @@ public class PackageServer {
serverType = PackageServerType.FHIR;
}
@Getter
private String url;
@Getter
private HTTPAuthenticationMode authenticationMode;
private HTTPAuthenticationMode authenticationMode;
@Getter
private PackageServerType serverType;
@ -43,9 +43,11 @@ public class PackageServer {
@Getter
private String token;
public String getUrl() {
return url;
}
@Getter
private String apiKey;
public static final String PRIMARY_SERVER = "https://packages.fhir.org";
public static final String SECONDARY_SERVER = "https://packages2.fhir.org/packages";
@ -69,24 +71,54 @@ public class PackageServer {
return new PackageServer(pojo.getUrl())
.withAuthenticationMode(getModeFromPOJO(pojo))
.withServerType(
pojo.getServerType() != null && pojo.getServerType().equalsIgnoreCase("npm") ? PackageServerType.NPM : PackageServerType.FHIR
getPackageServerType(pojo.getType())
)
.withUsername(pojo.getUsername())
.withPassword(pojo.getPassword())
.withToken(pojo.getToken());
.withToken(pojo.getToken())
.withApiKey(pojo.getApikey());
}
private static boolean isPackageServer(String serverType) {
if (serverType == null) {
return false;
}
if (serverType.equals("fhir-package")) {
return true;
}
if (serverType.equals("npm-package")) {
return true;
}
return false;
}
private static PackageServerType getPackageServerType(String serverType) {
if (serverType == null) {
return null;
}
if (serverType.equals("fhir-package")) {
return PackageServerType.FHIR;
}
if (serverType.equals("npm-package")) {
return PackageServerType.NPM;
}
return null;
}
@Nullable
private static HTTPAuthenticationMode getModeFromPOJO(ServerDetailsPOJO pojo) {
if (pojo.getAuthenticationType().equalsIgnoreCase("basic")) return HTTPAuthenticationMode.BASIC;
if (pojo.getAuthenticationType().equalsIgnoreCase("token")) return HTTPAuthenticationMode.TOKEN;
if (pojo.getAuthenticationType().equalsIgnoreCase("apikey")) return HTTPAuthenticationMode.APIKEY;
return null;
}
public static List<PackageServer> getConfiguredServers() {
return FhirSettings.getPackageServers().stream().map(
PackageServer::getPackageServerFromPOJO
).collect(Collectors.toList());
return FhirSettings.getServers().stream()
.filter(serverDetailsPOJO -> isPackageServer(serverDetailsPOJO.getType()))
.map(PackageServer::getPackageServerFromPOJO)
.collect(Collectors.toList());
}
@Override
@ -101,6 +133,7 @@ public class PackageServer {
packageServer.username = this.username;
packageServer.password = this.password;
packageServer.token = this.token;
packageServer.apiKey = this.apiKey;
return packageServer;
}
@ -133,4 +166,10 @@ public class PackageServer {
packageServer.token = token;
return packageServer;
}
public PackageServer withApiKey(String apiKey) {
PackageServer packageServer = this.copy();
packageServer.apiKey = apiKey;
return packageServer;
}
}

View File

@ -222,25 +222,17 @@ public class FhirSettings {
public static boolean isIgnoreDefaultPackageServers() {
getInstance();
if (instance.fhirSettings.getPackageManagement() == null || instance.fhirSettings.getPackageManagement().getIgnoreDefaultServers() == null) {
if (instance.fhirSettings.getIgnoreDefaultPackageServers() == null) {
return false;
}
return instance.fhirSettings.getPackageManagement().getIgnoreDefaultServers();
return instance.fhirSettings.getIgnoreDefaultPackageServers();
}
public static List<ServerDetailsPOJO> getPackageServers() {
public static List<ServerDetailsPOJO> getServers() {
getInstance();
if (instance.fhirSettings.getPackageManagement() == null) {
if (instance.fhirSettings.getServers() == null) {
return Collections.emptyList();
}
return Arrays.asList(instance.fhirSettings.getPackageManagement().getServers().toArray(new ServerDetailsPOJO[]{}));
}
public static List<ServerDetailsPOJO> getTerminologyServers() {
getInstance();
if (instance.fhirSettings.getTerminologyServers() == null) {
return Collections.emptyList();
}
return Arrays.asList(instance.fhirSettings.getTerminologyServers().getServers().toArray(new ServerDetailsPOJO[]{}));
return Arrays.asList(instance.fhirSettings.getServers().toArray(new ServerDetailsPOJO[]{}));
}
}

View File

@ -1,5 +1,7 @@
package org.hl7.fhir.utilities.settings;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import lombok.AllArgsConstructor;
@ -39,8 +41,9 @@ public class FhirSettingsPOJO {
private String txFhirDevelopment;
private String txFhirLocal;
private PackageManagementPOJO packageManagement;
private TerminologyServersPOJO terminologyServers;
private Boolean ignoreDefaultPackageServers;
private List<ServerDetailsPOJO> servers;
protected FhirSettingsPOJO() {
apiKeys = null;
@ -53,8 +56,6 @@ public class FhirSettingsPOJO {
txFhirProduction = TX_SERVER_PROD;
txFhirDevelopment = TX_SERVER_DEV;
txFhirLocal = TX_SERVER_LOCAL;
packageManagement = null;
terminologyServers = null;
servers = new ArrayList<>();
}
}

View File

@ -1,25 +0,0 @@
package org.hl7.fhir.utilities.settings;
import java.util.ArrayList;
import java.util.List;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.extern.jackson.Jacksonized;
@Data
@Builder
@Jacksonized
@AllArgsConstructor
public class PackageManagementPOJO {
private Boolean ignoreDefaultServers;
private List<ServerDetailsPOJO> servers;
protected PackageManagementPOJO() {
ignoreDefaultServers = false;
servers = new ArrayList<>();
}
}

View File

@ -10,14 +10,25 @@ import lombok.extern.jackson.Jacksonized;
@Jacksonized
@AllArgsConstructor
public class ServerDetailsPOJO {
String url;
// possible values: none, basic, token, apikey
String authenticationType;
// npm or fhir, because the FHIR npm usage varies a little bit from general NPM usage (change over time)
String serverType;
/**
* This helps clients use appropriate API endpoints for each server type.
* <p/>
* It can be of the following types:
* <ul>
* <li>web</li>
* <li>fhir</li>
* <li>npm-package</li>
* <li>fhir-package</li>
* </ul>
*/
String type;
String username;

View File

@ -1,22 +0,0 @@
package org.hl7.fhir.utilities.settings;
import java.util.ArrayList;
import java.util.List;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.extern.jackson.Jacksonized;
@Data
@Builder
@Jacksonized
@AllArgsConstructor
public class TerminologyServersPOJO {
private List<ServerDetailsPOJO> servers;
protected TerminologyServersPOJO() {
servers = new ArrayList<>();
}
}

View File

@ -164,7 +164,7 @@ public class ManagedWebAccessAuthTests {
return new ServerDetailsPOJO(
server.url("").toString(),
"basic",
"dummyServerType",
"fhir",
DUMMY_USERNAME,
DUMMY_PASSWORD,
null, null);
@ -183,7 +183,7 @@ public void testTokenAuthFromSettings() throws IOException, InterruptedException
return new ServerDetailsPOJO(
server.url("").toString(),
"token",
"dummyServerType",
"fhir",
null,
null,
DUMMY_TOKEN, null);
@ -202,7 +202,7 @@ public void testTokenAuthFromSettings() throws IOException, InterruptedException
return new ServerDetailsPOJO(
server.url("").toString(),
"apikey",
"dummyServerType",
"fhir",
null,
null,
null, DUMMY_API_KEY);

View File

@ -85,19 +85,19 @@ public class FhirSettingsTests implements ResourceLoaderTests {
assertEquals("dummy-temp-path", fhirSettings.getTempPath());
assertEquals("dummy-test-igs-path", fhirSettings.getTestIgsPath());
assertTrue(fhirSettings.getPackageManagement().getIgnoreDefaultServers());
assertTrue(fhirSettings.getIgnoreDefaultPackageServers());
List<ServerDetailsPOJO> packageServers = fhirSettings.getPackageManagement().getServers();
List<ServerDetailsPOJO> servers = fhirSettings.getServers();
assertEquals(2, packageServers.size());
assertEquals(2, servers.size());
assertEquals("http://dummy.org", packageServers.get(0).url);
assertEquals("npm", packageServers.get(0).serverType);
assertEquals("joe", packageServers.get(0).username);
assertEquals("swordfish", packageServers.get(0).password);
assertEquals("BASIC", packageServers.get(0).authenticationType);
assertEquals("http://dummy.org", servers.get(0).url);
assertEquals("npm-package", servers.get(0).type);
assertEquals("joe", servers.get(0).username);
assertEquals("swordfish", servers.get(0).password);
assertEquals("BASIC", servers.get(0).authenticationType);
assertEquals("http://dummy2.com", packageServers.get(1).url);
assertEquals("http://dummy2.com", servers.get(1).url);
}
}

View File

@ -2,30 +2,28 @@
"apiKeys": {
"dummy-api-key": "dummy-api-key-value"
},
"npmPath": "dummy-npm-path",
"npmPath": "dummy-npm-path",
"rubyPath": "dummy-ruby-path",
"fhirTestCasesPath": "dummy-fhir-test-cases-path",
"diffToolPath": "dummy-diff-tool-path",
"tempPath": "dummy-temp-path",
"testIgsPath": "dummy-test-igs-path",
"unusedField" : "unused",
"packageManagement" : {
"ignoreDefaultServers" : true,
"servers": [
{
"url": "http://dummy.org",
"serverType": "npm",
"authenticationType": "BASIC",
"username": "joe",
"password": "swordfish"
},
{
"url": "http://dummy2.com",
"goobledy-goo": 5
}
]
},
"unusedData" : {
"unusedDateField" : "unused-data"
"unusedField": "unused",
"ignoreDefaultPackageServers": true,
"servers": [
{
"url": "http://dummy.org",
"type": "npm-package",
"authenticationType": "BASIC",
"username": "joe",
"password": "swordfish"
},
{
"url": "http://dummy2.com",
"goobledy-goo": 5
}
],
"unusedData": {
"unusedDateField": "unused-data"
}
}

View File

@ -430,7 +430,7 @@ public class IgLoader implements IValidationEngineLoader {
private InputStream fetchFromUrlSpecific(String source, boolean optional) throws FHIRException, IOException {
try {
HTTPResult res = ManagedWebAccess.get(source + "?nocache=" + System.currentTimeMillis());
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), source + "?nocache=" + System.currentTimeMillis());
res.checkThrowException();
return new ByteArrayInputStream(res.getContent());
} catch (IOException e) {
@ -583,12 +583,12 @@ public class IgLoader implements IValidationEngineLoader {
private byte[] fetchFromUrlSpecific(String source, String contentType, boolean optional, List<String> errors) throws FHIRException, IOException {
try {
try {
// try with cache-busting option and then try withhout in case the server doesn't support that
HTTPResult res = ManagedWebAccess.get(source + "?nocache=" + System.currentTimeMillis(), contentType);
// try with cache-busting option and then try without in case the server doesn't support that
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"),source + "?nocache=" + System.currentTimeMillis(), contentType);
res.checkThrowException();
return res.getContent();
} catch (Exception e) {
HTTPResult res = ManagedWebAccess.get(source, contentType);
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), source, contentType);
res.checkThrowException();
return res.getContent();
}

View File

@ -8,13 +8,7 @@ import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.*;
import java.util.stream.Collectors;
import java.util.zip.ZipEntry;
import java.util.zip.ZipInputStream;
@ -319,7 +313,7 @@ public class Scanner {
}
protected void download(String address, String filename) throws IOException {
HTTPResult res = ManagedWebAccess.get(address);
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), address);
res.checkThrowException();
TextFile.bytesToFile(res.getContent(), filename);
}

View File

@ -19,7 +19,6 @@ import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Set;
import java.util.UUID;
import org.fhir.ucum.UcumEssenceService;
import org.hl7.fhir.convertors.factory.VersionConvertorFactory_10_50;
@ -72,12 +71,9 @@ import org.hl7.fhir.r5.utils.validation.IMessagingServices;
import org.hl7.fhir.r5.utils.validation.IResourceValidator;
import org.hl7.fhir.r5.utils.validation.IValidationPolicyAdvisor;
import org.hl7.fhir.r5.utils.validation.IValidatorResourceFetcher;
import org.hl7.fhir.r5.utils.validation.IValidationPolicyAdvisor.AdditionalBindingPurpose;
import org.hl7.fhir.r5.utils.validation.IValidationPolicyAdvisor.CodedContentValidationAction;
import org.hl7.fhir.r5.utils.validation.constants.BestPracticeWarningLevel;
import org.hl7.fhir.r5.utils.validation.constants.BindingKind;
import org.hl7.fhir.r5.utils.validation.constants.CheckDisplayOption;
import org.hl7.fhir.r5.utils.validation.constants.CodedContentValidationPolicy;
import org.hl7.fhir.r5.utils.validation.constants.ContainedReferenceValidationPolicy;
import org.hl7.fhir.r5.utils.validation.constants.IdStatus;
import org.hl7.fhir.r5.utils.validation.constants.ReferenceValidationPolicy;
@ -942,7 +938,7 @@ public class ValidationEngine implements IValidatorResourceFetcher, IValidationP
if (output.startsWith("http://")) {
ByteArrayOutputStream bs = new ByteArrayOutputStream();
handleOutputToStream(r, output, bs, version);
HTTPResult res = ManagedWebAccess.post(output, bs.toByteArray(), "application/fhir+xml", "application/fhir+xml");
HTTPResult res = ManagedWebAccess.post(Arrays.asList("web"), output, bs.toByteArray(), "application/fhir+xml", "application/fhir+xml");
res.checkThrowException();
} else {
FileOutputStream s = ManagedFileAccess.outStream(output);
@ -1099,7 +1095,7 @@ public class ValidationEngine implements IValidatorResourceFetcher, IValidationP
@Override
public byte[] fetchRaw(IResourceValidator validator, String source) throws IOException {
HTTPResult res = ManagedWebAccess.get(source);
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), source);
res.checkThrowException();
return res.getContent();
}

View File

@ -2,6 +2,7 @@ package org.hl7.fhir.validation.cli.utils;
import java.io.File;
import java.io.IOException;
import java.util.Arrays;
import org.hl7.fhir.exceptions.FHIRException;
import org.hl7.fhir.utilities.TextFile;
@ -25,7 +26,7 @@ public class ProfileLoader {
private static byte[] loadProfileFromUrl(String src) throws FHIRException {
try {
HTTPResult res = ManagedWebAccess.get(src + "?nocache=" + System.currentTimeMillis());
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), src + "?nocache=" + System.currentTimeMillis());
res.checkThrowException();
return res.getContent();
} catch (Exception e) {

View File

@ -2,6 +2,7 @@ package org.hl7.fhir.validation.ipa;
import java.io.ByteArrayInputStream;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Map;
@ -160,7 +161,7 @@ public class IPAValidator {
private Element makeRequest(ValidationNode vn, String url) {
try {
HTTPResult result = ManagedWebAccess.get(url, "application/fhir+json");
HTTPResult result = ManagedWebAccess.get(Arrays.asList("web"), url, "application/fhir+json");
if (result.getCode() >= 300) {
vn.getIssues().add(new ValidationMessage(Source.IPAValidator, IssueType.EXCEPTION, "http.request",
"HTTP Return code is "+result.getCode()+" "+result.getMessage(),

View File

@ -8,17 +8,8 @@ import java.io.IOException;
import java.io.InputStream;
import java.net.MalformedURLException;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.EnumSet;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.*;
import java.util.Map.Entry;
import java.util.Set;
import org.apache.commons.io.IOUtils;
import org.apache.commons.lang3.NotImplementedException;
@ -858,7 +849,7 @@ public class ValidationTests implements IEvaluationContext, IValidatorResourceFe
@Override
public byte[] fetchRaw(IResourceValidator validator, String source) throws MalformedURLException, IOException {
HTTPResult res = ManagedWebAccess.get(source);
HTTPResult res = ManagedWebAccess.get(Arrays.asList("web"), source);
res.checkThrowException();
return res.getContent();
}