* [#2176] RSQL filtering with exist/not-exist support Signed-off-by: Avgustin Marinov <Avgustin.Marinov@bosch.com> * [#2176] Big Refactoring * RSQL: all maps with joins with on --------- Signed-off-by: Avgustin Marinov <Avgustin.Marinov@bosch.com>
This commit is contained in:
@@ -15,6 +15,8 @@ import static org.assertj.core.api.Assertions.assertThatExceptionOfType;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collections;
|
||||
|
||||
import jakarta.persistence.EntityManager;
|
||||
|
||||
import io.qameta.allure.Description;
|
||||
import io.qameta.allure.Feature;
|
||||
import io.qameta.allure.Story;
|
||||
@@ -23,20 +25,29 @@ import org.eclipse.hawkbit.repository.SoftwareModuleFields;
|
||||
import org.eclipse.hawkbit.repository.exception.RSQLParameterSyntaxException;
|
||||
import org.eclipse.hawkbit.repository.exception.RSQLParameterUnsupportedFieldException;
|
||||
import org.eclipse.hawkbit.repository.jpa.AbstractJpaIntegrationTest;
|
||||
import org.eclipse.hawkbit.repository.jpa.model.JpaDistributionSet;
|
||||
import org.eclipse.hawkbit.repository.model.DistributionSet;
|
||||
import org.eclipse.hawkbit.repository.model.DistributionSetTag;
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModule;
|
||||
import org.eclipse.hawkbit.repository.rsql.VirtualPropertyReplacer;
|
||||
import org.eclipse.hawkbit.repository.test.util.TestdataFactory;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.data.domain.Page;
|
||||
import org.springframework.data.domain.PageRequest;
|
||||
import org.springframework.orm.jpa.vendor.Database;
|
||||
|
||||
@Feature("Component Tests - Repository")
|
||||
@Story("RSQL filter distribution set")
|
||||
@SuppressWarnings("java:S6813") // constructor injects are not possible for test classes
|
||||
class RSQLDistributionSetFieldTest extends AbstractJpaIntegrationTest {
|
||||
|
||||
@Autowired
|
||||
protected VirtualPropertyReplacer virtualPropertyReplacer;
|
||||
@Autowired
|
||||
protected EntityManager entityManager;
|
||||
|
||||
private DistributionSet ds;
|
||||
private SoftwareModule sm;
|
||||
|
||||
@@ -190,11 +201,14 @@ class RSQLDistributionSetFieldTest extends AbstractJpaIntegrationTest {
|
||||
assertRSQLQuery(DistributionSetFields.METADATA.name() + ".key*==value.dot", 0);
|
||||
assertRSQLQuery(DistributionSetFields.METADATA.name() + ".*==value.dot", 0);
|
||||
assertRSQLQuery(DistributionSetFields.METADATA.name() + "..==value.dot", 0);
|
||||
assertRSQLQueryThrowsException(DistributionSetFields.METADATA.name() + ".==value.dot",
|
||||
assertRSQLQueryThrowsException(
|
||||
DistributionSetFields.METADATA.name() + ".==value.dot",
|
||||
RSQLParameterUnsupportedFieldException.class);
|
||||
assertRSQLQueryThrowsException(DistributionSetFields.METADATA.name() + "*==value.dot",
|
||||
assertRSQLQueryThrowsException(
|
||||
DistributionSetFields.METADATA.name() + "*==value.dot",
|
||||
RSQLParameterUnsupportedFieldException.class);
|
||||
assertRSQLQueryThrowsException(DistributionSetFields.METADATA.name() + "==value.dot",
|
||||
assertRSQLQueryThrowsException(
|
||||
DistributionSetFields.METADATA.name() + "==value.dot",
|
||||
RSQLParameterUnsupportedFieldException.class);
|
||||
|
||||
}
|
||||
@@ -206,18 +220,15 @@ class RSQLDistributionSetFieldTest extends AbstractJpaIntegrationTest {
|
||||
assertThat(countAll).as("Found entity size is wrong").isEqualTo(expectedEntity);
|
||||
}
|
||||
|
||||
private <T extends Throwable> void assertRSQLQueryThrowsException(final String rsqlParam,
|
||||
final Class<T> expectedException) {
|
||||
private <T extends Throwable> void assertRSQLQueryThrowsException(final String rsqlParam, final Class<T> expectedException) {
|
||||
assertThatExceptionOfType(expectedException)
|
||||
.isThrownBy(() -> RSQLUtility.validateRsqlFor(rsqlParam, DistributionSetFields.class));
|
||||
.isThrownBy(() -> RSQLUtility.validateRsqlFor(
|
||||
rsqlParam, DistributionSetFields.class, JpaDistributionSet.class, virtualPropertyReplacer, entityManager));
|
||||
}
|
||||
|
||||
private DistributionSet createDistributionSetWithMetadata(final String metadataKeyName,
|
||||
final String metadataValue) {
|
||||
private DistributionSet createDistributionSetWithMetadata(final String metadataKeyName, final String metadataValue) {
|
||||
final DistributionSet distributionSet = testdataFactory.createDistributionSet();
|
||||
createDistributionSetMetadata(distributionSet.getId(),
|
||||
entityFactory.generateDsMetadata(metadataKeyName, metadataValue));
|
||||
createDistributionSetMetadata(distributionSet.getId(), entityFactory.generateDsMetadata(metadataKeyName, metadataValue));
|
||||
return distributionSet;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
@@ -11,35 +11,44 @@ package org.eclipse.hawkbit.repository.jpa.rsql;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.assertj.core.api.Assertions.assertThatExceptionOfType;
|
||||
import static org.junit.jupiter.api.Assertions.fail;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import jakarta.persistence.EntityManager;
|
||||
|
||||
import io.qameta.allure.Description;
|
||||
import io.qameta.allure.Feature;
|
||||
import io.qameta.allure.Story;
|
||||
import org.assertj.core.util.Maps;
|
||||
import org.eclipse.hawkbit.repository.TargetFields;
|
||||
import org.eclipse.hawkbit.repository.TargetTypeFields;
|
||||
import org.eclipse.hawkbit.repository.exception.RSQLParameterUnsupportedFieldException;
|
||||
import org.eclipse.hawkbit.repository.jpa.AbstractJpaIntegrationTest;
|
||||
import org.eclipse.hawkbit.repository.jpa.model.JpaTarget;
|
||||
import org.eclipse.hawkbit.repository.model.DistributionSet;
|
||||
import org.eclipse.hawkbit.repository.model.Target;
|
||||
import org.eclipse.hawkbit.repository.model.TargetTag;
|
||||
import org.eclipse.hawkbit.repository.model.TargetType;
|
||||
import org.eclipse.hawkbit.repository.rsql.VirtualPropertyReplacer;
|
||||
import org.eclipse.hawkbit.repository.test.util.TestdataFactory;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.data.domain.Slice;
|
||||
|
||||
@Feature("Component Tests - Repository")
|
||||
@Story("RSQL filter target")
|
||||
@SuppressWarnings("java:S6813") // constructor injects are not possible for test classes
|
||||
class RSQLTargetFieldTest extends AbstractJpaIntegrationTest {
|
||||
|
||||
private static final String OR = ",";
|
||||
private static final String AND = ";";
|
||||
|
||||
@Autowired
|
||||
protected VirtualPropertyReplacer virtualPropertyReplacer;
|
||||
@Autowired
|
||||
protected EntityManager entityManager;
|
||||
|
||||
private Target target;
|
||||
private Target target2;
|
||||
private TargetType targetType1;
|
||||
@@ -47,45 +56,6 @@ class RSQLTargetFieldTest extends AbstractJpaIntegrationTest {
|
||||
|
||||
@BeforeEach
|
||||
void setupBeforeTest() {
|
||||
final DistributionSet ds = testdataFactory.createDistributionSet("AssignedDs");
|
||||
|
||||
final Map<String, String> attributes = new HashMap<>();
|
||||
|
||||
target = targetManagement.create(entityFactory.target().create().controllerId("targetId123")
|
||||
.name("targetName123").description("targetDesc123"));
|
||||
attributes.put("revision", "1.1");
|
||||
target = controllerManagement.updateControllerAttributes(target.getControllerId(), attributes, null);
|
||||
target = controllerManagement.findOrRegisterTargetIfItDoesNotExist(target.getControllerId(), LOCALHOST);
|
||||
createTargetMetadata(target.getControllerId(), entityFactory.generateTargetMetadata("metaKey", "metaValue"));
|
||||
|
||||
target2 = targetManagement
|
||||
.create(entityFactory.target().create().controllerId("targetId1234").description("targetId1234"));
|
||||
attributes.put("revision", "1.2");
|
||||
|
||||
target2 = controllerManagement.updateControllerAttributes(target2.getControllerId(), attributes, null);
|
||||
target2 = controllerManagement.findOrRegisterTargetIfItDoesNotExist(target2.getControllerId(), LOCALHOST);
|
||||
createTargetMetadata(target2.getControllerId(), entityFactory.generateTargetMetadata("metaKey", "value"));
|
||||
|
||||
final Target target3 = testdataFactory.createTarget("targetId1235");
|
||||
final Target target4 = testdataFactory.createTarget("targetId1236");
|
||||
testdataFactory.createTarget("targetId1237");
|
||||
|
||||
final TargetTag targetTag = targetTagManagement.create(entityFactory.tag().create().name("Tag1"));
|
||||
final TargetTag targetTag2 = targetTagManagement.create(entityFactory.tag().create().name("Tag2"));
|
||||
final TargetTag targetTag3 = targetTagManagement.create(entityFactory.tag().create().name("Tag3"));
|
||||
targetTagManagement.create(entityFactory.tag().create().name("Tag4"));
|
||||
|
||||
targetManagement.assignTag(Arrays.asList(target.getControllerId(), target2.getControllerId()),
|
||||
targetTag.getId());
|
||||
|
||||
targetManagement.assignTag(Arrays.asList(target3.getControllerId(), target4.getControllerId()),
|
||||
targetTag2.getId());
|
||||
targetManagement.assignTag(
|
||||
Arrays.asList(target.getControllerId(), target3.getControllerId(), target4.getControllerId()),
|
||||
targetTag3.getId());
|
||||
|
||||
assignDistributionSet(ds.getId(), target.getControllerId());
|
||||
|
||||
targetType1 = targetTypeManagement
|
||||
.create(entityFactory.targetType().create()
|
||||
.name("Type1").description("Desc. Type1")
|
||||
@@ -95,8 +65,43 @@ class RSQLTargetFieldTest extends AbstractJpaIntegrationTest {
|
||||
.name("Type2").description("Desc. Type2")
|
||||
.key("Type2.key"));
|
||||
|
||||
final DistributionSet ds = testdataFactory.createDistributionSet("AssignedDs");
|
||||
|
||||
final TargetTag targetTag = targetTagManagement.create(entityFactory.tag().create().name("Tag1"));
|
||||
final TargetTag targetTag2 = targetTagManagement.create(entityFactory.tag().create().name("Tag2"));
|
||||
final TargetTag targetTag3 = targetTagManagement.create(entityFactory.tag().create().name("Tag3"));
|
||||
targetTagManagement.create(entityFactory.tag().create().name("Tag4"));
|
||||
|
||||
target = targetManagement.create(
|
||||
entityFactory.target().create()
|
||||
.controllerId("targetId123")
|
||||
.name("targetName123")
|
||||
.description("targetDesc123"));
|
||||
target = controllerManagement.updateControllerAttributes(target.getControllerId(), Map.of("revision", "1.1"), null);
|
||||
target = controllerManagement.findOrRegisterTargetIfItDoesNotExist(target.getControllerId(), LOCALHOST);
|
||||
createTargetMetadata(target.getControllerId(), entityFactory.generateTargetMetadata("metaKey", "metaValue"));
|
||||
assignDistributionSet(ds.getId(), target.getControllerId());
|
||||
targetManagement.assignType(target.getControllerId(), targetType1.getId());
|
||||
|
||||
target2 = targetManagement.create(
|
||||
entityFactory.target().create()
|
||||
.controllerId("targetId1234")
|
||||
.description("targetId1234"));
|
||||
target2 = controllerManagement.updateControllerAttributes(target2.getControllerId(), Map.of("revision", "1.2"), null);
|
||||
targetManagement.assignType(target2.getControllerId(), targetType2.getId());
|
||||
createTargetMetadata(target2.getControllerId(), entityFactory.generateTargetMetadata("metaKey", "value"));
|
||||
target2 = controllerManagement.findOrRegisterTargetIfItDoesNotExist(target2.getControllerId(), LOCALHOST);
|
||||
targetManagement.assignTag(Arrays.asList(target.getControllerId(), target2.getControllerId()), targetTag.getId());
|
||||
|
||||
final Target target3 = testdataFactory.createTarget("targetId1235");
|
||||
|
||||
final Target target4 = testdataFactory.createTarget("targetId1236");
|
||||
testdataFactory.createTarget("targetId1237");
|
||||
targetManagement.assignTag(Arrays.asList(target3.getControllerId(), target4.getControllerId()), targetTag2.getId());
|
||||
|
||||
targetManagement.assignTag(
|
||||
Arrays.asList(target.getControllerId(), target3.getControllerId(), target4.getControllerId()),
|
||||
targetTag3.getId());
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -159,8 +164,38 @@ class RSQLTargetFieldTest extends AbstractJpaIntegrationTest {
|
||||
@Test
|
||||
@Description("Test filter target by attribute")
|
||||
void testFilterByAttribute() {
|
||||
controllerManagement.updateControllerAttributes(testdataFactory.createTarget().getControllerId(),
|
||||
Maps.newHashMap("test.dot", "value.dot"), null);
|
||||
controllerManagement.updateControllerAttributes(
|
||||
testdataFactory.createTarget().getControllerId(),
|
||||
Map.of(
|
||||
"test.dot", "value.dot",
|
||||
"test.null", "null"),
|
||||
null);
|
||||
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.dot>=value.dos", 1);
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.dot==value.dot", 1);
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.null==null", 1); // "null" check
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.n/a==null", 0); // "null" check
|
||||
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.dot=is=value.dot", 1);
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.null=is=null", 5); // null check
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.n/a=is=null", 1 + 5); // null check
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.dot=eq=value.dot", 1);
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.null=eq=null", 5); // null check
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.n/a=eq=null", 1 + 5); // null check
|
||||
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.dot!=value.dot", 0);
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.null!=null", 0); // "null" check
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.null!=null2", 1); // value check
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.n/a!=null", 0); // "null" check
|
||||
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.dot=not=value.dot", 5);
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.null=not=null", 1); // null check
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.null=not=null2", 1 + 5); // value check
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.n/a=not=null", 0); // null check
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.dot=ne=value.dot", 5);
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.null=ne=null", 1); // null check
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.null=ne=null2", 1 + 5); // value check
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.n/a=ne=null", 0); // null check
|
||||
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".revision==1.1", 1);
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".revision!=1.1", 1);
|
||||
@@ -168,7 +203,6 @@ class RSQLTargetFieldTest extends AbstractJpaIntegrationTest {
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".revision==noExist*", 0);
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".revision=in=(1.1,notexist)", 1);
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".revision=out=(1.1)", 1);
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".test.dot==value.dot", 1);
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".key.dot*==value.dot", 0);
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".key.*==value.dot", 0);
|
||||
assertRSQLQuery(TargetFields.ATTRIBUTE.name() + ".key.==value.dot", 0);
|
||||
@@ -196,10 +230,8 @@ class RSQLTargetFieldTest extends AbstractJpaIntegrationTest {
|
||||
assertRSQLQuery(TargetFields.ASSIGNEDDS.name() + ".version==" + TestdataFactory.DEFAULT_VERSION, 1);
|
||||
assertRSQLQuery(TargetFields.ASSIGNEDDS.name() + ".version==*1*", 1);
|
||||
assertRSQLQuery(TargetFields.ASSIGNEDDS.name() + ".version==noExist*", 0);
|
||||
assertRSQLQuery(
|
||||
TargetFields.ASSIGNEDDS.name() + ".version=in=(" + TestdataFactory.DEFAULT_VERSION + ",notexist)", 1);
|
||||
assertRSQLQuery(
|
||||
TargetFields.ASSIGNEDDS.name() + ".version=out=(" + TestdataFactory.DEFAULT_VERSION + ",notexist)", 4);
|
||||
assertRSQLQuery(TargetFields.ASSIGNEDDS.name() + ".version=in=(" + TestdataFactory.DEFAULT_VERSION + ",notexist)", 1);
|
||||
assertRSQLQuery(TargetFields.ASSIGNEDDS.name() + ".version=out=(" + TestdataFactory.DEFAULT_VERSION + ",notexist)", 4);
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -238,18 +270,41 @@ class RSQLTargetFieldTest extends AbstractJpaIntegrationTest {
|
||||
@Test
|
||||
@Description("Test filter target by metadata")
|
||||
void testFilterByMetadata() {
|
||||
createTargetMetadata(testdataFactory.createTarget().getControllerId(),
|
||||
entityFactory.generateTargetMetadata("key.dot", "value.dot"));
|
||||
createTargetMetadata(testdataFactory.createTarget().getControllerId(), entityFactory.generateTargetMetadata("key.dot", "value.dot"));
|
||||
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey==metaValue", 1);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey==null", 0); // "null" check
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey==*v*", 2);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey==noExist*", 0);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=in=(metaValue,notexist)", 1);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=out=(metaValue,notexist)", 1);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".notExist==metaValue", 0);
|
||||
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=is=metaValue", 1);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=is=null", 4); // null check (1 of the initial five has)
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=is=*v*", 2);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=is=noExist*", 0);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".notExist=is=null", 1 + 5); // null check
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=eq=metaValue", 1);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=eq=null", 4); // null check (1 of the initial five has)
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=eq=*v*", 2);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=eq=noExist*", 0);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".notExist=eq=null", 1 + 5); // null check
|
||||
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey!=metaValue", 1);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey!=null", 2);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".notExist!=metaValue", 0);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey!=notExist", 2);
|
||||
//
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=not=metaValue", 1 + 4);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=not=null", 2); // null check (2 of the initial five)
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".notExist=not=metaValue", 1 + 5);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=not=notExist", 1 + 5);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=ne=metaValue", 1 + 4);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=ne=null", 2); // null check (2 of the initial five)
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".notExist=ne=metaValue", 1 + 5);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=ne=notExist", 1 + 5);
|
||||
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=in=(metaValue,notexist)", 1);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".metaKey=out=(metaValue,notexist)", 1);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".key.dot==value.dot", 1);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".key.dot*==value.dot", 0);
|
||||
assertRSQLQuery(TargetFields.METADATA.name() + ".key.*==value.dot", 0);
|
||||
@@ -265,41 +320,37 @@ class RSQLTargetFieldTest extends AbstractJpaIntegrationTest {
|
||||
@Test
|
||||
@Description("Test filter based on more complex RSQL queries")
|
||||
void testFilterByComplexQueries() {
|
||||
assertRSQLQuery(TargetFields.NAME.name() + "!=targetName123" + AND + TargetFields.METADATA.name() + ".metaKey!=value", 0);
|
||||
assertRSQLQuery(
|
||||
TargetFields.NAME.name() + "!=targetName123" + AND + TargetFields.METADATA.name() + ".metaKey!=value",
|
||||
0);
|
||||
assertRSQLQuery("(" + TargetFields.TAG.name() + "!=TAG1" + OR + TargetFields.TAG.name() + "!=TAG2)" + AND
|
||||
+ TargetFields.CONTROLLERID.name() + "!=targetId1235", 4);
|
||||
"(" + TargetFields.TAG.name() + "!=TAG1" + OR + TargetFields.TAG.name() + "!=TAG2)" +
|
||||
AND + TargetFields.CONTROLLERID.name() + "!=targetId1235", 4);
|
||||
}
|
||||
|
||||
@Test
|
||||
@Description("Testing allowed RSQL keys based on TargetFields definition")
|
||||
void rsqlValidTargetFields() {
|
||||
final String rsql1 = "ID == '0123' and NAME == abcd and DESCRIPTION == absd"
|
||||
+ " and CREATEDAT =lt= 0123 and LASTMODIFIEDAT =gt= 0123"
|
||||
+ " and CONTROLLERID == 0123 and UPDATESTATUS == PENDING"
|
||||
+ " and IPADDRESS == 0123 and LASTCONTROLLERREQUESTAT == 0123" + " and tag == beta";
|
||||
RSQLUtility.validateRsqlFor(
|
||||
"ID == '0123' and NAME == abcd and DESCRIPTION == absd and CREATEDAT =lt= 0123 and LASTMODIFIEDAT =gt= 0123" +
|
||||
" and CONTROLLERID == 0123 and UPDATESTATUS == PENDING and IPADDRESS == 0123 and LASTCONTROLLERREQUESTAT == 0123" +
|
||||
" and tag == beta",
|
||||
TargetFields.class, JpaTarget.class, virtualPropertyReplacer, entityManager);
|
||||
RSQLUtility.validateRsqlFor(
|
||||
"ASSIGNEDDS.name == abcd and ASSIGNEDDS.version == 0123 and INSTALLEDDS.name == abcd and INSTALLEDDS.version == 0123",
|
||||
TargetFields.class, JpaTarget.class, virtualPropertyReplacer, entityManager);
|
||||
RSQLUtility.validateRsqlFor(
|
||||
"ATTRIBUTE.subkey1 == test and ATTRIBUTE.subkey2 == test and METADATA.metakey1 == abcd and METADATA.metavalue2 == asdfg",
|
||||
TargetFields.class, JpaTarget.class, virtualPropertyReplacer, entityManager);
|
||||
RSQLUtility.validateRsqlFor(
|
||||
"CREATEDAT =lt= ${NOW_TS} and LASTMODIFIEDAT =ge= ${OVERDUE_TS}",
|
||||
TargetFields.class, JpaTarget.class, virtualPropertyReplacer, entityManager);
|
||||
RSQLUtility.validateRsqlFor(
|
||||
"ATTRIBUTE.test.dot == test and ATTRIBUTE.subkey2 == test and METADATA.test.dot == abcd and METADATA.metavalue2 == asdfg",
|
||||
TargetFields.class, JpaTarget.class, virtualPropertyReplacer, entityManager);
|
||||
|
||||
RSQLUtility.validateRsqlFor(rsql1, TargetFields.class);
|
||||
|
||||
final String rsql2 = "ASSIGNEDDS.name == abcd and ASSIGNEDDS.version == 0123"
|
||||
+ " and INSTALLEDDS.name == abcd and INSTALLEDDS.version == 0123";
|
||||
RSQLUtility.validateRsqlFor(rsql2, TargetFields.class);
|
||||
|
||||
final String rsql3 = "ATTRIBUTE.subkey1 == test and ATTRIBUTE.subkey2 == test"
|
||||
+ " and METADATA.metakey1 == abcd and METADATA.metavalue2 == asdfg";
|
||||
RSQLUtility.validateRsqlFor(rsql3, TargetFields.class);
|
||||
|
||||
final String rsql4 = "CREATEDAT =lt= ${NOW_TS} and LASTMODIFIEDAT =ge= ${OVERDUE_TS}";
|
||||
RSQLUtility.validateRsqlFor(rsql4, TargetFields.class);
|
||||
|
||||
final String rsql5 = "wrongfield == abcd";
|
||||
assertThatExceptionOfType(RSQLParameterUnsupportedFieldException.class)
|
||||
.isThrownBy(() -> RSQLUtility.validateRsqlFor(rsql5, TargetFields.class));
|
||||
|
||||
final String rsql6 = "ATTRIBUTE.test.dot == test and ATTRIBUTE.subkey2 == test"
|
||||
+ " and METADATA.test.dot == abcd and METADATA.metavalue2 == asdfg";
|
||||
RSQLUtility.validateRsqlFor(rsql6, TargetFields.class);
|
||||
.isThrownBy(() -> RSQLUtility.validateRsqlFor(
|
||||
"wrongfield == abcd",
|
||||
TargetFields.class, JpaTarget.class, virtualPropertyReplacer, entityManager));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -338,6 +389,7 @@ class RSQLTargetFieldTest extends AbstractJpaIntegrationTest {
|
||||
|
||||
private void assertRSQLQueryThrowsException(final String rsqlParam) {
|
||||
assertThatExceptionOfType(RSQLParameterUnsupportedFieldException.class)
|
||||
.isThrownBy(() -> RSQLUtility.validateRsqlFor(rsqlParam, TargetFields.class));
|
||||
.isThrownBy(() -> RSQLUtility.validateRsqlFor(
|
||||
rsqlParam, TargetFields.class, JpaTarget.class, virtualPropertyReplacer, entityManager));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -57,12 +57,12 @@ class RSQLToSQLTest {
|
||||
print(JpaTarget.class, TargetFields.class, "controllerId==ctrlr1");
|
||||
// reference - fk to a table
|
||||
print(JpaTarget.class, TargetFields.class, "assignedds.name==x and assignedds.version==y");
|
||||
// list (map table that refers main)
|
||||
print(JpaTarget.class, TargetFields.class, "metadata.key1==value1");
|
||||
// map (map table that refers main)
|
||||
print(JpaTarget.class, TargetFields.class, "attribute.key1==value1");
|
||||
// list of non-simple (with mapping table)
|
||||
print(JpaTarget.class, TargetFields.class, "tag==tag1");
|
||||
// list (map table that refers main)
|
||||
print(JpaTarget.class, TargetFields.class, "attribute.key1==value1");
|
||||
// map (map table that refers main)
|
||||
print(JpaTarget.class, TargetFields.class, "metadata.key1==value1");
|
||||
}
|
||||
|
||||
@Test
|
||||
|
||||
@@ -44,14 +44,12 @@ import org.eclipse.hawkbit.repository.RsqlQueryField;
|
||||
import org.eclipse.hawkbit.repository.SoftwareModuleFields;
|
||||
import org.eclipse.hawkbit.repository.TargetFields;
|
||||
import org.eclipse.hawkbit.repository.TenantConfigurationManagement;
|
||||
import org.eclipse.hawkbit.repository.exception.RSQLParameterSyntaxException;
|
||||
import org.eclipse.hawkbit.repository.exception.RSQLParameterUnsupportedFieldException;
|
||||
import org.eclipse.hawkbit.repository.model.SoftwareModule;
|
||||
import org.eclipse.hawkbit.repository.model.TenantConfigurationValue;
|
||||
import org.eclipse.hawkbit.repository.model.helper.SystemSecurityContextHolder;
|
||||
import org.eclipse.hawkbit.repository.model.helper.TenantConfigurationManagementHolder;
|
||||
import org.eclipse.hawkbit.repository.rsql.RsqlConfigHolder;
|
||||
import org.eclipse.hawkbit.repository.rsql.RsqlVisitorFactory;
|
||||
import org.eclipse.hawkbit.repository.rsql.VirtualPropertyReplacer;
|
||||
import org.eclipse.hawkbit.repository.rsql.VirtualPropertyResolver;
|
||||
import org.eclipse.hawkbit.security.SystemSecurityContext;
|
||||
@@ -88,8 +86,6 @@ class RSQLUtilityTest {
|
||||
private TenantConfigurationManagement confMgmt;
|
||||
@MockitoBean
|
||||
private SystemSecurityContext securityContext;
|
||||
@MockitoBean
|
||||
private RsqlVisitorFactory rsqlVisitorFactory;
|
||||
@Mock
|
||||
private Root<Object> baseSoftwareModuleRootMock;
|
||||
@Mock
|
||||
@@ -109,63 +105,6 @@ class RSQLUtilityTest {
|
||||
setupRoot(subqueryRootMock);
|
||||
}
|
||||
|
||||
@Test
|
||||
@Description("Testing throwing exception in case of not allowed RSQL key")
|
||||
void rsqlUnsupportedFieldExceptionTest() {
|
||||
final String rsql1 = "wrongfield == abcd";
|
||||
assertThatExceptionOfType(RSQLParameterUnsupportedFieldException.class)
|
||||
.isThrownBy(() -> validateRsqlForTestFields(rsql1));
|
||||
|
||||
final String rsql2 = "wrongfield == abcd or TESTFIELD_WITH_SUB_ENTITIES.subentity11 == 0123";
|
||||
assertThatExceptionOfType(RSQLParameterUnsupportedFieldException.class)
|
||||
.isThrownBy(() -> validateRsqlForTestFields(rsql2));
|
||||
}
|
||||
|
||||
@Test
|
||||
@Description("Testing exception in case of not allowed subkey")
|
||||
void rsqlUnsupportedSubkeyThrowException() {
|
||||
final String rsql1 = "TESTFIELD_WITH_SUB_ENTITIES.unsupported == abcd and TESTFIELD_WITH_SUB_ENTITIES.subentity22 == 0123";
|
||||
assertThatExceptionOfType(RSQLParameterUnsupportedFieldException.class)
|
||||
.isThrownBy(() -> validateRsqlForTestFields(rsql1));
|
||||
|
||||
final String rsql2 = "TESTFIELD_WITH_SUB_ENTITIES.unsupported == abcd or TESTFIELD_WITH_SUB_ENTITIES.subentity22 == 0123";
|
||||
assertThatExceptionOfType(RSQLParameterUnsupportedFieldException.class)
|
||||
.isThrownBy(() -> validateRsqlForTestFields(rsql2));
|
||||
|
||||
final String rsql3 = "TESTFIELD == abcd or TESTFIELD_WITH_SUB_ENTITIES.unsupported == 0123";
|
||||
assertThatExceptionOfType(RSQLParameterUnsupportedFieldException.class)
|
||||
.isThrownBy(() -> validateRsqlForTestFields(rsql3));
|
||||
}
|
||||
|
||||
@Test
|
||||
@Description("Testing valid RSQL keys based on TestFieldEnum.class")
|
||||
void rsqlFieldValidation() {
|
||||
|
||||
final String rsql1 = "TESTFIELD_WITH_SUB_ENTITIES.subentity11 == abcd and TESTFIELD_WITH_SUB_ENTITIES.subentity22 == 0123";
|
||||
final String rsql2 = "TESTFIELD_WITH_SUB_ENTITIES.subentity11 == abcd or TESTFIELD_WITH_SUB_ENTITIES.subentity22 == 0123";
|
||||
final String rsql3 = "TESTFIELD_WITH_SUB_ENTITIES.subentity11 == abcd and TESTFIELD_WITH_SUB_ENTITIES.subentity22 == 0123 and TESTFIELD == any";
|
||||
|
||||
validateRsqlForTestFields(rsql1);
|
||||
validateRsqlForTestFields(rsql2);
|
||||
validateRsqlForTestFields(rsql3);
|
||||
}
|
||||
|
||||
@Test
|
||||
@Description("Verify that RSQL expressions are validated case insensitive")
|
||||
void mixedCaseRsqlFieldValidation() {
|
||||
when(rsqlVisitorFactory.validationRsqlVisitor(TargetFields.class)).thenReturn(new FieldValidationRsqlVisitor<>(TargetFields.class));
|
||||
final String rsqlWithMixedCase = "name==b And name==c aND Name==d OR NAME=iN=y oR nAme=IN=z";
|
||||
RSQLUtility.validateRsqlFor(rsqlWithMixedCase, TargetFields.class);
|
||||
}
|
||||
|
||||
@Test
|
||||
void wrongRsqlSyntaxThrowSyntaxException() {
|
||||
final Specification<Object> rsqlSpecification = RSQLUtility.buildRsqlSpecification("name==abc;d", SoftwareModuleFields.class, null, testDb);
|
||||
assertThatExceptionOfType(RSQLParameterSyntaxException.class)
|
||||
.as("RSQLParameterSyntaxException because of wrong RSQL syntax")
|
||||
.isThrownBy(() -> rsqlSpecification.toPredicate(baseSoftwareModuleRootMock, criteriaQueryMock, criteriaBuilderMock));
|
||||
}
|
||||
|
||||
@Test
|
||||
void wrongFieldThrowUnsupportedFieldException() {
|
||||
when(baseSoftwareModuleRootMock.getJavaType()).thenReturn((Class) SoftwareModule.class);
|
||||
@@ -481,12 +420,6 @@ class RSQLUtilityTest {
|
||||
return (Path<Y>) path;
|
||||
}
|
||||
|
||||
private void validateRsqlForTestFields(final String rsql) {
|
||||
when(rsqlVisitorFactory.validationRsqlVisitor(TestFieldEnum.class)).thenReturn(
|
||||
new FieldValidationRsqlVisitor<>(TestFieldEnum.class));
|
||||
RSQLUtility.validateRsqlFor(rsql, TestFieldEnum.class);
|
||||
}
|
||||
|
||||
private void reset0(final Object... mocks) {
|
||||
reset(mocks);
|
||||
if (Arrays.asList(mocks).contains(baseSoftwareModuleRootMock)) {
|
||||
@@ -553,8 +486,8 @@ class RSQLUtilityTest {
|
||||
}
|
||||
|
||||
@Bean
|
||||
RsqlConfigHolder rsqlVisitorFactoryHolder() {
|
||||
RsqlConfigHolder rsqlConfigHolder() {
|
||||
return RsqlConfigHolder.getInstance();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -12,10 +12,10 @@
|
||||
|
||||
logging.level.org.eclipse.persistence=ERROR
|
||||
## Uncomment to see the debug of persistence, e.g. to see the generated SQLs
|
||||
#logging.level.org.eclipse.persistence=DEBUG
|
||||
#spring.jpa.properties.eclipselink.logging.level=FINE
|
||||
#spring.jpa.properties.eclipselink.logging.level.sql=FINE
|
||||
#spring.jpa.properties.eclipselink.logging.parameters=true
|
||||
logging.level.org.eclipse.persistence=DEBUG
|
||||
spring.jpa.properties.eclipselink.logging.level=FINE
|
||||
spring.jpa.properties.eclipselink.logging.level.sql=FINE
|
||||
spring.jpa.properties.eclipselink.logging.parameters=true
|
||||
|
||||
## Enable EclipseLink performance monitor (monitoring and profile)
|
||||
#spring.jpa.properties.eclipselink.profiler=PerformanceMonitor
|
||||
|
||||
Reference in New Issue
Block a user