Merge remote-tracking branch 'remotes/origin/master' into im_20200728_term_multi_version_support

This commit is contained in:
ianmarshall 2020-09-15 16:49:06 -04:00
commit ca0bdc8e4c
11 changed files with 146 additions and 118 deletions

View File

@ -243,10 +243,10 @@
"description": "With the ACS App, Community Health Agents (CHA) work gets faster and faster, and they can take better care of their community. Best of all, it is 100% free to the Health Agent.", "description": "With the ACS App, Community Health Agents (CHA) work gets faster and faster, and they can take better care of their community. Best of all, it is 100% free to the Health Agent.",
"link": "http://ephealth.com.br/?lang=en", "link": "http://ephealth.com.br/?lang=en",
"contactName": "Alan Lescano", "contactName": "Alan Lescano",
"contactEmail": "alan@ephealth.com.br", "contactEmail": "alan.lesc1@gmail.com",
"city": "Sao Paulo, Brazil", "city": "Sao Paulo, Brazil",
"lat": -6.6167, "lat": -23.533773,
"lon": -38.1500, "lon": -46.625290,
"added": "2019-09-29" "added": "2019-09-29"
}, },
{ {

View File

@ -0,0 +1,5 @@
---
type: add
issue: 2078
title: "When using package support to install a package with STORE_AND_INSTALL mode, resources that are already
present in the database will now be updated to the contents of the version in the package."

View File

@ -4,5 +4,11 @@
title: "The version of a few dependencies have been bumped to the latest versions title: "The version of a few dependencies have been bumped to the latest versions
(dependent HAPI modules listed in brackets): (dependent HAPI modules listed in brackets):
<ul> <ul>
<li>Flyway (JPA): 6.4.1-&gt; 6.5.4</li> <li>Jackson (Base): 2.10.0 -&gt; 2.11.2</li>
<li>Flyway (JPA): 6.4.1 -&gt; 6.5.4</li>
<li>UCUM (JPA): 1.0.2 -&gt; 1.0.3</li>
<li>JQuery (Testpage Overlay): 3.3.1 -&gt; 3.5.1</li>
<li>Awesome Bootstrap Checkbos (Testpage Overlay): 1.0.1 -&gt; 1.0.2</li>
<li>MomentJS (Testpage Overlay): 2.15.1 -&gt; 2.27.0</li>
<li>Select2 (Testpage Overlay): 4.0.3 -&gt; 4.0.13</li>
</ul>" </ul>"

View File

@ -29,11 +29,13 @@ import ca.uhn.fhir.jpa.api.dao.IFhirResourceDao;
import ca.uhn.fhir.jpa.dao.data.INpmPackageVersionDao; import ca.uhn.fhir.jpa.dao.data.INpmPackageVersionDao;
import ca.uhn.fhir.jpa.model.entity.NpmPackageVersionEntity; import ca.uhn.fhir.jpa.model.entity.NpmPackageVersionEntity;
import ca.uhn.fhir.jpa.searchparam.SearchParameterMap; import ca.uhn.fhir.jpa.searchparam.SearchParameterMap;
import ca.uhn.fhir.jpa.searchparam.registry.ISearchParamRegistry;
import ca.uhn.fhir.rest.api.server.IBundleProvider; import ca.uhn.fhir.rest.api.server.IBundleProvider;
import ca.uhn.fhir.rest.param.StringParam; import ca.uhn.fhir.rest.param.StringParam;
import ca.uhn.fhir.rest.param.TokenParam; import ca.uhn.fhir.rest.param.TokenParam;
import ca.uhn.fhir.rest.param.UriParam; import ca.uhn.fhir.rest.param.UriParam;
import ca.uhn.fhir.rest.server.exceptions.InternalErrorException; import ca.uhn.fhir.rest.server.exceptions.InternalErrorException;
import ca.uhn.fhir.rest.server.exceptions.PreconditionFailedException;
import ca.uhn.fhir.util.FhirTerser; import ca.uhn.fhir.util.FhirTerser;
import ca.uhn.fhir.util.SearchParameterUtil; import ca.uhn.fhir.util.SearchParameterUtil;
import com.google.common.annotations.VisibleForTesting; import com.google.common.annotations.VisibleForTesting;
@ -94,6 +96,8 @@ public class PackageInstallerSvcImpl implements IPackageInstallerSvc {
private PlatformTransactionManager myTxManager; private PlatformTransactionManager myTxManager;
@Autowired @Autowired
private INpmPackageVersionDao myPackageVersionDao; private INpmPackageVersionDao myPackageVersionDao;
@Autowired
private ISearchParamRegistry mySearchParamRegistry;
/** /**
* Constructor * Constructor
@ -161,6 +165,9 @@ public class PackageInstallerSvcImpl implements IPackageInstallerSvc {
if (theInstallationSpec.getInstallMode() == PackageInstallationSpec.InstallModeEnum.STORE_AND_INSTALL) { if (theInstallationSpec.getInstallMode() == PackageInstallationSpec.InstallModeEnum.STORE_AND_INSTALL) {
install(npmPackage, theInstallationSpec, retVal); install(npmPackage, theInstallationSpec, retVal);
// If any SearchParameters were installed, let's load them right away
mySearchParamRegistry.refreshCacheIfNecessary();
} }
} catch (IOException e) { } catch (IOException e) {
@ -304,11 +311,20 @@ public class PackageInstallerSvcImpl implements IPackageInstallerSvc {
IFhirResourceDao dao = myDaoRegistry.getResourceDao(theResource.getClass()); IFhirResourceDao dao = myDaoRegistry.getResourceDao(theResource.getClass());
SearchParameterMap map = createSearchParameterMapFor(theResource); SearchParameterMap map = createSearchParameterMapFor(theResource);
IBundleProvider searchResult = dao.search(map); IBundleProvider searchResult = dao.search(map);
if (searchResult.isEmpty()) { if (validForUpload(theResource)) {
if (searchResult.isEmpty()) {
if (validForUpload(theResource)) { ourLog.info("Creating new resource matching {}", map.toNormalizedQueryString(myFhirContext));
theOutcome.incrementResourcesInstalled(myFhirContext.getResourceType(theResource)); theOutcome.incrementResourcesInstalled(myFhirContext.getResourceType(theResource));
dao.create(theResource); dao.create(theResource);
} else {
ourLog.info("Updating existing resource matching {}", map.toNormalizedQueryString(myFhirContext));
theOutcome.incrementResourcesInstalled(myFhirContext.getResourceType(theResource));
theResource.setId(searchResult.getResources(0,1).get(0).getIdElement().toUnqualifiedVersionless());
dao.update(theResource);
} }
} }

View File

@ -11,8 +11,11 @@ import ca.uhn.fhir.jpa.model.entity.NpmPackageEntity;
import ca.uhn.fhir.jpa.model.entity.NpmPackageVersionEntity; import ca.uhn.fhir.jpa.model.entity.NpmPackageVersionEntity;
import ca.uhn.fhir.jpa.model.entity.NpmPackageVersionResourceEntity; import ca.uhn.fhir.jpa.model.entity.NpmPackageVersionResourceEntity;
import ca.uhn.fhir.jpa.searchparam.SearchParameterMap; import ca.uhn.fhir.jpa.searchparam.SearchParameterMap;
import ca.uhn.fhir.jpa.searchparam.registry.ISearchParamRegistry;
import ca.uhn.fhir.rest.api.Constants; import ca.uhn.fhir.rest.api.Constants;
import ca.uhn.fhir.rest.api.server.IBundleProvider; import ca.uhn.fhir.rest.api.server.IBundleProvider;
import ca.uhn.fhir.rest.param.ReferenceParam;
import ca.uhn.fhir.rest.param.TokenParam;
import ca.uhn.fhir.rest.param.UriParam; import ca.uhn.fhir.rest.param.UriParam;
import ca.uhn.fhir.rest.server.exceptions.InternalErrorException; import ca.uhn.fhir.rest.server.exceptions.InternalErrorException;
import ca.uhn.fhir.test.utilities.JettyUtil; import ca.uhn.fhir.test.utilities.JettyUtil;
@ -22,7 +25,13 @@ import org.eclipse.jetty.server.Server;
import org.eclipse.jetty.servlet.ServletHandler; import org.eclipse.jetty.servlet.ServletHandler;
import org.eclipse.jetty.servlet.ServletHolder; import org.eclipse.jetty.servlet.ServletHolder;
import org.hl7.fhir.instance.model.api.IBaseResource; import org.hl7.fhir.instance.model.api.IBaseResource;
import org.hl7.fhir.instance.model.api.IIdType;
import org.hl7.fhir.r4.model.Enumerations;
import org.hl7.fhir.r4.model.ImplementationGuide; import org.hl7.fhir.r4.model.ImplementationGuide;
import org.hl7.fhir.r4.model.Organization;
import org.hl7.fhir.r4.model.PractitionerRole;
import org.hl7.fhir.r4.model.Reference;
import org.hl7.fhir.r4.model.SearchParameter;
import org.hl7.fhir.r4.model.StructureDefinition; import org.hl7.fhir.r4.model.StructureDefinition;
import org.hl7.fhir.utilities.cache.NpmPackage; import org.hl7.fhir.utilities.cache.NpmPackage;
import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.AfterEach;
@ -230,7 +239,6 @@ public class NpmTestR4 extends BaseJpaR4Test {
} }
@Test @Test
public void testInstallR4PackageWithNoDescription() throws Exception { public void testInstallR4PackageWithNoDescription() throws Exception {
myDaoConfig.setAllowExternalReferences(true); myDaoConfig.setAllowExternalReferences(true);
@ -433,6 +441,53 @@ public class NpmTestR4 extends BaseJpaR4Test {
} }
@Test
public void testInstallPkgContainingSearchParameter() throws IOException {
myDaoConfig.setAllowExternalReferences(true);
byte[] contents0111 = loadClasspathBytes("/packages/test-exchange-sample.tgz");
myFakeNpmServlet.myResponses.put("/test-exchange.fhir.us.com/2.1.1", contents0111);
contents0111 = loadClasspathBytes("/packages/test-exchange-sample-2.tgz");
myFakeNpmServlet.myResponses.put("/test-exchange.fhir.us.com/2.1.2", contents0111);
// Install older version
PackageInstallationSpec spec = new PackageInstallationSpec().setName("test-exchange.fhir.us.com").setVersion("2.1.1").setInstallMode(PackageInstallationSpec.InstallModeEnum.STORE_AND_INSTALL);
igInstaller.install(spec);
IBundleProvider spSearch = mySearchParameterDao.search(SearchParameterMap.newSynchronous("code", new TokenParam("network-id")));
assertEquals(1, spSearch.sizeOrThrowNpe());
SearchParameter sp = (SearchParameter) spSearch.getResources(0, 1).get(0);
assertEquals("network-id", sp.getCode());
assertEquals("2.1", sp.getVersion());
assertEquals(Enumerations.PublicationStatus.ACTIVE, sp.getStatus());
Organization org = new Organization();
org.setName("Hello");
IIdType orgId = myOrganizationDao.create(org).getId().toUnqualifiedVersionless();
PractitionerRole pr = new PractitionerRole();
pr.addExtension().setUrl("http://test-exchange.com/fhir/us/providerdataexchange/StructureDefinition/networkreference").setValue(new Reference(orgId));
myPractitionerRoleDao.create(pr);
SearchParameterMap map = SearchParameterMap.newSynchronous("network-id", new ReferenceParam(orgId.getValue()));
spSearch = myPractitionerRoleDao.search(map);
assertEquals(1, spSearch.sizeOrThrowNpe());
// Install newer version
spec = new PackageInstallationSpec().setName("test-exchange.fhir.us.com").setVersion("2.1.2").setInstallMode(PackageInstallationSpec.InstallModeEnum.STORE_AND_INSTALL);
igInstaller.install(spec);
spSearch = mySearchParameterDao.search(SearchParameterMap.newSynchronous("code", new TokenParam("network-id")));
assertEquals(1, spSearch.sizeOrThrowNpe());
sp = (SearchParameter) spSearch.getResources(0, 1).get(0);
assertEquals("network-id", sp.getCode());
assertEquals(Enumerations.PublicationStatus.ACTIVE, sp.getStatus());
assertEquals("2.2", sp.getVersion());
}
@Test @Test
public void testLoadContents() throws IOException { public void testLoadContents() throws IOException {
byte[] contents0111 = loadClasspathBytes("/packages/hl7.fhir.uv.shorthand-0.11.1.tgz"); byte[] contents0111 = loadClasspathBytes("/packages/hl7.fhir.uv.shorthand-0.11.1.tgz");

View File

@ -106,6 +106,13 @@ public interface ITestDataBuilder {
}; };
} }
/**
* Set Organization.name
*/
default Consumer<IBaseResource> withName(String theStatus) {
return t -> __setPrimitiveChild(getFhirContext(), t, "name", "string", theStatus);
}
default Consumer<IBaseResource> withId(String theId) { default Consumer<IBaseResource> withId(String theId) {
return t -> { return t -> {
assertThat(theId, matchesPattern("[a-zA-Z0-9]+")); assertThat(theId, matchesPattern("[a-zA-Z0-9]+"));
@ -129,6 +136,10 @@ public interface ITestDataBuilder {
return createResource("Patient", theModifiers); return createResource("Patient", theModifiers);
} }
default IIdType createOrganization(Consumer<IBaseResource>... theModifiers) {
return createResource("Organization", theModifiers);
}
default IIdType createResource(String theResourceType, Consumer<IBaseResource>[] theModifiers) { default IIdType createResource(String theResourceType, Consumer<IBaseResource>[] theModifiers) {
IBaseResource resource = getFhirContext().getResourceDefinition(theResourceType).newInstance(); IBaseResource resource = getFhirContext().getResourceDefinition(theResourceType).newInstance();
for (Consumer<IBaseResource> next : theModifiers) { for (Consumer<IBaseResource> next : theModifiers) {
@ -155,6 +166,30 @@ public interface ITestDataBuilder {
}; };
} }
default Consumer<IBaseResource> withObservationHasMember(@Nullable IIdType theHasMember) {
return t -> {
if (theHasMember != null) {
IBaseReference reference = (IBaseReference) getFhirContext().getElementDefinition("Reference").newInstance();
reference.setReference(theHasMember.getValue());
RuntimeResourceDefinition resourceDef = getFhirContext().getResourceDefinition(t.getClass());
resourceDef.getChildByName("hasMember").getMutator().addValue(t, reference);
}
};
}
default Consumer<IBaseResource> withOrganization(@Nullable IIdType theHasMember) {
return t -> {
if (theHasMember != null) {
IBaseReference reference = (IBaseReference) getFhirContext().getElementDefinition("Reference").newInstance();
reference.setReference(theHasMember.getValue());
RuntimeResourceDefinition resourceDef = getFhirContext().getResourceDefinition(t.getClass());
resourceDef.getChildByName("managingOrganization").getMutator().addValue(t, reference);
}
};
}
/** /**
* Users of this API must implement this method * Users of this API must implement this method
*/ */

View File

@ -29,8 +29,8 @@
<script th:src="@{/resources/moment/min/moment-with-locales.min.js}"></script> <script th:src="@{/resources/moment/min/moment-with-locales.min.js}"></script>
<link th:href="@{/resources/Eonasdan-bootstrap-datetimepicker/css/bootstrap-datetimepicker.min.css}" rel="stylesheet" /> <link th:href="@{/resources/Eonasdan-bootstrap-datetimepicker/css/bootstrap-datetimepicker.min.css}" rel="stylesheet" />
<script th:src="@{/resources/Eonasdan-bootstrap-datetimepicker/js/bootstrap-datetimepicker.js}"></script> <script th:src="@{/resources/Eonasdan-bootstrap-datetimepicker/js/bootstrap-datetimepicker.js}"></script>
<link th:href="@{/resources/select2/dist/css/select2.css}" rel="stylesheet"/> <link th:href="@{/resources/select2/css/select2.css}" rel="stylesheet"/>
<script th:src="@{/resources/select2/dist/js/select2.min.js}"></script> <script th:src="@{/resources/select2/js/select2.min.js}"></script>
<script src="js/RestfulTester.js" type="text/javascript"></script> <script src="js/RestfulTester.js" type="text/javascript"></script>

View File

@ -210,7 +210,7 @@
<dependency> <dependency>
<groupId>org.apache.ant</groupId> <groupId>org.apache.ant</groupId>
<artifactId>ant</artifactId> <artifactId>ant</artifactId>
<version>1.7.0</version> <version>1.10.8</version>
</dependency> </dependency>
<!-- This is just used for --> <!-- This is just used for -->

127
pom.xml
View File

@ -679,7 +679,7 @@
<properties> <properties>
<fhir_core_version>5.1.0</fhir_core_version> <fhir_core_version>5.1.0</fhir_core_version>
<ucum_version>1.0.2</ucum_version> <ucum_version>1.0.3</ucum_version>
<surefire_jvm_args>-Dfile.encoding=UTF-8 -Xmx2048m</surefire_jvm_args> <surefire_jvm_args>-Dfile.encoding=UTF-8 -Xmx2048m</surefire_jvm_args>
@ -726,8 +726,8 @@
<hibernate_validator_version>6.1.3.Final</hibernate_validator_version> <hibernate_validator_version>6.1.3.Final</hibernate_validator_version>
<httpcore_version>4.4.13</httpcore_version> <httpcore_version>4.4.13</httpcore_version>
<httpclient_version>4.5.12</httpclient_version> <httpclient_version>4.5.12</httpclient_version>
<jackson_version>2.10.0</jackson_version> <jackson_version>2.11.2</jackson_version>
<jackson_databind_version>2.10.0</jackson_databind_version> <jackson_databind_version>2.11.2</jackson_databind_version>
<maven_assembly_plugin_version>3.1.0</maven_assembly_plugin_version> <maven_assembly_plugin_version>3.1.0</maven_assembly_plugin_version>
<maven_license_plugin_version>1.8</maven_license_plugin_version> <maven_license_plugin_version>1.8</maven_license_plugin_version>
<resteasy_version>4.0.0.Beta3</resteasy_version> <resteasy_version>4.0.0.Beta3</resteasy_version>
@ -1018,11 +1018,6 @@
<artifactId>javax.ws.rs-api</artifactId> <artifactId>javax.ws.rs-api</artifactId>
<version>2.0.1</version> <version>2.0.1</version>
</dependency> </dependency>
<dependency>
<groupId>io.github.devacfr.maven.skins</groupId>
<artifactId>reflow-velocity-tools</artifactId>
<version>2.0.0-beta2</version>
</dependency>
<dependency> <dependency>
<groupId>io.swagger</groupId> <groupId>io.swagger</groupId>
<artifactId>swagger-annotations</artifactId> <artifactId>swagger-annotations</artifactId>
@ -1572,6 +1567,12 @@
<groupId>org.webjars</groupId> <groupId>org.webjars</groupId>
<artifactId>bootstrap</artifactId> <artifactId>bootstrap</artifactId>
<version>3.3.7</version> <version>3.3.7</version>
<exclusions>
<exclusion>
<groupId>org.webjars</groupId>
<artifactId>jquery</artifactId>
</exclusion>
</exclusions>
</dependency> </dependency>
<dependency> <dependency>
<groupId>org.webjars</groupId> <groupId>org.webjars</groupId>
@ -1586,7 +1587,7 @@
<dependency> <dependency>
<groupId>org.webjars.bower</groupId> <groupId>org.webjars.bower</groupId>
<artifactId>awesome-bootstrap-checkbox</artifactId> <artifactId>awesome-bootstrap-checkbox</artifactId>
<version>1.0.1</version> <version>1.0.2</version>
</dependency> </dependency>
<dependency> <dependency>
<groupId>org.webjars</groupId> <groupId>org.webjars</groupId>
@ -1596,17 +1597,23 @@
<dependency> <dependency>
<groupId>org.webjars</groupId> <groupId>org.webjars</groupId>
<artifactId>select2</artifactId> <artifactId>select2</artifactId>
<version>4.0.3</version> <version>4.0.13</version>
<exclusions>
<exclusion>
<groupId>org.webjars</groupId>
<artifactId>jquery</artifactId>
</exclusion>
</exclusions>
</dependency> </dependency>
<dependency> <dependency>
<groupId>org.webjars.bower</groupId> <groupId>org.webjars.bower</groupId>
<artifactId>jquery</artifactId> <artifactId>jquery</artifactId>
<version>3.3.1</version> <version>3.5.1</version>
</dependency> </dependency>
<dependency> <dependency>
<groupId>org.webjars.bower</groupId> <groupId>org.webjars.bower</groupId>
<artifactId>moment</artifactId> <artifactId>moment</artifactId>
<version>2.15.1</version> <version>2.27.0</version>
</dependency> </dependency>
<dependency> <dependency>
<groupId>org.xmlunit</groupId> <groupId>org.xmlunit</groupId>
@ -1873,49 +1880,6 @@
</excludes> </excludes>
</configuration> </configuration>
</plugin> </plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-site-plugin</artifactId>
<version>3.7.1</version>
<configuration>
<skip>false</skip>
<skipDeploy>true</skipDeploy>
<inputEncoding>UTF-8</inputEncoding>
<outputEncoding>UTF-8</outputEncoding>
<relativizeDecorationLinks>false</relativizeDecorationLinks>
</configuration>
<dependencies>
<dependency>
<groupId>org.apache.maven.wagon</groupId>
<artifactId>wagon-scm</artifactId>
</dependency>
<dependency>
<groupId>org.apache.maven.scm</groupId>
<artifactId>maven-scm-manager-plexus</artifactId>
</dependency>
<dependency>
<groupId>org.apache.maven.scm</groupId>
<artifactId>maven-scm-provider-gitexe</artifactId>
</dependency>
<dependency>
<groupId>org.apache.maven.scm</groupId>
<artifactId>maven-scm-api</artifactId>
</dependency>
<!-- <dependency> <groupId>org.apache.maven.doxia</groupId> <artifactId>doxia-core</artifactId> </dependency> -->
<dependency>
<groupId>org.apache.maven.doxia</groupId>
<artifactId>doxia-module-markdown</artifactId>
</dependency>
<dependency>
<groupId>io.github.devacfr.maven.skins</groupId>
<artifactId>reflow-velocity-tools</artifactId>
</dependency>
<dependency>
<groupId>org.apache.velocity</groupId>
<artifactId>velocity</artifactId>
</dependency>
</dependencies>
</plugin>
<!--This plugin's configuration is used to store Eclipse m2e settings only. It has no influence on the Maven build itself. --> <!--This plugin's configuration is used to store Eclipse m2e settings only. It has no influence on the Maven build itself. -->
<plugin> <plugin>
<groupId>org.eclipse.m2e</groupId> <groupId>org.eclipse.m2e</groupId>
@ -2310,59 +2274,6 @@
</execution> </execution>
</executions> </executions>
</plugin> </plugin>
<plugin>
<artifactId>maven-site-plugin</artifactId>
<inherited>false</inherited>
<executions>
<execution>
<id>stage-for-scm-publish</id>
<phase>post-site</phase>
<goals>
<goal>stage</goal>
</goals>
<configuration>
<stagingDirectory>${siteMainDirectory}</stagingDirectory>
</configuration>
</execution>
</executions>
<dependencies>
<dependency>
<groupId>org.apache.maven.wagon</groupId>
<artifactId>wagon-scm</artifactId>
<version>3.0.0</version>
</dependency>
<dependency>
<groupId>org.apache.maven.scm</groupId>
<artifactId>maven-scm-manager-plexus</artifactId>
<version>1.9.5</version>
</dependency>
<dependency>
<groupId>org.apache.maven.scm</groupId>
<artifactId>maven-scm-provider-gitexe</artifactId>
<version>1.9.5</version>
</dependency>
<dependency>
<groupId>org.apache.maven.scm</groupId>
<artifactId>maven-scm-api</artifactId>
<version>1.9.5</version>
</dependency>
<dependency>
<groupId>org.apache.maven.doxia</groupId>
<artifactId>doxia-module-markdown</artifactId>
<version>1.8</version>
</dependency>
<dependency>
<groupId>io.github.devacfr.maven.skins</groupId>
<artifactId>reflow-velocity-tools</artifactId>
<version>2.0.0-beta2</version>
</dependency>
<dependency>
<groupId>org.apache.velocity</groupId>
<artifactId>velocity</artifactId>
<version>1.7</version>
</dependency>
</dependencies>
</plugin>
<plugin> <plugin>
<groupId>org.apache.maven.plugins</groupId> <groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-scm-publish-plugin</artifactId> <artifactId>maven-scm-publish-plugin</artifactId>