View Javadoc
1   package de.dlr.shepard.integrationtests;
2   
3   import static io.restassured.RestAssured.given;
4   import static org.assertj.core.api.Assertions.assertThat;
5   import static org.junit.jupiter.api.Assertions.assertEquals;
6   
7   import de.dlr.shepard.common.search.io.QueryType;
8   import de.dlr.shepard.common.search.io.ResponseBody;
9   import de.dlr.shepard.common.search.io.ResultTriple;
10  import de.dlr.shepard.common.search.io.SearchBody;
11  import de.dlr.shepard.common.search.io.SearchParams;
12  import de.dlr.shepard.common.search.io.SearchScope;
13  import de.dlr.shepard.common.util.Constants;
14  import de.dlr.shepard.common.util.TraversalRules;
15  import de.dlr.shepard.context.collection.io.CollectionIO;
16  import de.dlr.shepard.context.collection.io.DataObjectIO;
17  import io.quarkus.test.junit.QuarkusIntegrationTest;
18  import java.util.Map;
19  import org.junit.jupiter.api.BeforeAll;
20  import org.junit.jupiter.api.MethodOrderer;
21  import org.junit.jupiter.api.Order;
22  import org.junit.jupiter.api.Test;
23  import org.junit.jupiter.api.TestMethodOrder;
24  
25  @QuarkusIntegrationTest
26  @TestMethodOrder(MethodOrderer.OrderAnnotation.class)
27  public class DataObjectSearcherIT extends BaseTestCaseIT {
28  
29    private static DataObjectIO dataObjectIO1;
30    private static DataObjectIO dataObjectIO2;
31    private static DataObjectIO dataObjectIO3;
32    private static DataObjectIO dataObjectIO4;
33    private static String dataObjectsURL;
34    private static CollectionIO collection;
35    private static String searchURL;
36  
37    @BeforeAll
38    public static void setUp() {
39      collection = createCollection("DataObjectSearcherTestCollection");
40      dataObjectsURL = String.format("/%s/%d/%s", Constants.COLLECTIONS, collection.getId(), Constants.DATA_OBJECTS);
41  
42      searchURL = "/" + Constants.SEARCH;
43      var payload1 = new DataObjectIO();
44      payload1.setName("DataObjectSearchDummy1");
45      payload1.setDescription("description1");
46      payload1.setAttributes(Map.of("a", "1", "b", "2"));
47      dataObjectIO1 = given()
48        .spec(requestSpecOfDefaultUser)
49        .body(payload1)
50        .when()
51        .post(dataObjectsURL)
52        .then()
53        .statusCode(201)
54        .extract()
55        .as(DataObjectIO.class);
56      var payload2 = new DataObjectIO();
57      payload2.setName("DataObjectSearchDummy2");
58      payload2.setDescription("description2");
59      payload2.setAttributes(Map.of("abc", "1", "bcd", "233"));
60      dataObjectIO2 = given()
61        .spec(requestSpecOfDefaultUser)
62        .body(payload2)
63        .when()
64        .post(dataObjectsURL)
65        .then()
66        .statusCode(201)
67        .extract()
68        .as(DataObjectIO.class);
69      dataObjectIO3 = createDataObjectWithParent("DataObjectSearchDummy3", collection.getId(), dataObjectIO1.getId());
70      dataObjectIO4 = createDataObjectWithParent("DataObjectSearchDummy4", collection.getId(), dataObjectIO3.getId());
71    }
72  
73    @Test
74    @Order(1)
75    public void findOneDataObjectWithOrTest() {
76      SearchBody searchBody = new SearchBody();
77      SearchScope searchScope = new SearchScope();
78      searchScope.setCollectionId(collection.getId());
79      searchScope.setTraversalRules(new TraversalRules[] {});
80      searchBody.setScopes(new SearchScope[] { searchScope });
81      SearchParams searchParams = new SearchParams();
82      searchParams.setQueryType(QueryType.DataObject);
83      String query = String.format(
84        """
85        {
86          "OR": [
87            {
88              "property": "id",
89              "value": %d,
90              "operator": "eq"
91            },
92            {
93              "property": "number",
94              "value": 123,
95              "operator": "le"
96            }
97          ]
98        }""",
99        dataObjectIO1.getId()
100     );
101     searchParams.setQuery(query);
102     searchBody.setSearchParams(searchParams);
103     var result = given()
104       .spec(requestSpecOfDefaultUser)
105       .body(searchBody)
106       .when()
107       .post(searchURL)
108       .then()
109       .statusCode(200)
110       .extract()
111       .as(ResponseBody.class);
112     ResultTriple triple1 = new ResultTriple(collection.getId(), dataObjectIO1.getId(), null);
113     assertThat(result.getResultSet()).contains(triple1);
114     assertThat(result.getResults()[0].getId()).isEqualTo(dataObjectIO1.getId());
115     assertThat(result.getSearchParams()).isEqualTo(searchParams);
116   }
117 
118   @Test
119   @Order(2)
120   public void findOneDataObjectWithAndAttributesTest() {
121     SearchBody searchBody = new SearchBody();
122     SearchScope searchScope = new SearchScope();
123     searchScope.setCollectionId(collection.getId());
124     searchScope.setTraversalRules(new TraversalRules[] {});
125     searchBody.setScopes(new SearchScope[] { searchScope });
126     SearchParams searchParams = new SearchParams();
127     searchParams.setQueryType(QueryType.DataObject);
128     String query = String.format(
129       """
130       {
131         "AND": [
132           {
133             "property": "id",
134             "value": %d,
135             "operator": "eq"
136           },
137           {
138             "property": "attributes.a",
139             "value": "1",
140             "operator": "eq"
141           }
142         ]
143       }""",
144       dataObjectIO1.getId()
145     );
146     searchParams.setQuery(query);
147     searchBody.setSearchParams(searchParams);
148     var result = given()
149       .spec(requestSpecOfDefaultUser)
150       .body(searchBody)
151       .when()
152       .post(searchURL)
153       .then()
154       .statusCode(200)
155       .extract()
156       .as(ResponseBody.class);
157     ResultTriple triple1 = new ResultTriple(collection.getId(), dataObjectIO1.getId(), null);
158     assertThat(result.getResultSet()).contains(triple1);
159   }
160 
161   @Test
162   @Order(3)
163   public void findOneDataObjectWithAndNameTest() {
164     SearchBody searchBody = new SearchBody();
165     SearchScope searchScope = new SearchScope();
166     searchScope.setCollectionId(collection.getId());
167     searchScope.setTraversalRules(new TraversalRules[] {});
168     searchBody.setScopes(new SearchScope[] { searchScope });
169     SearchParams searchParams = new SearchParams();
170     searchParams.setQueryType(QueryType.DataObject);
171     String query = String.format(
172       """
173       {
174         "AND": [
175           {
176             "property": "id",
177             "value": %d,
178             "operator": "eq"
179           },
180           {
181             "property": "name",
182             "value": "DataObjectSearchDummy1",
183             "operator": "eq"
184           }
185         ]
186       }""",
187       dataObjectIO1.getId()
188     );
189     searchParams.setQuery(query);
190     searchBody.setSearchParams(searchParams);
191     var result = given()
192       .spec(requestSpecOfDefaultUser)
193       .body(searchBody)
194       .when()
195       .post(searchURL)
196       .then()
197       .statusCode(200)
198       .extract()
199       .as(ResponseBody.class);
200     ResultTriple triple1 = new ResultTriple(collection.getId(), dataObjectIO1.getId(), null);
201     assertThat(result.getResultSet()).contains(triple1);
202   }
203 
204   @Test
205   @Order(4)
206   public void findNoDataObjectWithAndTest() {
207     SearchBody searchBody = new SearchBody();
208     SearchScope searchScope = new SearchScope();
209     searchScope.setCollectionId(collection.getId());
210     searchScope.setTraversalRules(new TraversalRules[] {});
211     searchBody.setScopes(new SearchScope[] { searchScope });
212     SearchParams searchParams = new SearchParams();
213     searchParams.setQueryType(QueryType.DataObject);
214     String query = String.format(
215       """
216       {
217         "AND": [
218           {
219             "property": "id",
220             "value": %d,
221             "operator": "eq"
222           },
223           {
224             "property": "name",
225             "value": "DataObjectSearchDummy2",
226             "operator": "eq"
227           }
228         ]
229       }""",
230       dataObjectIO1.getId()
231     );
232     searchParams.setQuery(query);
233     searchBody.setSearchParams(searchParams);
234     var result = given()
235       .spec(requestSpecOfDefaultUser)
236       .body(searchBody)
237       .when()
238       .post(searchURL)
239       .then()
240       .statusCode(200)
241       .extract()
242       .as(ResponseBody.class);
243     assertEquals(0, result.getResultSet().length);
244   }
245 
246   @Test
247   @Order(5)
248   public void findNoneOfTwoDataObjectsTest() {
249     SearchBody searchBody = new SearchBody();
250     SearchScope searchScope = new SearchScope();
251     searchScope.setCollectionId(collection.getId());
252     searchScope.setTraversalRules(new TraversalRules[] {});
253     searchBody.setScopes(new SearchScope[] { searchScope });
254     SearchParams searchParams = new SearchParams();
255     searchParams.setQueryType(QueryType.DataObject);
256     String query = String.format(
257       """
258       {
259         "AND": [
260           {
261             "property": "id",
262             "value": %d,
263             "operator": "eq"
264           },
265           {
266             "property": "name",
267             "value": "DataObjectSearchDummy2",
268             "operator": "eq"
269           }
270         ]
271       }""",
272       dataObjectIO1.getId()
273     );
274     searchParams.setQuery(query);
275     searchBody.setSearchParams(searchParams);
276     var result = given()
277       .spec(requestSpecOfDefaultUser)
278       .body(searchBody)
279       .when()
280       .post(searchURL)
281       .then()
282       .statusCode(200)
283       .extract()
284       .as(ResponseBody.class);
285     ResultTriple triple1 = new ResultTriple(collection.getId(), dataObjectIO1.getId(), null);
286     ResultTriple triple2 = new ResultTriple(collection.getId(), dataObjectIO2.getId(), null);
287     assertThat(result.getResultSet()).doesNotContain(triple1, triple2);
288   }
289 
290   @Test
291   @Order(6)
292   public void findOneOutOfTwoDataObjectsTest() {
293     SearchBody searchBody = new SearchBody();
294     SearchScope searchScope = new SearchScope();
295     searchScope.setCollectionId(collection.getId());
296     searchScope.setTraversalRules(new TraversalRules[] {});
297     searchBody.setScopes(new SearchScope[] { searchScope });
298     SearchParams searchParams = new SearchParams();
299     searchParams.setQueryType(QueryType.DataObject);
300     String query = String.format(
301       """
302       {
303         "AND": [
304           {
305             "property": "id",
306             "value": %d,
307             "operator": "eq"
308           },
309           {
310             "property": "name",
311             "value": "DataObjectSearchDummy",
312             "operator": "contains"
313           }
314         ]
315       }""",
316       dataObjectIO2.getId()
317     );
318     searchParams.setQuery(query);
319     searchBody.setSearchParams(searchParams);
320     var result = given()
321       .spec(requestSpecOfDefaultUser)
322       .body(searchBody)
323       .when()
324       .post(searchURL)
325       .then()
326       .statusCode(200)
327       .extract()
328       .as(ResponseBody.class);
329     ResultTriple triple1 = new ResultTriple(collection.getId(), dataObjectIO1.getId(), null);
330     ResultTriple triple2 = new ResultTriple(collection.getId(), dataObjectIO2.getId(), null);
331     assertThat(result.getResultSet()).doesNotContain(triple1);
332     assertThat(result.getResultSet()).contains(triple2);
333   }
334 
335   @Test
336   @Order(7)
337   public void findTwoDataObjectsWithOrTest() {
338     SearchBody searchBody = new SearchBody();
339     SearchScope searchScope = new SearchScope();
340     searchScope.setCollectionId(collection.getId());
341     searchScope.setTraversalRules(new TraversalRules[] {});
342     searchBody.setScopes(new SearchScope[] { searchScope });
343     SearchParams searchParams = new SearchParams();
344     searchParams.setQueryType(QueryType.DataObject);
345     String query = String.format(
346       """
347       {
348         "OR": [
349           {
350             "property": "id",
351             "value": %d,
352             "operator": "eq"
353           },
354           {
355             "property": "name",
356             "value": "DataObjectSearchDummy1",
357             "operator": "eq"
358           }
359         ]
360       }""",
361       dataObjectIO2.getId()
362     );
363     searchParams.setQuery(query);
364     searchBody.setSearchParams(searchParams);
365     var result = given()
366       .spec(requestSpecOfDefaultUser)
367       .body(searchBody)
368       .when()
369       .post(searchURL)
370       .then()
371       .statusCode(200)
372       .extract()
373       .as(ResponseBody.class);
374     ResultTriple triple1 = new ResultTriple(collection.getId(), dataObjectIO1.getId(), null);
375     ResultTriple triple2 = new ResultTriple(collection.getId(), dataObjectIO2.getId(), null);
376     assertThat(result.getResultSet()).contains(triple1, triple2);
377   }
378 
379   @Test
380   @Order(8)
381   public void findOneOutOfFourDataObjectsTest() {
382     SearchBody searchBody = new SearchBody();
383     SearchScope searchScope = new SearchScope();
384     searchScope.setCollectionId(collection.getId());
385     searchScope.setDataObjectId(dataObjectIO1.getId());
386     searchScope.setTraversalRules(new TraversalRules[] { TraversalRules.children });
387     searchBody.setScopes(new SearchScope[] { searchScope });
388     SearchParams searchParams = new SearchParams();
389     searchParams.setQueryType(QueryType.DataObject);
390     String query = String.format(
391       """
392       {
393         "AND": [
394           {
395             "property": "id",
396             "value": %d,
397             "operator": "eq"
398           },
399           {
400             "property": "name",
401             "value": "DataObjectSearchDummy4",
402             "operator": "eq"
403           }
404       ]}""",
405       dataObjectIO4.getId()
406     );
407     searchParams.setQuery(query);
408     searchBody.setSearchParams(searchParams);
409     var result = given()
410       .spec(requestSpecOfDefaultUser)
411       .body(searchBody)
412       .when()
413       .post(searchURL)
414       .then()
415       .statusCode(200)
416       .extract()
417       .as(ResponseBody.class);
418     ResultTriple triple1 = new ResultTriple(collection.getId(), dataObjectIO1.getId(), null);
419     ResultTriple triple2 = new ResultTriple(collection.getId(), dataObjectIO2.getId(), null);
420     ResultTriple triple3 = new ResultTriple(collection.getId(), dataObjectIO3.getId(), null);
421     ResultTriple triple4 = new ResultTriple(collection.getId(), dataObjectIO4.getId(), null);
422     assertThat(result.getResultSet()).doesNotContain(triple1, triple2, triple3);
423     assertThat(result.getResultSet()).contains(triple4);
424   }
425 
426   @Test
427   @Order(8)
428   public void findAnotherOneOutOfFourDataObjectsByParentsTest() {
429     SearchBody searchBody = new SearchBody();
430     SearchScope searchScope = new SearchScope();
431     searchScope.setCollectionId(collection.getId());
432     searchScope.setDataObjectId(dataObjectIO4.getId());
433     searchScope.setTraversalRules(new TraversalRules[] { TraversalRules.parents });
434     searchBody.setScopes(new SearchScope[] { searchScope });
435     SearchParams searchParams = new SearchParams();
436     searchParams.setQueryType(QueryType.DataObject);
437     String query = String.format(
438       """
439       {
440         "AND": [
441           {
442             "property": "id",
443             "value": %d,
444             "operator": "eq"
445           },
446           {
447             "property": "name",
448             "value": "DataObjectSearchDummy1",
449             "operator": "eq"
450           }
451       ]}""",
452       dataObjectIO1.getId()
453     );
454     searchParams.setQuery(query);
455     searchBody.setSearchParams(searchParams);
456     var result = given()
457       .spec(requestSpecOfDefaultUser)
458       .body(searchBody)
459       .when()
460       .post(searchURL)
461       .then()
462       .statusCode(200)
463       .extract()
464       .as(ResponseBody.class);
465     ResultTriple triple1 = new ResultTriple(collection.getId(), dataObjectIO1.getId(), null);
466     ResultTriple triple2 = new ResultTriple(collection.getId(), dataObjectIO2.getId(), null);
467     ResultTriple triple3 = new ResultTriple(collection.getId(), dataObjectIO3.getId(), null);
468     ResultTriple triple4 = new ResultTriple(collection.getId(), dataObjectIO4.getId(), null);
469     assertThat(result.getResultSet()).contains(triple1);
470     assertThat(result.getResultSet()).doesNotContain(triple2, triple3, triple4);
471   }
472 
473   @Test
474   @Order(10)
475   public void stringContainsTest() {
476     SearchBody searchBody = new SearchBody();
477     SearchScope searchScope = new SearchScope();
478     searchScope.setTraversalRules(new TraversalRules[] {});
479     searchBody.setScopes(new SearchScope[] { searchScope });
480     SearchParams searchParams = new SearchParams();
481     searchParams.setQueryType(QueryType.DataObject);
482     String query =
483       """
484       {
485         "property": "name",
486         "value": "ummy",
487         "operator": "contains"
488       }""";
489     searchParams.setQuery(query);
490     searchBody.setSearchParams(searchParams);
491     var result = given()
492       .spec(requestSpecOfDefaultUser)
493       .body(searchBody)
494       .when()
495       .post(searchURL)
496       .then()
497       .statusCode(200)
498       .extract()
499       .as(ResponseBody.class);
500     ResultTriple triple1 = new ResultTriple(collection.getId(), dataObjectIO1.getId(), null);
501     ResultTriple triple2 = new ResultTriple(collection.getId(), dataObjectIO2.getId(), null);
502     ResultTriple triple3 = new ResultTriple(collection.getId(), dataObjectIO3.getId(), null);
503     ResultTriple triple4 = new ResultTriple(collection.getId(), dataObjectIO4.getId(), null);
504     assertThat(result.getResultSet()).contains(triple1, triple2, triple3, triple4);
505   }
506 
507   @Test
508   @Order(11)
509   public void unauthorizedUserTest() {
510     SearchBody searchBody = new SearchBody();
511     SearchScope searchScope = new SearchScope();
512     searchScope.setTraversalRules(new TraversalRules[] {});
513     searchBody.setScopes(new SearchScope[] { searchScope });
514     SearchParams searchParams = new SearchParams();
515     searchParams.setQueryType(QueryType.DataObject);
516     String query =
517       """
518       {
519         "property": "referencedDataObjectId",
520         "value": "ummy",
521         "operator": "eq"
522       }""";
523     searchParams.setQuery(query);
524     searchBody.setSearchParams(searchParams);
525     var result = given()
526       .spec(requestSpecOfOtherUser)
527       .body(searchBody)
528       .when()
529       .post(searchURL)
530       .then()
531       .statusCode(200)
532       .extract()
533       .as(ResponseBody.class);
534     assertEquals(0, result.getResultSet().length);
535   }
536 
537   private static DataObjectIO createDataObjectWithParent(String name, long collectionId, long parentID) {
538     var dataObjectsURL = String.format("/%s/%d/%s/", Constants.COLLECTIONS, collectionId, Constants.DATA_OBJECTS);
539 
540     DataObjectIO dataObjectIO = new DataObjectIO();
541     dataObjectIO.setName(name);
542     dataObjectIO.setParentId(parentID);
543     var dataObject = given()
544       .spec(requestSpecOfDefaultUser)
545       .body(dataObjectIO)
546       .when()
547       .post(dataObjectsURL)
548       .then()
549       .statusCode(201)
550       .extract()
551       .as(DataObjectIO.class);
552     return dataObject;
553   }
554 }