Skip to content

Method: testUpdateSimpleListOfIdentifiersByAddingNewItems()

1: /*
2: * JOPA
3: * Copyright (C) 2024 Czech Technical University in Prague
4: *
5: * This library is free software; you can redistribute it and/or
6: * modify it under the terms of the GNU Lesser General Public
7: * License as published by the Free Software Foundation; either
8: * version 3.0 of the License, or (at your option) any later version.
9: *
10: * This library is distributed in the hope that it will be useful,
11: * but WITHOUT ANY WARRANTY; without even the implied warranty of
12: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13: * Lesser General Public License for more details.
14: *
15: * You should have received a copy of the GNU Lesser General Public
16: * License along with this library.
17: */
18: package cz.cvut.kbss.jopa.test.runner;
19:
20: import cz.cvut.kbss.jopa.exceptions.RollbackException;
21: import cz.cvut.kbss.jopa.model.MultilingualString;
22: import cz.cvut.kbss.jopa.model.SequencesVocabulary;
23: import cz.cvut.kbss.jopa.test.OWLClassA;
24: import cz.cvut.kbss.jopa.test.OWLClassC;
25: import cz.cvut.kbss.jopa.test.OWLClassE;
26: import cz.cvut.kbss.jopa.test.OWLClassK;
27: import cz.cvut.kbss.jopa.test.OWLClassM;
28: import cz.cvut.kbss.jopa.test.OWLClassP;
29: import cz.cvut.kbss.jopa.test.Vocabulary;
30: import cz.cvut.kbss.jopa.test.environment.DataAccessor;
31: import cz.cvut.kbss.jopa.test.environment.Generators;
32: import cz.cvut.kbss.jopa.test.environment.PersistenceFactory;
33: import cz.cvut.kbss.jopa.test.environment.Quad;
34: import cz.cvut.kbss.jopa.vocabulary.RDF;
35: import cz.cvut.kbss.ontodriver.model.LangString;
36: import org.junit.jupiter.api.Test;
37: import org.slf4j.Logger;
38:
39: import java.net.URI;
40: import java.time.LocalDate;
41: import java.util.ArrayList;
42: import java.util.List;
43: import java.util.Map;
44: import java.util.stream.Collectors;
45: import java.util.stream.IntStream;
46:
47: import static org.hamcrest.MatcherAssert.assertThat;
48: import static org.hamcrest.Matchers.empty;
49: import static org.junit.jupiter.api.Assertions.assertEquals;
50: import static org.junit.jupiter.api.Assertions.assertFalse;
51: import static org.junit.jupiter.api.Assertions.assertNotEquals;
52: import static org.junit.jupiter.api.Assertions.assertNotNull;
53: import static org.junit.jupiter.api.Assertions.assertNull;
54: import static org.junit.jupiter.api.Assertions.assertThrows;
55: import static org.junit.jupiter.api.Assertions.assertTrue;
56:
57: public abstract class ListsTestRunner extends BaseRunner {
58:
59: protected ListsTestRunner(Logger logger, PersistenceFactory persistenceFactory, DataAccessor dataAccessor) {
60: super(logger, persistenceFactory, dataAccessor);
61: }
62:
63: static void verifyLists(List<OWLClassE> expected, List<OWLClassE> actual) {
64: assertEquals(expected.size(), actual.size());
65: for (int i = 0; i < expected.size(); i++) {
66: assertEquals(expected.get(i).getUri(), actual.get(i).getUri());
67: assertEquals(expected.get(i).getStringAttribute(), actual.get(i).getStringAttribute());
68: }
69: }
70:
71: @Test
72: void testPersistWithSimpleList() {
73: this.em = getEntityManager("PersistSimpleList", false);
74: entityC.setSimpleList(Generators.createSimpleList(10));
75: persistCWithLists(entityC);
76:
77: final OWLClassA a = findRequired(OWLClassA.class, entityC.getSimpleList().get(1).getUri());
78: final OWLClassC c = findRequired(OWLClassC.class, entityC.getUri());
79: assertNotNull(c.getSimpleList());
80: assertFalse(c.getSimpleList().isEmpty());
81: assertEquals(entityC.getSimpleList().size(), c.getSimpleList().size());
82: assertTrue(c.getSimpleList().contains(a));
83: }
84:
85: @Test
86: void persistingEntityWithSimpleListWithoutCascadeIsIllegal() {
87: this.em = getEntityManager("PersistSimpleListNoCascade", false);
88: entityC.setSimpleList(Generators.createSimpleList(10));
89: assertThrows(RollbackException.class, () -> persist(entityC));
90: }
91:
92: @Test
93: void persistWithSimpleListSavesListReferenceWhenAllItemsArePersisted() {
94: this.em = getEntityManager("persistWithSimpleListSavesListReferenceWhenAllItemsArePersisted", false);
95: final OWLClassK entityK = new OWLClassK();
96: entityK.setSimpleList(IntStream.range(0, 5).mapToObj(i -> {
97: final OWLClassE item = new OWLClassE();
98: item.setStringAttribute("item" + i);
99: return item;
100: }).collect(Collectors.toList()));
101: em.getTransaction().begin();
102: em.persist(entityK);
103: entityK.getSimpleList().forEach(item -> assertNull(item.getUri()));
104: entityK.getSimpleList().forEach(em::persist);
105: entityK.getSimpleList().forEach(item -> assertNotNull(item.getUri()));
106: em.getTransaction().commit();
107:
108: final OWLClassK result = findRequired(OWLClassK.class, entityK.getUri());
109: verifyLists(entityK.getSimpleList(), result.getSimpleList());
110: }
111:
112: @Test
113: void testPersistWithReferencedList() {
114: this.em = getEntityManager("PersistReferencedList", false);
115: entityC.setReferencedList(Generators.createReferencedList(5));
116: em.getTransaction().begin();
117: em.persist(entityC);
118: entityC.getReferencedList().forEach(em::persist);
119: assertTrue(em.contains(entityC));
120: assertTrue(em.contains(entityC.getReferencedList().get(0)));
121: em.getTransaction().commit();
122:
123: final OWLClassC c = findRequired(OWLClassC.class, entityC.getUri());
124: assertNotNull(c.getReferencedList());
125: assertFalse(c.getReferencedList().isEmpty());
126: assertEquals(entityC.getReferencedList().size(), c.getReferencedList().size());
127: for (OWLClassA a : entityC.getReferencedList()) {
128: final OWLClassA resA = em.find(OWLClassA.class, a.getUri());
129: assertNotNull(resA);
130: assertEquals(a.getStringAttribute(), resA.getStringAttribute());
131: assertTrue(c.getReferencedList().contains(resA));
132: }
133: }
134:
135:
136: @Test
137: void persistingEntityWithReferencedListWithoutCascadeIsIllegal() {
138: this.em = getEntityManager("PersistReferencedListNoCascade", false);
139: entityC.setReferencedList(Generators.createReferencedList(5));
140: assertThrows(RollbackException.class, () -> persist(entityC));
141: }
142:
143: @Test
144: void persistWithReferencedListSavesListReferenceWhenAllItemsArePersisted() {
145: this.em = getEntityManager("persistWithReferencedListSavesListReferenceWhenAllItemsArePersisted", false);
146: final OWLClassK entityK = new OWLClassK();
147: entityK.setReferencedList(IntStream.range(0, 5).mapToObj(i -> {
148: final OWLClassE item = new OWLClassE();
149: item.setStringAttribute("item" + i);
150: return item;
151: }).collect(Collectors.toList()));
152: em.getTransaction().begin();
153: em.persist(entityK);
154: entityK.getReferencedList().forEach(item -> assertNull(item.getUri()));
155: entityK.getReferencedList().forEach(em::persist);
156: entityK.getReferencedList().forEach(item -> assertNotNull(item.getUri()));
157: em.getTransaction().commit();
158:
159: final OWLClassK result = findRequired(OWLClassK.class, entityK.getUri());
160: verifyLists(entityK.getReferencedList(), result.getReferencedList());
161: }
162:
163: @Test
164: void testPersistSimpleAndReferencedList() {
165: this.em = getEntityManager("PersistSimpleAndReferencedList", false);
166: entityC.setReferencedList(Generators.createReferencedList(5));
167: entityC.setSimpleList(Generators.createSimpleList(5));
168: persistCWithLists(entityC);
169:
170: final OWLClassC c = findRequired(OWLClassC.class, entityC.getUri());
171: assertNotNull(c.getSimpleList());
172: assertEquals(entityC.getSimpleList().size(), c.getSimpleList().size());
173: assertNotNull(c.getReferencedList());
174: assertEquals(entityC.getReferencedList().size(), c.getReferencedList().size());
175: for (OWLClassA a : entityC.getSimpleList()) {
176: final OWLClassA resA = findRequired(OWLClassA.class, a.getUri());
177: assertTrue(c.getSimpleList().contains(resA));
178: }
179: for (OWLClassA a : entityC.getReferencedList()) {
180: final OWLClassA resA = findRequired(OWLClassA.class, a.getUri());
181: assertTrue(c.getReferencedList().contains(resA));
182: }
183: }
184:
185: @Test
186: void testPersistInstanceWithSimpleListOfIdentifiers() {
187: this.em = getEntityManager("PersistInstanceWithSimpleListOfIdentifiers", false);
188: entityP.setSimpleList(Generators.createListOfIdentifiers());
189: persist(entityP);
190: em.clear();
191:
192: final OWLClassP res = findRequired(OWLClassP.class, entityP.getUri());
193: assertEquals(entityP.getSimpleList(), res.getSimpleList());
194: }
195:
196: @Test
197: void testPersistInstanceWithReferencedListOfIdentifiers() {
198: this.em = getEntityManager("PersistInstanceWithReferencedListOfIdentifiers", false);
199: entityP.setReferencedList(Generators.createListOfIdentifiers());
200: persist(entityP);
201: em.clear();
202:
203: final OWLClassP res = findRequired(OWLClassP.class, entityP.getUri());
204: assertEquals(entityP.getReferencedList(), res.getReferencedList());
205: }
206:
207: @Test
208: void persistSupportsReferencedListsContainingDataPropertyLiteralValues() {
209: this.em = getEntityManager("persistSupportsReferencedListsContainingDataPropertyLiteralValues", false);
210: entityM.setLiteralReferencedList(Generators.createDataPropertyList());
211: persist(entityM);
212:
213: for (int i = 0; i < entityM.getLiteralReferencedList().size(); i++) {
214: assertTrue(em.createNativeQuery("ASK WHERE { ?prev ?hasNext ?node . ?node ?hasContent ?content . }", Boolean.class)
215: .setParameter("hasNext", URI.create(i == 0 ? Vocabulary.p_m_literalReferencedList : SequencesVocabulary.s_p_hasNext))
216: .setParameter("hasContent", URI.create(SequencesVocabulary.s_p_hasContents))
217: .setParameter("content", entityM.getLiteralReferencedList().get(i)).getSingleResult());
218: }
219: }
220:
221: @Test
222: void testRemoveFromSimpleListAndRepository() {
223: this.em = getEntityManager("RemoveFromSimpleList", false);
224: final int size = 5;
225: entityC.setSimpleList(Generators.createSimpleList(10));
226: persistCWithLists(entityC);
227:
228: final int randIndex = Generators.randomInt(size);
229: final OWLClassA a = findRequired(OWLClassA.class, entityC.getSimpleList().get(randIndex).getUri());
230: final OWLClassC c = findRequired(OWLClassC.class, entityC.getUri());
231: em.getTransaction().begin();
232: // We have to remove A from the simple list as well because otherwise we would break the chain in instances
233: assertTrue(c.getSimpleList().remove(a));
234: em.remove(a);
235: em.getTransaction().commit();
236:
237: final OWLClassA resA = em.find(OWLClassA.class, a.getUri());
238: assertNull(resA);
239: final OWLClassC resC = findRequired(OWLClassC.class, entityC.getUri());
240: assertFalse(resC.getSimpleList().stream().anyMatch(item -> item.getUri().equals(a.getUri())));
241: }
242:
243: @Test
244: void testRemoveFromReferencedListAndRepository() {
245: this.em = getEntityManager("RemoveFromReferencedList", false);
246: final int size = 10;
247: entityC.setReferencedList(Generators.createReferencedList(size));
248: persistCWithLists(entityC);
249:
250: final int randIndex = Generators.randomInt(size);
251: final OWLClassA a = findRequired(OWLClassA.class, entityC.getReferencedList().get(randIndex).getUri());
252: final OWLClassC c = findRequired(OWLClassC.class, entityC.getUri());
253: em.getTransaction().begin();
254: // We have to remove A from the referenced list as well because otherwise we would break the chain in instances
255: assertTrue(c.getReferencedList().remove(a));
256: em.remove(a);
257: em.getTransaction().commit();
258:
259: final OWLClassA resA = em.find(OWLClassA.class, a.getUri());
260: assertNull(resA);
261: final OWLClassC resC = findRequired(OWLClassC.class, entityC.getUri());
262: assertFalse(resC.getReferencedList().stream().anyMatch(item -> item.getUri().equals(a.getUri())));
263: }
264:
265: @Test
266: void testRemoveListOwner() {
267: this.em = getEntityManager("RemoveListOwner", false);
268: entityC.setSimpleList(Generators.createSimpleList());
269: entityC.setReferencedList(Generators.createReferencedList());
270: persistCWithLists(entityC);
271:
272: final OWLClassC c = findRequired(OWLClassC.class, entityC.getUri());
273: em.getTransaction().begin();
274: em.remove(c);
275: em.getTransaction().commit();
276:
277: em.getEntityManagerFactory().getCache().evictAll();
278: for (OWLClassA a : entityC.getSimpleList()) {
279: assertNotNull(em.find(OWLClassA.class, a.getUri()));
280: }
281: for (OWLClassA a : entityC.getReferencedList()) {
282: assertNotNull(em.find(OWLClassA.class, a.getUri()));
283: }
284: }
285:
286: @Test
287: void removingNewlyPersistedInstanceRemovesPendingListReferencesAndAllowsTransactionToFinish() {
288: this.em = getEntityManager(
289: "removingNewlyPersistedInstanceRemovesPendingListReferencesAndAllowsTransactionToFinish", true);
290: em.getTransaction().begin();
291: entityC.setSimpleList(Generators.createSimpleList());
292: entityC.setReferencedList(Generators.createReferencedList());
293: em.persist(entityC);
294: em.remove(entityC);
295: em.getTransaction().commit();
296:
297: assertNull(em.find(OWLClassC.class, entityC.getUri()));
298: entityC.getSimpleList().forEach(a -> assertNull(em.find(OWLClassA.class, a.getUri())));
299: entityC.getReferencedList().forEach(a -> assertNull(em.find(OWLClassA.class, a.getUri())));
300: }
301:
302: @Test
303: void removingListItemsFromNewlyPersistedOwnerRemovesThemFromPendingReferencesAndAllowsTransactionToFinish() {
304: this.em = getEntityManager(
305: "removingListItemsFromNewlyPersistedOwnerRemovesThemFromPendingReferencesAndAllowsTransactionToFinish",
306: false);
307: em.getTransaction().begin();
308: entityC.setSimpleList(Generators.createSimpleList());
309: entityC.setReferencedList(Generators.createReferencedList());
310: em.persist(entityC);
311: entityC.getSimpleList().clear();
312: entityC.getReferencedList().clear();
313: em.getTransaction().commit();
314:
315: final OWLClassC result = em.find(OWLClassC.class, entityC.getUri());
316: assertNotNull(result);
317: assertThat(result.getSimpleList(), empty());
318: assertThat(result.getReferencedList(), empty());
319: }
320:
321: @Test
322: void retrieveSupportsDataPropertyReferencedLists() throws Exception {
323: this.em = getEntityManager("retrieveSupportsDataPropertyReferencedLists", false);
324: final List<Quad> data = new ArrayList<>(List.of(new Quad(URI.create(entityM.getKey()), URI.create(RDF.TYPE), URI.create(Vocabulary.C_OWL_CLASS_M))));
325: final List<LocalDate> dates = new ArrayList<>();
326: URI previous = URI.create(entityM.getKey());
327: for (int i = 5; i >= 0; i--) {
328: final LocalDate d = LocalDate.now().minusDays(i);
329: dates.add(d);
330: final URI node = URI.create(entityM.getKey() + "-SEQ" + (5 - i));
331: data.add(new Quad(previous, URI.create(i == 5 ? Vocabulary.p_m_literalReferencedList : SequencesVocabulary.s_p_hasNext), node));
332: data.add(new Quad(node, SequencesVocabulary.p_hasContents, d));
333: previous = node;
334: }
335: persistTestData(data, em);
336:
337: final OWLClassM result = findRequired(OWLClassM.class, entityM.getKey());
338: assertEquals(dates, result.getLiteralReferencedList());
339: }
340:
341: @Test
342: void testRemoveFromSimpleList() {
343: this.em = getEntityManager("UpdateRemoveFromSimpleList", true);
344: entityC.setSimpleList(Generators.createSimpleList());
345: persistCWithLists(entityC);
346:
347: final OWLClassC c = findRequired(OWLClassC.class, entityC.getUri());
348: em.getTransaction().begin();
349: final OWLClassA a = c.getSimpleList().get(1);
350: c.getSimpleList().remove(a);
351: em.getTransaction().commit();
352:
353: final OWLClassA resA = findRequired(OWLClassA.class, a.getUri());
354: final OWLClassC resC = findRequired(OWLClassC.class, c.getUri());
355: assertEquals(c.getSimpleList().size(), resC.getSimpleList().size());
356: assertEquals(entityC.getSimpleList().size() - 1, resC.getSimpleList().size());
357: for (OWLClassA aa : resC.getSimpleList()) {
358: assertNotEquals(resA.getUri(), aa.getUri());
359: }
360: }
361:
362: @Test
363: void testAddToSimpleList() {
364: this.em = getEntityManager("UpdateAddToSimpleList", true);
365: entityC.setSimpleList(Generators.createSimpleList());
366: em.getTransaction().begin();
367: em.persist(entityC);
368: entityC.getSimpleList().forEach(em::persist);
369: em.persist(entityA);
370: em.getTransaction().commit();
371:
372: em.getTransaction().begin();
373: final OWLClassC c = findRequired(OWLClassC.class, entityC.getUri());
374: final OWLClassA a = findRequired(OWLClassA.class, entityA.getUri());
375: assertFalse(c.getSimpleList().contains(a));
376: c.getSimpleList().add(a);
377: em.getTransaction().commit();
378:
379: final OWLClassC resC = findRequired(OWLClassC.class, entityC.getUri());
380: assertEquals(c.getSimpleList().size(), resC.getSimpleList().size());
381: assertEquals(entityC.getSimpleList().size() + 1, resC.getSimpleList().size());
382: final OWLClassA resA = findRequired(OWLClassA.class, entityA.getUri());
383: assertTrue(resC.getSimpleList().contains(resA));
384: }
385:
386: @Test
387: void testClearSimpleList() {
388: this.em = getEntityManager("UpdateClearSimpleList", true);
389: entityC.setSimpleList(Generators.createSimpleList());
390: persistCWithLists(entityC);
391:
392: final OWLClassC c = findRequired(OWLClassC.class, entityC.getUri());
393: assertFalse(c.getSimpleList().isEmpty());
394: em.getTransaction().begin();
395: c.getSimpleList().clear();
396: em.getTransaction().commit();
397:
398: final OWLClassC resC = findRequired(OWLClassC.class, entityC.getUri());
399: assertTrue(resC.getSimpleList() == null || resC.getSimpleList().isEmpty());
400: for (OWLClassA a : entityC.getSimpleList()) {
401: verifyExists(OWLClassA.class, a.getUri());
402: }
403: }
404:
405: @Test
406: void testReplaceSimpleList() {
407: this.em = getEntityManager("UpdateReplaceSimpleList", true);
408: entityC.setSimpleList(Generators.createSimpleList());
409: persistCWithLists(entityC);
410:
411: final OWLClassC c = findRequired(OWLClassC.class, entityC.getUri());
412: final List<OWLClassA> newList = new ArrayList<>(1);
413: newList.add(entityA);
414: em.getTransaction().begin();
415: em.persist(entityA);
416: c.setSimpleList(newList);
417: em.getTransaction().commit();
418:
419: final OWLClassC resC = findRequired(OWLClassC.class, entityC.getUri());
420: assertEquals(newList.size(), resC.getSimpleList().size());
421: boolean found;
422: for (OWLClassA a : newList) {
423: found = false;
424: for (OWLClassA aa : resC.getSimpleList()) {
425: if (a.getUri().equals(aa.getUri())) {
426: found = true;
427: break;
428: }
429: }
430: assertTrue(found);
431: }
432: for (OWLClassA a : entityC.getSimpleList()) {
433: assertNotNull(em.find(OWLClassA.class, a.getUri()));
434: }
435: }
436:
437: @Test
438: void testRemoveFromReferencedList() {
439: this.em = getEntityManager("UpdateRemoveFromReferencedList", true);
440: entityC.setReferencedList(Generators.createReferencedList());
441: persistCWithLists(entityC);
442:
443: final OWLClassC c = findRequired(OWLClassC.class, entityC.getUri());
444: em.getTransaction().begin();
445: final OWLClassA a = c.getReferencedList().get(Generators.randomInt(c.getReferencedList().size()));
446: c.getReferencedList().remove(a);
447: em.getTransaction().commit();
448:
449: final OWLClassA resA = findRequired(OWLClassA.class, a.getUri());
450: final OWLClassC resC = findRequired(OWLClassC.class, c.getUri());
451: assertEquals(c.getReferencedList().size(), resC.getReferencedList().size());
452: assertEquals(entityC.getReferencedList().size() - 1, resC.getReferencedList().size());
453: for (OWLClassA aa : resC.getReferencedList()) {
454: assertNotEquals(resA.getUri(), aa.getUri());
455: }
456: }
457:
458: @Test
459: void testAddToReferencedList() {
460: this.em = getEntityManager("UpdateAddToReferencedList", true);
461: entityC.setReferencedList(Generators.createReferencedList());
462: persistCWithLists(entityC);
463:
464: em.getTransaction().begin();
465: final OWLClassC c = findRequired(OWLClassC.class, entityC.getUri());
466: em.persist(entityA);
467: c.getReferencedList().add(entityA);
468: em.getTransaction().commit();
469:
470: final OWLClassC resC = findRequired(OWLClassC.class, entityC.getUri());
471: assertEquals(c.getReferencedList().size(), resC.getReferencedList().size());
472: assertEquals(entityC.getReferencedList().size() + 1, resC.getReferencedList().size());
473: final OWLClassA resA = findRequired(OWLClassA.class, entityA.getUri());
474: assertTrue(resC.getReferencedList().contains(resA));
475: }
476:
477: @Test
478: void testClearReferencedList() {
479: this.em = getEntityManager("UpdateClearReferencedList", true);
480: entityC.setReferencedList(Generators.createReferencedList());
481: persistCWithLists(entityC);
482:
483: final OWLClassC c = findRequired(OWLClassC.class, entityC.getUri());
484: assertFalse(c.getReferencedList().isEmpty());
485: em.getTransaction().begin();
486: c.setReferencedList(null);
487: em.getTransaction().commit();
488:
489: final OWLClassC resC = findRequired(OWLClassC.class, entityC.getUri());
490: assertNull(resC.getReferencedList());
491: for (OWLClassA a : entityC.getReferencedList()) {
492: verifyExists(OWLClassA.class, a.getUri());
493: }
494: }
495:
496: @Test
497: void testReplaceReferencedList() {
498: this.em = getEntityManager("UpdateReplaceReferencedList", true);
499: entityC.setReferencedList(Generators.createReferencedList());
500: persistCWithLists(entityC);
501:
502: final OWLClassC c = findRequired(OWLClassC.class, entityC.getUri());
503: final List<OWLClassA> newList = new ArrayList<>(1);
504: newList.add(entityA);
505: em.getTransaction().begin();
506: em.persist(entityA);
507: c.setReferencedList(newList);
508: em.getTransaction().commit();
509:
510: final OWLClassC resC = findRequired(OWLClassC.class, entityC.getUri());
511: assertEquals(newList.size(), resC.getReferencedList().size());
512: boolean found;
513: for (OWLClassA a : newList) {
514: found = false;
515: for (OWLClassA aa : resC.getReferencedList()) {
516: if (a.getUri().equals(aa.getUri())) {
517: found = true;
518: break;
519: }
520: }
521: assertTrue(found);
522: }
523: for (OWLClassA a : entityC.getReferencedList()) {
524: verifyExists(OWLClassA.class, a.getUri());
525: }
526: }
527:
528: @Test
529: void testUpdateSimpleListOfIdentifiersByAddingNewItems() {
530: this.em = getEntityManager("UpdateSimpleListOfIdentifiersByAddingItems", true);
531: entityP.setSimpleList(Generators.createListOfIdentifiers());
532: persist(entityP);
533:
534: final OWLClassP update = findRequired(OWLClassP.class, entityP.getUri());
535: em.getTransaction().begin();
536:• for (int i = 0; i < Generators.randomPositiveInt(5, 10); i++) {
537: final URI u = URI.create(Vocabulary.INDIVIDUAL_IRI_BASE + "Added-" + i);
538: // Insert at random position
539: update.getSimpleList().add(Generators.randomInt(update.getSimpleList().size()), u);
540: }
541: em.getTransaction().commit();
542:
543: final OWLClassP res = findRequired(OWLClassP.class, entityP.getUri());
544: assertEquals(update.getSimpleList(), res.getSimpleList());
545: }
546:
547: @Test
548: void testUpdateReferencedListByRemovingAndAddingItems() {
549: this.em = getEntityManager("UpdateReferencedListByRemovingAndAddingItems", true);
550: entityP.setReferencedList(Generators.createListOfIdentifiers());
551: persist(entityP);
552:
553: final OWLClassP update = findRequired(OWLClassP.class, entityP.getUri());
554: em.getTransaction().begin();
555: for (int i = 0; i < Generators.randomPositiveInt(5, 10); i++) {
556: final URI u = URI.create(Vocabulary.INDIVIDUAL_IRI_BASE + "Added-" + i);
557: // We might even overwrite items set in previous iterations, but it does not matter. JOPA should handle it
558: update.getReferencedList().set(Generators.randomInt(update.getReferencedList().size()), u);
559: }
560: em.getTransaction().commit();
561:
562: final OWLClassP res = findRequired(OWLClassP.class, entityP.getUri());
563: assertEquals(update.getReferencedList(), res.getReferencedList());
564: }
565:
566: @Test
567: void updateKeepsPendingListReferenceWhenItemIsAddedToIt() {
568: this.em = getEntityManager("updateKeepsPendingListReferenceWhenItemIsAddedToIt", true);
569: final OWLClassK entityK = new OWLClassK();
570: entityK.setSimpleList(generateEInstances(5));
571: entityK.setReferencedList(generateEInstances(6));
572: em.getTransaction().begin();
573: em.persist(entityK);
574: entityK.getSimpleList().forEach(e -> {
575: assertNull(e.getUri());
576: em.persist(e);
577: });
578: entityK.getReferencedList().forEach(e -> {
579: assertNull(e.getUri());
580: em.persist(e);
581: });
582: em.getTransaction().commit();
583:
584: final OWLClassE addedSimple = new OWLClassE();
585: addedSimple.setStringAttribute("addedSimple");
586: final OWLClassE addedReferenced = new OWLClassE();
587: addedReferenced.setStringAttribute("addedReferenced");
588: em.getTransaction().begin();
589: final OWLClassK update = em.find(OWLClassK.class, entityK.getUri());
590: update.getSimpleList().add(addedSimple);
591: update.getReferencedList().add(addedReferenced);
592: assertNull(addedSimple.getUri());
593: assertNull(addedReferenced.getUri());
594: em.persist(addedSimple);
595: em.persist(addedReferenced);
596: em.getTransaction().commit();
597:
598: final OWLClassK result = findRequired(OWLClassK.class, entityK.getUri());
599: assertEquals(addedSimple.getUri(), result.getSimpleList().get(result.getSimpleList().size() - 1).getUri());
600: assertEquals(addedReferenced.getUri(),
601: result.getReferencedList().get(result.getReferencedList().size() - 1).getUri());
602: }
603:
604: private static List<OWLClassE> generateEInstances(int count) {
605: return IntStream.range(0, count).mapToObj(i -> {
606: final OWLClassE e = new OWLClassE();
607: e.setStringAttribute("instance" + i);
608: return e;
609: }).collect(Collectors.toList());
610: }
611:
612: @Test
613: void updateSupportsChangesInDataPropertyReferencedLists() {
614: this.em = getEntityManager("updateSupportsChangesInDataPropertyReferencedLists", false);
615: entityM.setLiteralReferencedList(Generators.createDataPropertyList());
616: persist(entityM);
617:
618: final List<LocalDate> updatedList = new ArrayList<>(entityM.getLiteralReferencedList());
619: updatedList.set(Generators.randomPositiveInt(0, updatedList.size()), LocalDate.now().minusDays(365));
620: updatedList.add(LocalDate.now().plusDays(365));
621: entityM.setLiteralReferencedList(updatedList);
622: transactional(() -> em.merge(entityM));
623:
624: final OWLClassM result = findRequired(OWLClassM.class, entityM.getKey());
625: assertEquals(updatedList, result.getLiteralReferencedList());
626: }
627:
628: @Test
629: void persistSupportsMultilingualReferencedLists() {
630: this.em = getEntityManager("persistSupportsMultilingualReferencedLists", false);
631: entityM.setMultilingualReferencedList(List.of(
632: new MultilingualString(Map.of("en", "First", "cs", "První")),
633: new MultilingualString(Map.of("en", "Second", "cs", "Druhý")),
634: new MultilingualString(Map.of("en", "Third", "cs", "Třetí"))
635: ));
636: persist(entityM);
637:
638: for (int i = 0; i < entityM.getMultilingualReferencedList().size(); i++) {
639: final URI hasNextProperty = URI.create(i == 0 ? Vocabulary.p_m_multilingualReferencedList : SequencesVocabulary.s_p_hasNext);
640: entityM.getMultilingualReferencedList().get(i).getValue()
641: .forEach((lang, value) -> assertTrue(em.createNativeQuery("ASK WHERE { ?prev ?hasNext ?node . ?node ?hasContent ?content . }", Boolean.class)
642: .setParameter("hasNext", hasNextProperty)
643: .setParameter("hasContent", URI.create(SequencesVocabulary.s_p_hasContents))
644: .setParameter("content", value, lang).getSingleResult()));
645: }
646: }
647:
648: @Test
649: void readSupportsMultilingualReferenceLists() throws Exception {
650: this.em = getEntityManager("readSupportsMultilingualReferenceLists", false);
651: final List<Quad> data = new ArrayList<>(List.of(new Quad(URI.create(entityM.getKey()), URI.create(RDF.TYPE), URI.create(Vocabulary.C_OWL_CLASS_M))));
652: final List<MultilingualString> strings = new ArrayList<>();
653: URI previous = URI.create(entityM.getKey());
654: for (int i = 5; i >= 0; i--) {
655: final MultilingualString mls = MultilingualString.create("Number " + i, "en");
656: mls.set("cs", "Číslo " + i);
657: strings.add(mls);
658: final URI node = URI.create(entityM.getKey() + "-SEQ" + (5 - i));
659: data.add(new Quad(previous, URI.create(i == 5 ? Vocabulary.p_m_multilingualReferencedList : SequencesVocabulary.s_p_hasNext), node));
660: mls.getValue()
661: .forEach((lang, val) -> data.add(new Quad(node, SequencesVocabulary.p_hasContents, new LangString(val, lang))));
662: previous = node;
663: }
664: persistTestData(data, em);
665:
666: final OWLClassM result = findRequired(OWLClassM.class, entityM.getKey());
667: assertEquals(strings, result.getMultilingualReferencedList());
668: }
669:
670: @Test
671: void updateSupportsChangesInMultilingualReferencedLists() {
672: this.em = getEntityManager("updateSupportsChangesInMultilingualReferencedLists", false);
673: entityM.setMultilingualReferencedList(List.of(
674: new MultilingualString(Map.of("en", "First", "cs", "První")),
675: new MultilingualString(Map.of("en", "Second", "cs", "Druhý")),
676: new MultilingualString(Map.of("en", "Third", "cs", "Třetí"))
677: ));
678: persist(entityM);
679:
680: final List<MultilingualString> newValue = new ArrayList<>(entityM.getMultilingualReferencedList());
681: newValue.set(Generators.randomPositiveInt(0, newValue.size()), new MultilingualString(Map.of("en", "New", "cs", "Nový")));
682: entityM.setMultilingualReferencedList(newValue);
683:
684: transactional(() -> em.merge(entityM));
685:
686: final OWLClassM result = findRequired(OWLClassM.class, entityM.getKey());
687: assertEquals(newValue, result.getMultilingualReferencedList());
688: }
689:
690: @Test
691: void removeMultilingualReferencedListItemRemovesStatementsFromRepository() {
692: this.em = getEntityManager("updateSupportsChangesInMultilingualReferencedLists", false);
693: entityM.setMultilingualReferencedList(List.of(
694: new MultilingualString(Map.of("en", "First", "cs", "První")),
695: new MultilingualString(Map.of("en", "Second", "cs", "Druhý")),
696: new MultilingualString(Map.of("en", "Third", "cs", "Třetí"))
697: ));
698: persist(entityM);
699: final MultilingualString toRemove = entityM.getMultilingualReferencedList()
700: .get(entityM.getMultilingualReferencedList().size() - 1);
701:
702: transactional(() -> {
703: final OWLClassM update = findRequired(OWLClassM.class, entityM.getKey());
704: update.getMultilingualReferencedList().remove(update.getMultilingualReferencedList().size() - 1);
705: });
706:
707: final OWLClassM result = findRequired(OWLClassM.class, entityM.getKey());
708: assertEquals(entityM.getMultilingualReferencedList().size() - 1, result.getMultilingualReferencedList().size());
709: toRemove.getValue()
710: .forEach((lang, val) -> assertFalse(em.createNativeQuery("ASK { ?node ?hasContent ?value }", Boolean.class)
711: .setParameter("hasContent", URI.create(Vocabulary.p_m_multilingualReferencedList))
712: .setParameter("value", val, lang).getSingleResult()));
713: }
714:
715: @Test
716: public void persistSavesRdfCollectionTerminatedByNil() {
717: this.em = getEntityManager("persistSavesRdfCollectionTerminatedByNil", false);
718: entityC.setRdfCollection(Generators.createRDFCollection(5));
719: persistCWithLists(entityC);
720:
721: final OWLClassC result = findRequired(OWLClassC.class, entityC.getUri());
722: assertEquals(entityC.getRdfCollection(), result.getRdfCollection());
723: assertTrue(em.createNativeQuery("ASK { ?node ?hasNext ?nil . }", Boolean.class)
724: .setParameter("hasNext", URI.create(RDF.REST))
725: .setParameter("nil", URI.create(RDF.NIL)).getSingleResult());
726: }
727:
728: @Test
729: public void updateUpdatesRdfCollectionTerminatedByNilAndMaintainsCorrectListEnding() {
730: this.em = getEntityManager("updateUpdatesRdfCollectionTerminatedByNilAndMaintainsCorrectListEnding", false);
731: entityC.setRdfCollection(Generators.createRDFCollection(5));
732: persistCWithLists(entityC);
733:
734: final List<OWLClassA> expectedList = new ArrayList<>(entityC.getRdfCollection());
735: entityC.getRdfCollection().remove(entityC.getRdfCollection().size() - 1);
736: expectedList.remove(expectedList.size() - 1);
737:
738: transactional(() -> em.merge(entityC));
739: final OWLClassC midUpdate = findRequired(OWLClassC.class, entityC.getUri());
740: assertEquals(expectedList, midUpdate.getRdfCollection());
741: assertEquals(1, em.createNativeQuery("SELECT (COUNT(?node) as ?cnt) WHERE { ?node ?hasNext ?nil . }", Integer.class)
742: .setParameter("hasNext", URI.create(RDF.REST))
743: .setParameter("nil", URI.create(RDF.NIL)).getSingleResult());
744: em.clear();
745:
746: final OWLClassA added = new OWLClassA(Generators.generateUri());
747: midUpdate.getRdfCollection().add(added);
748: expectedList.add(added);
749: transactional(() -> {
750: em.merge(midUpdate);
751: em.persist(added);
752: });
753: final OWLClassC result = findRequired(OWLClassC.class, entityC.getUri());
754: // Trigger lazy loading
755: assertFalse(result.getRdfCollection().isEmpty());
756: assertEquals(expectedList, result.getRdfCollection());
757: assertEquals(1, em.createNativeQuery("SELECT (COUNT(?node) as ?cnt) WHERE { ?node ?hasNext ?nil . }", Integer.class)
758: .setParameter("hasNext", URI.create(RDF.REST))
759: .setParameter("nil", URI.create(RDF.NIL)).getSingleResult());
760: }
761: }