]> gerrit.simantics Code Review - simantics/platform.git/blob - tests/org.simantics.db.tests/src/org/simantics/db/tests/regression/bugs/SimanticsBug1659Test1.java
Multiple reader thread support for db client
[simantics/platform.git] / tests / org.simantics.db.tests / src / org / simantics / db / tests / regression / bugs / SimanticsBug1659Test1.java
1 package org.simantics.db.tests.regression.bugs;
2
3 import org.junit.Test;
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;
20
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;
32     Session session;
33     Resource testRoot;
34     Resource type;
35     DataContainer<Integer> loopCount = new DataContainer<Integer>();
36     DataContainer<Integer> listenerCount = new DataContainer<Integer>();
37     
38     @Test
39     public void testSimanticsBug16591()
40     throws DatabaseException {
41         session = getSession();
42         session.syncRequest(new Init());
43         loopCount.set(-1);
44         listenerCount.set(0);
45         int oldCount = 0;
46         for (int i=0; i<LOOP_COUNT; ++i) {
47             loopCount.set(i);
48             if (DEBUG)
49                 System.out.println("Create " + i);
50             session.syncRequest(new Create());
51             if (DEBUG)
52                 System.out.println("Query " + i);
53             session.syncRequest(new Query());
54             if (DEBUG)
55                 System.out.println("Delete loop=" + i + " listeners=" + listenerCount.get());
56             loopCount.set(-1);
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);
62                 oldCount = count;
63             }
64             session.syncRequest(new Delete());
65             if (DEBUG)
66                 System.out.println("Done " + i);
67 //            if (DEBUG)
68 //                System.out.println("collect " + i);
69 //            try {
70 //                Thread.sleep(100);
71 //            } catch (InterruptedException e) {
72 //                e.printStackTrace();
73 //            }
74         }
75     }
76     class Init extends WriteRequest {
77         @Override
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);          
86         }
87     }
88     class Create extends WriteRequest {
89         @Override
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) {
96                 if (i % 10000 == 0) {
97                     if (DEBUG)
98                         System.out.println("flush");
99                     g.flushCluster();
100                 }
101                 Resource r = g.newResource();
102                 g.claim(r, l0.InstanceOf, type);
103                 g.claim(root, l0.ConsistsOf, r);
104             }
105         }
106     }
107     class Query extends AsyncReadRequest {
108         @Override
109         public void run(AsyncReadGraph g) {
110                 try {
111                         Layer0 l0 = Layer0.getInstance(g);
112                         for (Resource r : g.getObjects(testRoot, l0.ConsistsOf)) {
113                                 if (DEBUG)
114                                         System.out.println("Resource " + r);
115                                 for (Resource rr : g.getObjects(r, l0.ConsistsOf)) {
116                                         //                    if (DEBUG)
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.");
122                                         if (USE_LISTENER)
123                                                 g.forPossibleObject(rr, l0.InstanceOf, new SyncListener<Resource>() {
124
125                                                         @Override
126                                                         public void execute(ReadGraph graph, Resource resource) throws DatabaseException {
127                                                                 if (DEBUG_LISTENER)
128                                                                         System.out.println("change " + resource);
129                                                         }
130
131                                                         @Override
132                                                         public void exception(ReadGraph graph, Throwable t)
133                                                                         throws DatabaseException {
134                                                                 t.printStackTrace();
135                                                                 fail("Listener got exception: " + t);
136                                                         }
137
138                                                         @Override
139                                                         public boolean isDisposed() {
140                                                                 if (DEBUG_LISTENER)
141                                                                         System.out.println("Asked if disposed.");
142                                                                 return true;
143                                                         }
144                                                 });
145                                         if (USE_LISTENER2) {
146                                                 g.forPossibleObject(rr, l0.InstanceOf, new Listener(loopCount, listenerCount));
147                                         }
148                                         if (USE_LISTENER3) {
149                                                 g.syncRequest(new PossibleObject(rr, l0.InstanceOf), new Listener(loopCount, listenerCount));
150                                         }
151                                 }
152                         }
153                 } catch (DatabaseException e) {
154                         e.printStackTrace();
155                 }
156         }
157     }
158     class Listener implements SyncListener<Resource> {
159         final DataContainer<Integer> loopCount;
160         final DataContainer<Integer> listenerCount;
161         final int me;
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();
169         }
170         @Override
171         public void execute(ReadGraph graph, Resource resource) throws DatabaseException {
172             if (DEBUG_LISTENER)
173                 System.out.println("change " + resource);
174         }
175
176         @Override
177         public void exception(ReadGraph graph, Throwable t)
178                 throws DatabaseException {
179             t.printStackTrace();
180             fail("Listener got exception: " + t);
181         }
182
183         @Override
184         public boolean isDisposed() {
185             if (DEBUG_LISTENER)
186                 System.out.println("Asked if disposed.");
187             if (disposed)
188                 return true;
189             disposed = loopCount.get() != me;
190             if (disposed) {
191                 int value = this.listenerCount.get() - 1;
192                 this.listenerCount.set(value);
193             }
194             return disposed;
195         }
196         
197     }
198     class Delete extends WriteRequest {
199         @Override
200         public void perform(WriteGraph g) throws DatabaseException {
201             Layer0 l0 = Layer0.getInstance(g);
202             for (Resource r : g.getObjects(testRoot, l0.ConsistsOf)) {
203                 if (DEBUG)
204                     System.out.println("Deny resource " + r);
205                 g.deny(testRoot, l0.ConsistsOf, r);
206             }
207         }
208     }
209 }