1 package org.simantics.db.tests.regression.bugs;
4 import org.simantics.db.AsyncReadGraph;
5 import org.simantics.db.ReadGraph;
6 import org.simantics.db.Resource;
7 import org.simantics.db.Session;
8 import org.simantics.db.WriteGraph;
9 import org.simantics.db.common.primitiverequest.PossibleObject;
10 import org.simantics.db.common.request.AsyncReadRequest;
11 import org.simantics.db.common.request.WriteRequest;
12 import org.simantics.db.exception.DatabaseException;
13 import org.simantics.db.procedure.SyncListener;
14 import org.simantics.db.service.ClusterControl;
15 import org.simantics.db.testing.base.ExistingDatabaseTest;
16 import org.simantics.db.testing.common.TestBase;
17 import org.simantics.db.tests.common.Configuration;
18 import org.simantics.layer0.Layer0;
19 import org.simantics.utils.DataContainer;
21 public class SimanticsBug1659Test1 extends ExistingDatabaseTest {
22 static int LOOP_COUNT = Configuration.get().i1659LoopCount;
23 static int RESOURCE_COUNT = 1000;
24 static boolean DEBUG = false;
25 static boolean DEBUG_LISTENER = false;
26 // Use transient listener.
27 static boolean USE_LISTENER = true;
28 // Use asynchronous listener.
29 static boolean USE_LISTENER2 = true;
30 // Use synchronous listener
31 static boolean USE_LISTENER3 = true;
35 DataContainer<Integer> loopCount = new DataContainer<Integer>();
36 DataContainer<Integer> listenerCount = new DataContainer<Integer>();
39 public void testSimanticsBug16591()
40 throws DatabaseException {
41 session = getSession();
42 session.syncRequest(new Init());
46 for (int i=0; i<LOOP_COUNT; ++i) {
49 System.out.println("Create " + i);
50 session.syncRequest(new Create());
52 System.out.println("Query " + i);
53 session.syncRequest(new Query());
55 System.out.println("Delete loop=" + i + " listeners=" + listenerCount.get());
57 ClusterControl support = getSession().getService(ClusterControl.class);
58 support.collectClusters(Integer.MAX_VALUE);
59 int count = listenerCount.get();
60 if (oldCount != count) {
61 // System.out.println("Listener count is " + count);
64 session.syncRequest(new Delete());
66 System.out.println("Done " + i);
68 // System.out.println("collect " + i);
71 // } catch (InterruptedException e) {
72 // e.printStackTrace();
76 class Init extends WriteRequest {
78 public void perform(WriteGraph g) throws DatabaseException {
79 Layer0 l0 = Layer0.getInstance(g);
80 Resource rl = g.getResource(TestBase.ROOT_LIBRARY_URI);
81 testRoot = g.newResource();
82 g.claim(testRoot, l0.InstanceOf, l0.Library);
83 g.claim(rl, l0.ConsistsOf, testRoot);
84 type = g.newResource();
85 g.claim(type, l0.Inherits, l0.Entity);
88 class Create extends WriteRequest {
90 public void perform(WriteGraph g) throws DatabaseException {
91 Resource root = g.newResource();
92 Layer0 l0 = Layer0.getInstance(g);
93 g.claim(root, l0.InstanceOf, l0.Library);
94 g.claim(testRoot, l0.ConsistsOf, root);
95 for (int i=0; i<RESOURCE_COUNT; ++i) {
98 System.out.println("flush");
101 Resource r = g.newResource();
102 g.claim(r, l0.InstanceOf, type);
103 g.claim(root, l0.ConsistsOf, r);
107 class Query extends AsyncReadRequest {
109 public void run(AsyncReadGraph g) {
111 Layer0 l0 = Layer0.getInstance(g);
112 for (Resource r : g.getObjects(testRoot, l0.ConsistsOf)) {
114 System.out.println("Resource " + r);
115 for (Resource rr : g.getObjects(r, l0.ConsistsOf)) {
117 // System.out.println("Resource " + rr);
118 if (!g.isInstanceOf(rr, type))
119 fail("Resource " + rr + " is not instance of type.");
120 if (!g.isInstanceOf(rr, l0.Entity))
121 fail("Resource " + rr + " is not instance of Entity.");
123 g.forPossibleObject(rr, l0.InstanceOf, new SyncListener<Resource>() {
126 public void execute(ReadGraph graph, Resource resource) throws DatabaseException {
128 System.out.println("change " + resource);
132 public void exception(ReadGraph graph, Throwable t)
133 throws DatabaseException {
135 fail("Listener got exception: " + t);
139 public boolean isDisposed() {
141 System.out.println("Asked if disposed.");
146 g.forPossibleObject(rr, l0.InstanceOf, new Listener(loopCount, listenerCount));
149 g.syncRequest(new PossibleObject(rr, l0.InstanceOf), new Listener(loopCount, listenerCount));
153 } catch (DatabaseException e) {
158 class Listener implements SyncListener<Resource> {
159 final DataContainer<Integer> loopCount;
160 final DataContainer<Integer> listenerCount;
162 boolean disposed = false;
163 Listener(DataContainer<Integer> loopCount, DataContainer<Integer> listenerCount) {
164 this.loopCount = loopCount;
165 this.listenerCount = listenerCount;
166 int value = this.listenerCount.get() + 1;
167 this.listenerCount.set(value);
168 this.me = loopCount.get();
171 public void execute(ReadGraph graph, Resource resource) throws DatabaseException {
173 System.out.println("change " + resource);
177 public void exception(ReadGraph graph, Throwable t)
178 throws DatabaseException {
180 fail("Listener got exception: " + t);
184 public boolean isDisposed() {
186 System.out.println("Asked if disposed.");
189 disposed = loopCount.get() != me;
191 int value = this.listenerCount.get() - 1;
192 this.listenerCount.set(value);
198 class Delete extends WriteRequest {
200 public void perform(WriteGraph g) throws DatabaseException {
201 Layer0 l0 = Layer0.getInstance(g);
202 for (Resource r : g.getObjects(testRoot, l0.ConsistsOf)) {
204 System.out.println("Deny resource " + r);
205 g.deny(testRoot, l0.ConsistsOf, r);