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

This commit is contained in:
ianmarshall 2020-03-31 21:57:26 -04:00
commit a302d26eb1
27 changed files with 389 additions and 42 deletions

View File

@ -149,6 +149,8 @@ public class Constants {
*/
public static final String PARAM_BUNDLETYPE = "_bundletype";
public static final String PARAM_FILTER = "_filter";
public static final String PARAM_CONTAINED = "_contained";
public static final String PARAM_CONTAINED_TYPE = "_containedType";
public static final String PARAM_CONTENT = "_content";
public static final String PARAM_COUNT = "_count";
public static final String PARAM_DELETE = "_delete";

View File

@ -36,6 +36,8 @@ ca.uhn.fhir.rest.server.method.IncludeParameter.orIncludeInRequest='OR' query pa
ca.uhn.fhir.rest.server.method.PageMethodBinding.unknownSearchId=Search ID "{0}" does not exist and may have expired
ca.uhn.fhir.rest.server.method.ReadMethodBinding.invalidParamsInRequest=Invalid query parameter(s) for this request: "{0}"
ca.uhn.fhir.rest.server.method.SearchMethodBinding.invalidSpecialParamName=Method [{0}] in provider [{1}] contains search parameter annotated to use name [{2}] - This name is reserved according to the FHIR specification and can not be used as a search parameter name.
ca.uhn.fhir.rest.server.method.SearchMethodBinding.idWithoutCompartment=Method [{0}] in provider [{1}] has an @IdParam parameter. This is only allowable for compartment search (e.g. @Search(compartment="foo") )
ca.uhn.fhir.rest.server.method.SearchMethodBinding.idNullForCompartmentSearch=ID parameter can not be null or empty for compartment search

View File

@ -0,0 +1,7 @@
---
type: add
issue: 1774
title: The REST Server will now raise an error if a client tries to perform a FHIR *read* operation while using
URL paramaters that are specific to FHIR *search* operations. This should help clients who are mistaking the
semantics between the two operations, as previously the search parameters were simply ignored leading to
confusion. Thanks to Jafer Khan for implementing this!

View File

@ -49,16 +49,16 @@
<artifactId>h2</artifactId>
<scope>test</scope>
</dependency>
<!--<dependency>
<dependency>
<groupId>org.apache.derby</groupId>
<artifactId>derbyshared</artifactId>
<artifactId>derby</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.apache.derby</groupId>
<artifactId>derbytools</artifactId>
<scope>test</scope>
</dependency>-->
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>

View File

@ -69,6 +69,8 @@ public class DropIdGeneratorTask extends BaseTask {
}
break;
case DERBY_EMBEDDED:
sql = "drop sequence " + myGeneratorName + " restrict";
break;
case H2_EMBEDDED:
sql = "drop sequence " + myGeneratorName;
break;

View File

@ -111,9 +111,11 @@ public class DropIndexTask extends BaseTableTask {
sql.add("alter table " + theTableName + " drop index " + theIndexName);
break;
case H2_EMBEDDED:
case DERBY_EMBEDDED:
sql.add("drop index " + theIndexName);
break;
case DERBY_EMBEDDED:
sql.add("alter table " + theTableName + " drop constraint " + theIndexName);
break;
case POSTGRES_9_4:
sql.add("alter table " + theTableName + " drop constraint if exists " + theIndexName + " cascade");
sql.add("drop index if exists " + theIndexName + " cascade");

View File

@ -13,13 +13,20 @@ import javax.annotation.Nonnull;
import java.sql.SQLException;
import java.util.Properties;
import java.util.Set;
import java.util.function.Supplier;
import static org.hamcrest.CoreMatchers.containsString;
import static org.hamcrest.CoreMatchers.startsWith;
import static org.hamcrest.Matchers.endsWith;
import static org.junit.Assert.*;
public class SchemaMigratorTest extends BaseTest {
private static final org.slf4j.Logger ourLog = org.slf4j.LoggerFactory.getLogger(SchemaMigratorTest.class);
public SchemaMigratorTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testMigrationRequired() {
SchemaMigrator schemaMigrator = createTableMigrator();
@ -28,7 +35,8 @@ public class SchemaMigratorTest extends BaseTest {
schemaMigrator.validate();
fail();
} catch (ConfigurationException e) {
assertEquals("The database schema for " + getUrl() + " is out of date. Current database schema version is unknown. Schema version required by application is 1.1. Please run the database migrator.", e.getMessage());
assertThat(e.getMessage(), startsWith("The database schema for "));
assertThat(e.getMessage(), endsWith(" is out of date. Current database schema version is unknown. Schema version required by application is 1.1. Please run the database migrator."));
}
schemaMigrator.migrate();
@ -71,28 +79,28 @@ public class SchemaMigratorTest extends BaseTest {
public void testSkipSchemaVersion() throws SQLException {
AddTableRawSqlTask taskA = new AddTableRawSqlTask("V4_1_0", "20191214.1");
taskA.setTableName("SOMETABLE_A");
taskA.addSql(DriverTypeEnum.H2_EMBEDDED, "create table SOMETABLE_A (PID bigint not null, TEXTCOL varchar(255))");
taskA.addSql(getDriverType(), "create table SOMETABLE_A (PID bigint not null, TEXTCOL varchar(255))");
AddTableRawSqlTask taskB = new AddTableRawSqlTask("V4_1_0", "20191214.2");
taskB.setTableName("SOMETABLE_B");
taskB.addSql(DriverTypeEnum.H2_EMBEDDED, "create table SOMETABLE_B (PID bigint not null, TEXTCOL varchar(255))");
taskB.addSql(getDriverType(), "create table SOMETABLE_B (PID bigint not null, TEXTCOL varchar(255))");
AddTableRawSqlTask taskC = new AddTableRawSqlTask("V4_1_0", "20191214.3");
taskC.setTableName("SOMETABLE_C");
taskC.addSql(DriverTypeEnum.H2_EMBEDDED, "create table SOMETABLE_C (PID bigint not null, TEXTCOL varchar(255))");
taskC.addSql(getDriverType(), "create table SOMETABLE_C (PID bigint not null, TEXTCOL varchar(255))");
AddTableRawSqlTask taskD = new AddTableRawSqlTask("V4_1_0", "20191214.4");
taskD.setTableName("SOMETABLE_D");
taskD.addSql(DriverTypeEnum.H2_EMBEDDED, "create table SOMETABLE_D (PID bigint not null, TEXTCOL varchar(255))");
taskD.addSql(getDriverType(), "create table SOMETABLE_D (PID bigint not null, TEXTCOL varchar(255))");
ImmutableList<BaseTask> taskList = ImmutableList.of(taskA, taskB, taskC, taskD);
MigrationTaskSkipper.setDoNothingOnSkippedTasks(taskList, "4_1_0.20191214.2, 4_1_0.20191214.4");
SchemaMigrator schemaMigrator = new SchemaMigrator(SchemaMigrator.HAPI_FHIR_MIGRATION_TABLENAME, getDataSource(), new Properties(), taskList);
schemaMigrator.setDriverType(DriverTypeEnum.H2_EMBEDDED);
schemaMigrator.setDriverType(getDriverType());
schemaMigrator.migrate();
DriverTypeEnum.ConnectionProperties connectionProperties = DriverTypeEnum.H2_EMBEDDED.newConnectionProperties(getDataSource().getUrl(), getDataSource().getUsername(), getDataSource().getPassword());
DriverTypeEnum.ConnectionProperties connectionProperties = super.getDriverType().newConnectionProperties(getDataSource().getUrl(), getDataSource().getUsername(), getDataSource().getPassword());
Set<String> tableNames = JdbcUtils.getTableNames(connectionProperties);
assertThat(tableNames, Matchers.containsInAnyOrder("SOMETABLE_A", "SOMETABLE_C"));
}
@ -100,7 +108,7 @@ public class SchemaMigratorTest extends BaseTest {
@Test
public void testMigrationRequiredNoFlyway() throws SQLException {
SchemaMigrator schemaMigrator = createTableMigrator();
schemaMigrator.setDriverType(DriverTypeEnum.H2_EMBEDDED);
schemaMigrator.setDriverType(getDriverType());
schemaMigrator.setDontUseFlyway(true);
// Validate shouldn't fail if we aren't using Flyway
@ -110,7 +118,7 @@ public class SchemaMigratorTest extends BaseTest {
schemaMigrator.validate();
DriverTypeEnum.ConnectionProperties connectionProperties = DriverTypeEnum.H2_EMBEDDED.newConnectionProperties(getDataSource().getUrl(), getDataSource().getUsername(), getDataSource().getPassword());
DriverTypeEnum.ConnectionProperties connectionProperties = getDriverType().newConnectionProperties(getDataSource().getUrl(), getDataSource().getUsername(), getDataSource().getPassword());
Set<String> tableNames = JdbcUtils.getTableNames(connectionProperties);
assertThat(tableNames, Matchers.contains("SOMETABLE"));
@ -125,9 +133,9 @@ public class SchemaMigratorTest extends BaseTest {
private SchemaMigrator createSchemaMigrator(String theTableName, String theSql, String theSchemaVersion) {
AddTableRawSqlTask task = new AddTableRawSqlTask("1", theSchemaVersion);
task.setTableName(theTableName);
task.addSql(DriverTypeEnum.H2_EMBEDDED, theSql);
task.addSql(getDriverType(), theSql);
SchemaMigrator retval = new SchemaMigrator(SchemaMigrator.HAPI_FHIR_MIGRATION_TABLENAME, getDataSource(), new Properties(), ImmutableList.of(task));
retval.setDriverType(DriverTypeEnum.H2_EMBEDDED);
retval.setDriverType(getDriverType());
return retval;
}
}

View File

@ -9,6 +9,7 @@ import org.junit.Test;
import java.sql.SQLException;
import java.util.Set;
import java.util.function.Supplier;
import java.util.stream.Collectors;
import static org.hamcrest.Matchers.containsInAnyOrder;
@ -18,6 +19,10 @@ import static org.junit.Assert.fail;
public class AddColumnTest extends BaseTest {
public AddColumnTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testColumnDoesntAlreadyExist() throws SQLException {
executeSql("create table SOMETABLE (PID bigint not null, TEXTCOL varchar(255))");

View File

@ -5,12 +5,17 @@ import org.hamcrest.Matchers;
import org.junit.Test;
import java.sql.SQLException;
import java.util.function.Supplier;
import static org.hamcrest.Matchers.empty;
import static org.junit.Assert.assertThat;
public class AddForeignKeyTaskTest extends BaseTest {
public AddForeignKeyTaskTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testAddForeignKey() throws SQLException {
executeSql("create table HOME (PID bigint not null, TEXTCOL varchar(255), primary key (PID))");

View File

@ -7,6 +7,7 @@ import ca.uhn.fhir.util.VersionEnum;
import org.junit.Test;
import java.sql.SQLException;
import java.util.function.Supplier;
import static org.hamcrest.Matchers.containsInAnyOrder;
import static org.hamcrest.Matchers.empty;
@ -15,6 +16,10 @@ import static org.junit.Assert.assertThat;
public class AddIdGeneratorTaskTest extends BaseTest {
public AddIdGeneratorTaskTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testAddIdGenerator() throws SQLException {
assertThat(JdbcUtils.getSequenceNames(getConnectionProperties()), empty());

View File

@ -4,6 +4,7 @@ import ca.uhn.fhir.jpa.migrate.JdbcUtils;
import org.junit.Test;
import java.sql.SQLException;
import java.util.function.Supplier;
import static org.hamcrest.Matchers.containsInAnyOrder;
import static org.hamcrest.Matchers.hasItem;
@ -11,6 +12,10 @@ import static org.junit.Assert.assertThat;
public class AddIndexTest extends BaseTest {
public AddIndexTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testUniqueConstraintAlreadyExists() throws SQLException {
executeSql("create table SOMETABLE (PID bigint not null, TEXTCOL varchar(255))");

View File

@ -1,5 +1,6 @@
package ca.uhn.fhir.jpa.migrate.taskdef;
import ca.uhn.fhir.jpa.migrate.DriverTypeEnum;
import ca.uhn.fhir.jpa.migrate.JdbcUtils;
import ca.uhn.fhir.jpa.migrate.tasks.api.BaseMigrationTasks;
import ca.uhn.fhir.jpa.migrate.tasks.api.Builder;
@ -8,12 +9,17 @@ import org.junit.Test;
import java.sql.SQLException;
import java.util.Set;
import java.util.function.Supplier;
import java.util.stream.Collectors;
import static org.hamcrest.Matchers.containsInAnyOrder;
import static org.junit.Assert.assertThat;
public class AddTableByColumnTaskTest extends BaseTest {
public AddTableByColumnTaskTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testAddTable() throws SQLException {
@ -27,7 +33,13 @@ public class AddTableByColumnTaskTest extends BaseTest {
.filter(s -> !s.startsWith("FK_REF_INDEX_"))
.filter(s -> !s.startsWith("PRIMARY_KEY_"))
.collect(Collectors.toSet());
assertThat(indexes, containsInAnyOrder("IDX_BONJOUR"));
// Derby auto-creates constraints with a system name for unique indexes
if (getDriverType().equals(DriverTypeEnum.DERBY_EMBEDDED)) {
indexes.removeIf(t->t.startsWith("SQL"));
}
assertThat(indexes.toString(), indexes, containsInAnyOrder("IDX_BONJOUR"));
}
private static class MyMigrationTasks extends BaseMigrationTasks<VersionEnum> {

View File

@ -5,18 +5,23 @@ import ca.uhn.fhir.jpa.migrate.JdbcUtils;
import org.junit.Test;
import java.sql.SQLException;
import java.util.function.Supplier;
import static org.hamcrest.Matchers.containsInAnyOrder;
import static org.junit.Assert.assertThat;
public class AddTableTest extends BaseTest {
public AddTableTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testTableDoesntAlreadyExist() throws SQLException {
AddTableRawSqlTask task = new AddTableRawSqlTask("1", "1");
task.setTableName("SOMETABLE");
task.addSql(DriverTypeEnum.H2_EMBEDDED, "create table SOMETABLE (PID bigint not null, TEXTCOL varchar(255))");
task.addSql(getDriverType(), "create table SOMETABLE (PID bigint not null, TEXTCOL varchar(255))");
getMigrator().addTask(task);
getMigrator().migrate();
@ -31,7 +36,7 @@ public class AddTableTest extends BaseTest {
AddTableRawSqlTask task = new AddTableRawSqlTask("1", "1");
task.setTableName("SOMETABLE");
task.addSql(DriverTypeEnum.H2_EMBEDDED, "create table SOMETABLE (PID bigint not null, TEXTCOL varchar(255))");
task.addSql(getDriverType(), "create table SOMETABLE (PID bigint not null, TEXTCOL varchar(255))");
getMigrator().addTask(task);
getMigrator().migrate();

View File

@ -8,11 +8,16 @@ import org.junit.Test;
import java.util.List;
import java.util.Map;
import java.util.function.Supplier;
import static org.junit.Assert.assertEquals;
public class ArbitrarySqlTaskTest extends BaseTest {
public ArbitrarySqlTaskTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void test350MigrateSearchParams() {
executeSql("create table HFJ_SEARCH_PARM (PID bigint not null, RES_TYPE varchar(255), PARAM_NAME varchar(255))");
@ -106,8 +111,8 @@ public class ArbitrarySqlTaskTest extends BaseTest {
};
migrator
.forVersion(VersionEnum.V3_5_0)
.executeRawSql("1", DriverTypeEnum.H2_EMBEDDED, "delete from TEST_UPDATE_TASK where RES_TYPE = 'Patient'")
.executeRawSql("2", DriverTypeEnum.H2_EMBEDDED, "delete from TEST_UPDATE_TASK where RES_TYPE = 'Encounter'");
.executeRawSql("1", getDriverType(), "delete from TEST_UPDATE_TASK where RES_TYPE = 'Patient'")
.executeRawSql("2", getDriverType(), "delete from TEST_UPDATE_TASK where RES_TYPE = 'Encounter'");
getMigrator().addTasks(migrator.getTasks(VersionEnum.V3_3_0, VersionEnum.V3_6_0));
getMigrator().migrate();

View File

@ -8,21 +8,46 @@ import org.apache.commons.dbcp2.BasicDataSource;
import org.intellij.lang.annotations.Language;
import org.junit.After;
import org.junit.Before;
import org.junit.runner.RunWith;
import org.junit.runners.Parameterized;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.jdbc.core.ColumnMapRowMapper;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.function.Supplier;
public class BaseTest {
@RunWith(Parameterized.class)
public abstract class BaseTest {
private static final String DATABASE_NAME = "DATABASE";
private static final Logger ourLog = LoggerFactory.getLogger(BaseTest.class);
private static int ourDatabaseUrl = 0;
private final Supplier<TestDatabaseDetails> myTestDatabaseDetails;
private BasicDataSource myDataSource;
private String myUrl;
private FlywayMigrator myMigrator;
private DriverTypeEnum.ConnectionProperties myConnectionProperties;
private final BasicDataSource myDataSource = new BasicDataSource();
public BaseTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
myTestDatabaseDetails = theTestDatabaseDetails;
}
@Before
public void before() {
TestDatabaseDetails testDatabaseDetails = myTestDatabaseDetails.get();
myUrl = testDatabaseDetails.myUrl;
myConnectionProperties = testDatabaseDetails.myConnectionProperties;
myDataSource = testDatabaseDetails.myDataSource;
myMigrator = testDatabaseDetails.myMigrator;
}
public String getUrl() {
return myUrl;
@ -32,19 +57,6 @@ public class BaseTest {
return myConnectionProperties;
}
@Before()
public void before() {
org.h2.Driver.class.toString();
myUrl = "jdbc:h2:mem:" + DATABASE_NAME + ourDatabaseUrl++;
myConnectionProperties = DriverTypeEnum.H2_EMBEDDED.newConnectionProperties(myUrl, "SA", "SA");
myDataSource.setUrl(myUrl);
myDataSource.setUsername("SA");
myDataSource.setPassword("SA");
myDataSource.setDriverClassName(DriverTypeEnum.H2_EMBEDDED.getDriverClassName());
myMigrator = new FlywayMigrator(SchemaMigrator.HAPI_FHIR_MIGRATION_TABLENAME, myDataSource, DriverTypeEnum.H2_EMBEDDED);
}
protected BasicDataSource getDataSource() {
return myDataSource;
}
@ -79,5 +91,75 @@ public class BaseTest {
myConnectionProperties.close();
}
protected DriverTypeEnum getDriverType() {
return myConnectionProperties.getDriverType();
}
public static class TestDatabaseDetails {
private final String myUrl;
private final DriverTypeEnum.ConnectionProperties myConnectionProperties;
private final BasicDataSource myDataSource;
private final FlywayMigrator myMigrator;
public TestDatabaseDetails(String theUrl, DriverTypeEnum.ConnectionProperties theConnectionProperties, BasicDataSource theDataSource, FlywayMigrator theMigrator) {
myUrl = theUrl;
myConnectionProperties = theConnectionProperties;
myDataSource = theDataSource;
myMigrator = theMigrator;
}
}
@Parameterized.Parameters(name = "{0}")
public static Collection<Supplier<TestDatabaseDetails>> data() {
ourLog.info("H2: {}", org.h2.Driver.class.toString());
ArrayList<Supplier<TestDatabaseDetails>> retVal = new ArrayList<>();
// H2
retVal.add(new Supplier<TestDatabaseDetails>() {
@Override
public TestDatabaseDetails get() {
String url = "jdbc:h2:mem:" + DATABASE_NAME + ourDatabaseUrl++;
DriverTypeEnum.ConnectionProperties connectionProperties = DriverTypeEnum.H2_EMBEDDED.newConnectionProperties(url, "SA", "SA");
BasicDataSource dataSource = new BasicDataSource();
dataSource.setUrl(url);
dataSource.setUsername("SA");
dataSource.setPassword("SA");
dataSource.setDriverClassName(DriverTypeEnum.H2_EMBEDDED.getDriverClassName());
FlywayMigrator migrator = new FlywayMigrator(SchemaMigrator.HAPI_FHIR_MIGRATION_TABLENAME, dataSource, DriverTypeEnum.H2_EMBEDDED);
return new TestDatabaseDetails(url, connectionProperties, dataSource, migrator);
}
@Override
public String toString() {
return "H2";
}
});
// Derby
retVal.add(new Supplier<TestDatabaseDetails>() {
@Override
public TestDatabaseDetails get() {
String url = "jdbc:derby:memory:" + DATABASE_NAME + ourDatabaseUrl++ + ";create=true";
DriverTypeEnum.ConnectionProperties connectionProperties = DriverTypeEnum.DERBY_EMBEDDED.newConnectionProperties(url, "SA", "SA");
BasicDataSource dataSource = new BasicDataSource();
dataSource.setUrl(url);
dataSource.setUsername("SA");
dataSource.setPassword("SA");
dataSource.setDriverClassName(DriverTypeEnum.DERBY_EMBEDDED.getDriverClassName());
FlywayMigrator migrator = new FlywayMigrator(SchemaMigrator.HAPI_FHIR_MIGRATION_TABLENAME, dataSource, DriverTypeEnum.DERBY_EMBEDDED);
return new TestDatabaseDetails(url, connectionProperties, dataSource, migrator);
}
@Override
public String toString() {
return "Derby";
}
});
return retVal;
}
}

View File

@ -7,11 +7,16 @@ import org.junit.Test;
import org.springframework.jdbc.core.JdbcTemplate;
import java.util.Map;
import java.util.function.Supplier;
import static org.junit.Assert.assertEquals;
public class CalculateHashesTest extends BaseTest {
public CalculateHashesTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testCreateHashes() {
executeSql("create table HFJ_SPIDX_TOKEN (SP_ID bigint not null, SP_MISSING boolean, SP_NAME varchar(100) not null, RES_ID bigint, RES_TYPE varchar(255) not null, SP_UPDATED timestamp, HASH_IDENTITY bigint, HASH_SYS bigint, HASH_SYS_AND_VALUE bigint, HASH_VALUE bigint, SP_SYSTEM varchar(200), SP_VALUE varchar(200), primary key (SP_ID))");

View File

@ -4,12 +4,17 @@ import ca.uhn.fhir.jpa.migrate.JdbcUtils;
import org.junit.Test;
import java.sql.SQLException;
import java.util.function.Supplier;
import static org.hamcrest.Matchers.containsInAnyOrder;
import static org.junit.Assert.assertThat;
public class DropColumnTest extends BaseTest {
public DropColumnTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testDropColumn() throws SQLException {
executeSql("create table SOMETABLE (PID bigint not null, TEXTCOL varchar(255))");

View File

@ -4,6 +4,7 @@ import ca.uhn.fhir.jpa.migrate.JdbcUtils;
import org.junit.Test;
import java.sql.SQLException;
import java.util.function.Supplier;
import static org.hamcrest.Matchers.empty;
import static org.hamcrest.collection.IsCollectionWithSize.hasSize;
@ -11,6 +12,10 @@ import static org.junit.Assert.assertThat;
public class DropForeignKeyTaskTest extends BaseTest {
public DropForeignKeyTaskTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testDropForeignKey() throws SQLException {
executeSql("create table PARENT (PID bigint not null, TEXTCOL varchar(255), primary key (PID))");
@ -19,7 +24,7 @@ public class DropForeignKeyTaskTest extends BaseTest {
assertThat(JdbcUtils.getForeignKeys(getConnectionProperties(), "PARENT", "CHILD"), hasSize(1));
DropForeignKeyTask task = new DropForeignKeyTask("1", "1");
DropForeignKeyTask task = new DropForeignKeyTask("1", "1");
task.setTableName("CHILD");
task.setParentTableName("PARENT");
task.setConstraintName("FK_MOM");

View File

@ -7,6 +7,7 @@ import ca.uhn.fhir.util.VersionEnum;
import org.junit.Test;
import java.sql.SQLException;
import java.util.function.Supplier;
import static org.hamcrest.Matchers.containsInAnyOrder;
import static org.hamcrest.Matchers.empty;
@ -15,6 +16,10 @@ import static org.junit.Assert.assertThat;
public class DropIdGeneratorTaskTest extends BaseTest {
public DropIdGeneratorTaskTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testAddIdGenerator() throws SQLException {
executeSql("create sequence SEQ_FOO start with 1 increment by 50");

View File

@ -4,12 +4,17 @@ import ca.uhn.fhir.jpa.migrate.JdbcUtils;
import org.junit.Test;
import java.sql.SQLException;
import java.util.function.Supplier;
import static org.hamcrest.Matchers.contains;
import static org.junit.Assert.assertThat;
public class DropIndexTest extends BaseTest {
public DropIndexTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testIndexAlreadyExists() throws SQLException {
executeSql("create table SOMETABLE (PID bigint not null, TEXTCOL varchar(255))");

View File

@ -4,6 +4,7 @@ import ca.uhn.fhir.jpa.migrate.JdbcUtils;
import org.junit.Test;
import java.sql.SQLException;
import java.util.function.Supplier;
import static org.hamcrest.Matchers.*;
import static org.hamcrest.core.IsNot.not;
@ -11,6 +12,10 @@ import static org.junit.Assert.assertThat;
public class DropTableTest extends BaseTest {
public DropTableTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testDropExistingTable() throws SQLException {
executeSql("create table SOMETABLE (PID bigint not null, TEXTCOL varchar(255))");
@ -32,7 +37,7 @@ public class DropTableTest extends BaseTest {
public void testDropTableWithForeignKey() throws SQLException {
executeSql("create table FOREIGNTABLE (PID bigint not null, TEXTCOL varchar(255), primary key (PID))");
executeSql("create table SOMETABLE (PID bigint not null, REMOTEPID bigint not null, primary key (PID))");
executeSql("alter table SOMETABLE add constraint FK_MYFK foreign key (REMOTEPID) references FOREIGNTABLE;");
executeSql("alter table SOMETABLE add constraint FK_MYFK foreign key (REMOTEPID) references FOREIGNTABLE");
DropTableTask task = new DropTableTask("1", "1");
task.setTableName("SOMETABLE");

View File

@ -6,11 +6,16 @@ import org.junit.Test;
import java.util.List;
import java.util.Map;
import java.util.function.Supplier;
import static org.junit.Assert.assertEquals;
public class ExecuteRawSqlTaskTest extends BaseTest {
public ExecuteRawSqlTaskTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testExecuteSql() {
executeSql("create table SOMETABLE (PID bigint not null, TEXTCOL varchar(255))");

View File

@ -9,12 +9,17 @@ import org.junit.Test;
import java.sql.SQLException;
import java.util.Collections;
import java.util.List;
import java.util.function.Supplier;
import static org.hamcrest.Matchers.containsInAnyOrder;
import static org.junit.Assert.assertThat;
public class InitializeSchemaTaskTest extends BaseTest {
public InitializeSchemaTaskTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testInitializeTwice() throws SQLException {
InitializeSchemaTask task = new InitializeSchemaTask("1", "1", new TestProvider());
@ -62,7 +67,7 @@ public class InitializeSchemaTaskTest extends BaseTest {
}
private int size() {
return getSqlStatements(DriverTypeEnum.H2_EMBEDDED).size();
return getSqlStatements(getDriverType()).size();
}
// This could be stricter, but we don't want this to be brittle.

View File

@ -1,17 +1,27 @@
package ca.uhn.fhir.jpa.migrate.taskdef;
import ca.uhn.fhir.jpa.migrate.DriverTypeEnum;
import ca.uhn.fhir.jpa.migrate.JdbcUtils;
import org.flywaydb.core.internal.command.DbMigrate;
import org.junit.Test;
import java.sql.SQLException;
import java.util.function.Supplier;
import static org.hamcrest.Matchers.containsInAnyOrder;
import static org.junit.Assert.*;
public class ModifyColumnTest extends BaseTest {
public ModifyColumnTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testColumnWithJdbcTypeClob() throws SQLException {
if (getDriverType() == DriverTypeEnum.DERBY_EMBEDDED) {
return;
}
executeSql("create table SOMETABLE (TEXTCOL clob)");
ModifyColumnTask task = new ModifyColumnTask("1", "1");
@ -126,7 +136,7 @@ public class ModifyColumnTest extends BaseTest {
assertFalse(JdbcUtils.isColumnNullable(getConnectionProperties(), "SOMETABLE", "PID"));
assertFalse(JdbcUtils.isColumnNullable(getConnectionProperties(), "SOMETABLE", "DATECOL"));
assertEquals(new JdbcUtils.ColumnType(BaseTableColumnTypeTask.ColumnTypeEnum.LONG, 19), JdbcUtils.getColumnType(getConnectionProperties(), "SOMETABLE", "PID"));
assertEquals(new JdbcUtils.ColumnType(BaseTableColumnTypeTask.ColumnTypeEnum.DATE_TIMESTAMP, 26), JdbcUtils.getColumnType(getConnectionProperties(), "SOMETABLE", "DATECOL"));
assertEquals(BaseTableColumnTypeTask.ColumnTypeEnum.DATE_TIMESTAMP, JdbcUtils.getColumnType(getConnectionProperties(), "SOMETABLE", "DATECOL").getColumnTypeEnum());
getMigrator().setNoColumnShrink(true);
@ -152,7 +162,7 @@ public class ModifyColumnTest extends BaseTest {
assertTrue(JdbcUtils.isColumnNullable(getConnectionProperties(), "SOMETABLE", "PID"));
assertTrue(JdbcUtils.isColumnNullable(getConnectionProperties(), "SOMETABLE", "DATECOL"));
assertEquals(new JdbcUtils.ColumnType(BaseTableColumnTypeTask.ColumnTypeEnum.LONG, 19), JdbcUtils.getColumnType(getConnectionProperties(), "SOMETABLE", "PID"));
assertEquals(new JdbcUtils.ColumnType(BaseTableColumnTypeTask.ColumnTypeEnum.DATE_TIMESTAMP, 26), JdbcUtils.getColumnType(getConnectionProperties(), "SOMETABLE", "DATECOL"));
assertEquals(BaseTableColumnTypeTask.ColumnTypeEnum.DATE_TIMESTAMP, JdbcUtils.getColumnType(getConnectionProperties(), "SOMETABLE", "DATECOL").getColumnTypeEnum());
// Make sure additional migrations don't crash
getMigrator().migrate();

View File

@ -6,12 +6,19 @@ import org.junit.Test;
import java.sql.SQLException;
import java.util.Set;
import java.util.function.Supplier;
import static org.hamcrest.Matchers.containsInAnyOrder;
import static org.junit.Assert.*;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertThat;
import static org.junit.Assert.fail;
public class RenameColumnTaskTest extends BaseTest {
public RenameColumnTaskTest(Supplier<TestDatabaseDetails> theTestDatabaseDetails) {
super(theTestDatabaseDetails);
}
@Test
public void testColumnAlreadyExists() throws SQLException {
executeSql("create table SOMETABLE (PID bigint not null, TEXTCOL varchar(255))");

View File

@ -51,6 +51,7 @@ import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Set;
import static org.apache.commons.lang3.StringUtils.isNotBlank;
@ -153,6 +154,22 @@ public class ReadMethodBinding extends BaseResourceReturningMethodBinding {
@Override
public IBundleProvider invokeServer(IRestfulServer<?> theServer, RequestDetails theRequest, Object[] theMethodParams) throws InvalidRequestException, InternalErrorException {
IIdType requestId = theRequest.getId();
FhirContext ctx = theRequest.getServer().getFhirContext();
String[] invalidQueryStringParams = new String[]{Constants.PARAM_CONTAINED, Constants.PARAM_COUNT, Constants.PARAM_INCLUDE, Constants.PARAM_REVINCLUDE, Constants.PARAM_SORT, Constants.PARAM_SEARCH_TOTAL_MODE};
List<String> invalidQueryStringParamsInRequest = new ArrayList<>();
Set<String> queryStringParamsInRequest = theRequest.getParameters().keySet();
for (String queryStringParamName : queryStringParamsInRequest) {
String lowercaseQueryStringParamName = queryStringParamName.toLowerCase();
if (StringUtils.startsWithAny(lowercaseQueryStringParamName, invalidQueryStringParams)) {
invalidQueryStringParamsInRequest.add(queryStringParamName);
}
}
if (!invalidQueryStringParamsInRequest.isEmpty()) {
throw new InvalidRequestException(ctx.getLocalizer().getMessage(ReadMethodBinding.class, "invalidParamsInRequest", invalidQueryStringParamsInRequest));
}
theMethodParams[myIdIndex] = ParameterUtil.convertIdToType(requestId, myIdParameterType);
@ -201,7 +218,7 @@ public class ReadMethodBinding extends BaseResourceReturningMethodBinding {
}
} // if we have at least 1 result
return retVal;
}

View File

@ -4,6 +4,7 @@ import static org.hamcrest.Matchers.stringContainsInOrder;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertThat;
import java.io.InputStream;
import java.nio.charset.StandardCharsets;
import java.util.concurrent.TimeUnit;
@ -64,6 +65,131 @@ public class ReadDstu3Test {
"</Patient>"));
}
@Test
public void testInvalidQueryParamsInRead() throws Exception {
CloseableHttpResponse status;
HttpGet httpGet;
httpGet = new HttpGet("http://localhost:" + ourPort + "/Patient/2?_contained=both&_format=xml&_pretty=true");
status = ourClient.execute(httpGet);
try (InputStream inputStream = status.getEntity().getContent()) {
assertEquals(400, status.getStatusLine().getStatusCode());
String responseContent = IOUtils.toString(inputStream, StandardCharsets.UTF_8);
assertThat(responseContent, stringContainsInOrder(
"<OperationOutcome xmlns=\"http://hl7.org/fhir\">",
" <issue>",
" <severity value=\"error\"/>",
" <code value=\"processing\"/>",
" <diagnostics value=\"Invalid query parameter(s) for this request: &quot;[_contained]&quot;\"/>",
" </issue>",
"</OperationOutcome>"
));
}
httpGet = new HttpGet("http://localhost:" + ourPort + "/Patient/2?_containedType=contained&_format=xml&_pretty=true");
status = ourClient.execute(httpGet);
try (InputStream inputStream = status.getEntity().getContent()) {
assertEquals(400, status.getStatusLine().getStatusCode());
String responseContent = IOUtils.toString(inputStream, StandardCharsets.UTF_8);
assertThat(responseContent, stringContainsInOrder(
"<OperationOutcome xmlns=\"http://hl7.org/fhir\">",
" <issue>",
" <severity value=\"error\"/>",
" <code value=\"processing\"/>",
" <diagnostics value=\"Invalid query parameter(s) for this request: &quot;[_containedType]&quot;\"/>",
" </issue>",
"</OperationOutcome>"
));
}
httpGet = new HttpGet("http://localhost:" + ourPort + "/Patient/2?_count=10&_format=xml&_pretty=true");
status = ourClient.execute(httpGet);
try (InputStream inputStream = status.getEntity().getContent()) {
assertEquals(400, status.getStatusLine().getStatusCode());
String responseContent = IOUtils.toString(inputStream, StandardCharsets.UTF_8);
assertThat(responseContent, stringContainsInOrder(
"<OperationOutcome xmlns=\"http://hl7.org/fhir\">",
" <issue>",
" <severity value=\"error\"/>",
" <code value=\"processing\"/>",
" <diagnostics value=\"Invalid query parameter(s) for this request: &quot;[_count]&quot;\"/>",
" </issue>",
"</OperationOutcome>"
));
}
httpGet = new HttpGet("http://localhost:" + ourPort + "/Patient/2?_include=Patient:organization&_format=xml&_pretty=true");
status = ourClient.execute(httpGet);
try (InputStream inputStream = status.getEntity().getContent()) {
assertEquals(400, status.getStatusLine().getStatusCode());
String responseContent = IOUtils.toString(inputStream, StandardCharsets.UTF_8);
assertThat(responseContent, stringContainsInOrder(
"<OperationOutcome xmlns=\"http://hl7.org/fhir\">",
" <issue>",
" <severity value=\"error\"/>",
" <code value=\"processing\"/>",
" <diagnostics value=\"Invalid query parameter(s) for this request: &quot;[_include]&quot;\"/>",
" </issue>",
"</OperationOutcome>"
));
}
httpGet = new HttpGet("http://localhost:" + ourPort + "/Patient/2?_revinclude=Provenance:target&_format=xml&_pretty=true");
status = ourClient.execute(httpGet);
try (InputStream inputStream = status.getEntity().getContent()) {
assertEquals(400, status.getStatusLine().getStatusCode());
String responseContent = IOUtils.toString(inputStream, StandardCharsets.UTF_8);
assertThat(responseContent, stringContainsInOrder(
"<OperationOutcome xmlns=\"http://hl7.org/fhir\">",
" <issue>",
" <severity value=\"error\"/>",
" <code value=\"processing\"/>",
" <diagnostics value=\"Invalid query parameter(s) for this request: &quot;[_revinclude]&quot;\"/>",
" </issue>",
"</OperationOutcome>"
));
}
httpGet = new HttpGet("http://localhost:" + ourPort + "/Patient/2?_sort=family&_format=xml&_pretty=true");
status = ourClient.execute(httpGet);
try (InputStream inputStream = status.getEntity().getContent()) {
assertEquals(400, status.getStatusLine().getStatusCode());
String responseContent = IOUtils.toString(inputStream, StandardCharsets.UTF_8);
assertThat(responseContent, stringContainsInOrder(
"<OperationOutcome xmlns=\"http://hl7.org/fhir\">",
" <issue>",
" <severity value=\"error\"/>",
" <code value=\"processing\"/>",
" <diagnostics value=\"Invalid query parameter(s) for this request: &quot;[_sort]&quot;\"/>",
" </issue>",
"</OperationOutcome>"
));
}
httpGet = new HttpGet("http://localhost:" + ourPort + "/Patient/2?_total=accurate&_format=xml&_pretty=true");
status = ourClient.execute(httpGet);
try (InputStream inputStream = status.getEntity().getContent()) {
assertEquals(400, status.getStatusLine().getStatusCode());
String responseContent = IOUtils.toString(inputStream, StandardCharsets.UTF_8);
assertThat(responseContent, stringContainsInOrder(
"<OperationOutcome xmlns=\"http://hl7.org/fhir\">",
" <issue>",
" <severity value=\"error\"/>",
" <code value=\"processing\"/>",
" <diagnostics value=\"Invalid query parameter(s) for this request: &quot;[_total]&quot;\"/>",
" </issue>",
"</OperationOutcome>"
));
}
}
@Test
public void testIfModifiedSince() throws Exception {