diff --git a/hapi-fhir-docs/src/main/resources/ca/uhn/hapi/fhir/changelog/6_8_0/4992-search-paramter-character-limit-error.yaml b/hapi-fhir-docs/src/main/resources/ca/uhn/hapi/fhir/changelog/6_8_0/4992-search-paramter-character-limit-error.yaml new file mode 100644 index 00000000000..4f5320ec7a3 --- /dev/null +++ b/hapi-fhir-docs/src/main/resources/ca/uhn/hapi/fhir/changelog/6_8_0/4992-search-paramter-character-limit-error.yaml @@ -0,0 +1,5 @@ +--- +type: fix +issue: 4992 +title: "Previously, when searching on a resource identifier or similar search field with over 200 characters, a HAPI-1238 error would be returned. + This has been fixed." diff --git a/hapi-fhir-docs/src/main/resources/ca/uhn/hapi/fhir/changelog/6_8_0/9999-something-something.yaml b/hapi-fhir-docs/src/main/resources/ca/uhn/hapi/fhir/changelog/6_8_0/9999-something-something.yaml deleted file mode 100644 index 953d776ff4f..00000000000 --- a/hapi-fhir-docs/src/main/resources/ca/uhn/hapi/fhir/changelog/6_8_0/9999-something-something.yaml +++ /dev/null @@ -1,4 +0,0 @@ ---- -type: fix -issue: 9999 -title: "Something something" diff --git a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/migrate/tasks/HapiFhirJpaMigrationTasks.java b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/migrate/tasks/HapiFhirJpaMigrationTasks.java index 5be7e373cfe..89f5ad497e7 100644 --- a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/migrate/tasks/HapiFhirJpaMigrationTasks.java +++ b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/migrate/tasks/HapiFhirJpaMigrationTasks.java @@ -277,6 +277,13 @@ public class HapiFhirJpaMigrationTasks extends BaseMigrationTasks { .unique(false) .withColumns("CONCEPT_MAP_GRP_ELM_PID") .onlyAppliesToPlatforms(NON_AUTOMATIC_FK_INDEX_PLATFORMS); + + { + version.onTable("HFJ_SPIDX_TOKEN") + .modifyColumn("20230615.1", "SP_VALUE") + .nullable() + .withType(ColumnTypeEnum.STRING, ResourceIndexedSearchParamToken.MAX_LENGTH_VALUE); + } } protected void init660() { diff --git a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/search/builder/predicate/TokenPredicateBuilder.java b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/search/builder/predicate/TokenPredicateBuilder.java index 7f2d347109d..f51f53f93eb 100644 --- a/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/search/builder/predicate/TokenPredicateBuilder.java +++ b/hapi-fhir-jpaserver-base/src/main/java/ca/uhn/fhir/jpa/search/builder/predicate/TokenPredicateBuilder.java @@ -159,12 +159,12 @@ public class TokenPredicateBuilder extends BaseSearchParamPredicateBuilder { throw new IllegalArgumentException(Msg.code(1236) + "Invalid token type: " + nextParameter.getClass()); } - if (system != null && system.length() > ResourceIndexedSearchParamToken.MAX_LENGTH) { - throw new InvalidRequestException(Msg.code(1237) + "Parameter[" + paramName + "] has system (" + system.length() + ") that is longer than maximum allowed (" + ResourceIndexedSearchParamToken.MAX_LENGTH + "): " + system); + if (system != null && system.length() > ResourceIndexedSearchParamToken.MAX_LENGTH_SYSTEM) { + throw new InvalidRequestException(Msg.code(1237) + "Parameter[" + paramName + "] has system (" + system.length() + ") that is longer than maximum allowed (" + ResourceIndexedSearchParamToken.MAX_LENGTH_200 + "): " + system); } - if (code != null && code.length() > ResourceIndexedSearchParamToken.MAX_LENGTH) { - throw new InvalidRequestException(Msg.code(1238) + "Parameter[" + paramName + "] has code (" + code.length() + ") that is longer than maximum allowed (" + ResourceIndexedSearchParamToken.MAX_LENGTH + "): " + code); + if (code != null && code.length() > ResourceIndexedSearchParamToken.MAX_LENGTH_VALUE) { + throw new InvalidRequestException(Msg.code(1238) + "Parameter[" + paramName + "] has code (" + code.length() + ") that is longer than maximum allowed (" + ResourceIndexedSearchParamToken.MAX_LENGTH_VALUE + "): " + code); } /* diff --git a/hapi-fhir-jpaserver-model/src/main/java/ca/uhn/fhir/jpa/model/entity/ResourceIndexedSearchParamToken.java b/hapi-fhir-jpaserver-model/src/main/java/ca/uhn/fhir/jpa/model/entity/ResourceIndexedSearchParamToken.java index f029ec3fc20..6e8ca7af548 100644 --- a/hapi-fhir-jpaserver-model/src/main/java/ca/uhn/fhir/jpa/model/entity/ResourceIndexedSearchParamToken.java +++ b/hapi-fhir-jpaserver-model/src/main/java/ca/uhn/fhir/jpa/model/entity/ResourceIndexedSearchParamToken.java @@ -67,16 +67,19 @@ import static org.apache.commons.lang3.StringUtils.trim; }) public class ResourceIndexedSearchParamToken extends BaseResourceIndexedSearchParam { - public static final int MAX_LENGTH = 200; + public static final int MAX_LENGTH_200 = 200; + public static final int MAX_LENGTH_400 = 200; + public static final int MAX_LENGTH_SYSTEM = MAX_LENGTH_200; + public static final int MAX_LENGTH_VALUE = MAX_LENGTH_400; private static final long serialVersionUID = 1L; @FullTextField - @Column(name = "SP_SYSTEM", nullable = true, length = MAX_LENGTH) + @Column(name = "SP_SYSTEM", nullable = true, length = MAX_LENGTH_SYSTEM) public String mySystem; @FullTextField - @Column(name = "SP_VALUE", nullable = true, length = MAX_LENGTH) + @Column(name = "SP_VALUE", nullable = true, length = MAX_LENGTH_VALUE) private String myValue; @SuppressWarnings("unused") diff --git a/hapi-fhir-jpaserver-searchparam/src/main/java/ca/uhn/fhir/jpa/searchparam/extractor/BaseSearchParamExtractor.java b/hapi-fhir-jpaserver-searchparam/src/main/java/ca/uhn/fhir/jpa/searchparam/extractor/BaseSearchParamExtractor.java index 9065ea29abd..a2b1ce3522c 100644 --- a/hapi-fhir-jpaserver-searchparam/src/main/java/ca/uhn/fhir/jpa/searchparam/extractor/BaseSearchParamExtractor.java +++ b/hapi-fhir-jpaserver-searchparam/src/main/java/ca/uhn/fhir/jpa/searchparam/extractor/BaseSearchParamExtractor.java @@ -63,7 +63,6 @@ import org.hl7.fhir.instance.model.api.IBaseReference; import org.hl7.fhir.instance.model.api.IBaseResource; import org.hl7.fhir.instance.model.api.IIdType; import org.hl7.fhir.instance.model.api.IPrimitiveType; -import org.hl7.fhir.r5.model.Base; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.ApplicationContext; @@ -91,7 +90,6 @@ import static ca.uhn.fhir.rest.api.RestSearchParameterTypeEnum.DATE; import static ca.uhn.fhir.rest.api.RestSearchParameterTypeEnum.REFERENCE; import static org.apache.commons.lang3.StringUtils.isBlank; import static org.apache.commons.lang3.StringUtils.isNotBlank; -import static org.apache.commons.lang3.StringUtils.startsWith; import static org.apache.commons.lang3.StringUtils.trim; public abstract class BaseSearchParamExtractor implements ISearchParamExtractor { @@ -1475,11 +1473,11 @@ public abstract class BaseSearchParamExtractor implements ISearchParamExtractor String value = theValue; ResourceIndexedSearchParamToken nextEntity = null; if (isNotBlank(system) || isNotBlank(value)) { - if (system != null && system.length() > ResourceIndexedSearchParamToken.MAX_LENGTH) { - system = system.substring(0, ResourceIndexedSearchParamToken.MAX_LENGTH); + if (system != null && system.length() > ResourceIndexedSearchParamToken.MAX_LENGTH_SYSTEM) { + system = system.substring(0, ResourceIndexedSearchParamToken.MAX_LENGTH_SYSTEM); } - if (value != null && value.length() > ResourceIndexedSearchParamToken.MAX_LENGTH) { - value = value.substring(0, ResourceIndexedSearchParamToken.MAX_LENGTH); + if (value != null && value.length() > ResourceIndexedSearchParamToken.MAX_LENGTH_VALUE) { + value = value.substring(0, ResourceIndexedSearchParamToken.MAX_LENGTH_VALUE); } nextEntity = new ResourceIndexedSearchParamToken(myPartitionSettings, theResourceType, searchParamName, system, value); diff --git a/hapi-fhir-jpaserver-test-r4/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirSystemDaoR4SearchTest.java b/hapi-fhir-jpaserver-test-r4/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirSystemDaoR4SearchTest.java index 72d93de914d..c63043b0c3e 100644 --- a/hapi-fhir-jpaserver-test-r4/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirSystemDaoR4SearchTest.java +++ b/hapi-fhir-jpaserver-test-r4/src/test/java/ca/uhn/fhir/jpa/dao/r4/FhirSystemDaoR4SearchTest.java @@ -1,5 +1,6 @@ package ca.uhn.fhir.jpa.dao.r4; +import ca.uhn.fhir.jpa.model.entity.ResourceIndexedSearchParamToken; import ca.uhn.fhir.jpa.searchparam.SearchParameterMap; import ca.uhn.fhir.model.dstu2.resource.Observation; import ca.uhn.fhir.rest.api.server.IBundleProvider; @@ -9,7 +10,6 @@ import org.hl7.fhir.r4.model.Identifier; import org.hl7.fhir.r4.model.Organization; import org.junit.jupiter.api.Test; -import static org.hamcrest.MatcherAssert.assertThat; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertTrue; @@ -30,6 +30,9 @@ public class FhirSystemDaoR4SearchTest extends BaseJpaR4SystemTest { myOrganizationDao.create(organization, mySrd); + final List allSearchTokens = myResourceIndexedSearchParamTokenDao.findAll(); + assertTrue(allSearchTokens.stream().anyMatch(token -> identifierValue.equals(token.getValue()))); + final SearchParameterMap searchParameterMap = SearchParameterMap.newSynchronous(Observation.SP_IDENTIFIER, new TokenParam(identifierValue)); final IBundleProvider bundle = myOrganizationDao.search(searchParameterMap, mySrd); @@ -58,6 +61,9 @@ public class FhirSystemDaoR4SearchTest extends BaseJpaR4SystemTest { myOrganizationDao.create(organization, mySrd); + final List allSearchTokens = myResourceIndexedSearchParamTokenDao.findAll(); + assertTrue(allSearchTokens.stream().anyMatch(token -> identifierValue.equals(token.getValue()))); + final SearchParameterMap searchParameterMap = SearchParameterMap.newSynchronous(Observation.SP_IDENTIFIER, new TokenParam(identifierValue)); final IBundleProvider bundle = myOrganizationDao.search(searchParameterMap, mySrd);