--- /dev/null
+package fi.vtt.simantics.procore.internal;\r
+\r
+import org.simantics.db.AsyncReadGraph;\r
+import org.simantics.db.DirectStatements;\r
+import org.simantics.db.ReadGraph;\r
+import org.simantics.db.RelationInfo;\r
+import org.simantics.db.Resource;\r
+import org.simantics.db.common.procedure.wrapper.NoneToAsyncProcedure;\r
+import org.simantics.db.common.procedure.wrapper.SyncToAsyncProcedure;\r
+import org.simantics.db.exception.DatabaseException;\r
+import org.simantics.db.impl.ClusterI;\r
+import org.simantics.db.impl.ClusterI.ClusterTypeEnum;\r
+import org.simantics.db.impl.ForEachObjectContextProcedure;\r
+import org.simantics.db.impl.ForEachObjectProcedure;\r
+import org.simantics.db.impl.ForPossibleRelatedValueContextProcedure;\r
+import org.simantics.db.impl.ForPossibleRelatedValueProcedure;\r
+import org.simantics.db.impl.ResourceImpl;\r
+import org.simantics.db.impl.TransientGraph;\r
+import org.simantics.db.impl.graph.ReadGraphImpl;\r
+import org.simantics.db.procedure.AsyncContextMultiProcedure;\r
+import org.simantics.db.procedure.AsyncContextProcedure;\r
+import org.simantics.db.procedure.AsyncMultiProcedure;\r
+import org.simantics.db.procedure.AsyncProcedure;\r
+import org.simantics.db.procedure.Procedure;\r
+import org.simantics.db.procedure.SyncProcedure;\r
+import org.simantics.db.procore.cluster.ClusterBig;\r
+import org.simantics.db.procore.cluster.ClusterImpl;\r
+import org.simantics.db.procore.cluster.ClusterSmall;\r
+import org.simantics.db.procore.cluster.ResourceTableSmall;\r
+import org.simantics.db.procore.cluster.ValueTableSmall;\r
+import org.simantics.db.request.AsyncRead;\r
+import org.simantics.db.service.DirectQuerySupport;\r
+import org.simantics.utils.datastructures.Callback;\r
+\r
+public class DirectQuerySupportImpl implements DirectQuerySupport {\r
+\r
+ final private SessionImplSocket session;\r
+ \r
+ DirectQuerySupportImpl(SessionImplSocket session) {\r
+ this.session = session;\r
+ }\r
+\r
+ @Override\r
+ final public void forEachDirectPersistentStatement(AsyncReadGraph graph, final Resource subject, final AsyncProcedure<DirectStatements> procedure) {\r
+ ReadGraphImpl impl = (ReadGraphImpl)graph;\r
+ impl.processor.forEachDirectStatement(impl, subject, procedure, true);\r
+ }\r
+\r
+ @Override\r
+ final public void forEachDirectStatement(AsyncReadGraph graph, final Resource subject, final AsyncProcedure<DirectStatements> procedure) {\r
+ ReadGraphImpl impl = (ReadGraphImpl)graph;\r
+ impl.processor.forEachDirectStatement(impl, subject, procedure, false);\r
+ }\r
+\r
+ @Override\r
+ public void forEachDirectStatement(AsyncReadGraph graph, Resource subject, SyncProcedure<DirectStatements> procedure) {\r
+ forEachDirectStatement(graph, subject, new SyncToAsyncProcedure<DirectStatements>(procedure));\r
+ }\r
+\r
+ @Override\r
+ public void forEachDirectStatement(AsyncReadGraph graph, Resource subject, Procedure<DirectStatements> procedure) {\r
+ ReadGraphImpl impl = (ReadGraphImpl)graph;\r
+ impl.processor.forEachDirectStatement(impl, subject, procedure);\r
+ }\r
+\r
+ @Override\r
+ public void forRelationInfo(AsyncReadGraph graph, Resource subject, AsyncProcedure<RelationInfo> procedure) {\r
+ ReadGraphImpl impl = (ReadGraphImpl)graph;\r
+ impl.processor.forRelationInfo(impl, subject, procedure);\r
+ }\r
+\r
+ @Override\r
+ public void forRelationInfo(AsyncReadGraph graph, Resource subject, SyncProcedure<RelationInfo> procedure) {\r
+ forRelationInfo(graph, subject, new SyncToAsyncProcedure<RelationInfo>(procedure));\r
+ }\r
+\r
+ @Override\r
+ public void forRelationInfo(AsyncReadGraph graph, Resource subject, Procedure<RelationInfo> procedure) {\r
+ forRelationInfo(graph, subject, new NoneToAsyncProcedure<RelationInfo>(procedure));\r
+ }\r
+\r
+ @Override\r
+ public AsyncMultiProcedure<Resource> compileForEachObject(ReadGraph graph, final Resource relation, AsyncMultiProcedure<Resource> user) {\r
+ \r
+ try {\r
+ RelationInfo info = graph.syncRequest(new AsyncRead<RelationInfo>() {\r
+\r
+ @Override\r
+ public void perform(AsyncReadGraph graph, AsyncProcedure<RelationInfo> procedure) {\r
+ forRelationInfo(graph, relation, procedure);\r
+ }\r
+\r
+ @Override\r
+ public int threadHash() {\r
+ return hashCode();\r
+ }\r
+\r
+ @Override\r
+ public int getFlags() {\r
+ return 0;\r
+ }\r
+\r
+ });\r
+ final int predicateKey = ((ResourceImpl)relation).id;\r
+ return new ForEachObjectProcedure(predicateKey, info, session.queryProvider2, user);\r
+ } catch (DatabaseException e) {\r
+ return null;\r
+ } \r
+ \r
+ }\r
+\r
+ @Override\r
+ public <C> AsyncContextMultiProcedure<C, Resource> compileForEachObject(ReadGraph graph, final Resource relation, AsyncContextMultiProcedure<C, Resource> user) {\r
+ \r
+ try {\r
+ RelationInfo info = graph.syncRequest(new AsyncRead<RelationInfo>() {\r
+\r
+ @Override\r
+ public void perform(AsyncReadGraph graph, AsyncProcedure<RelationInfo> procedure) {\r
+ forRelationInfo(graph, relation, procedure);\r
+ }\r
+\r
+ @Override\r
+ public int threadHash() {\r
+ return hashCode();\r
+ }\r
+\r
+ @Override\r
+ public int getFlags() {\r
+ return 0;\r
+ }\r
+\r
+ });\r
+ final int predicateKey = ((ResourceImpl)relation).id;\r
+ return new ForEachObjectContextProcedure<C>(predicateKey, info, session.queryProvider2, user);\r
+ } catch (DatabaseException e) {\r
+ return null;\r
+ } \r
+ \r
+ }\r
+ \r
+ @Override\r
+ public <T> AsyncProcedure<T> compilePossibleRelatedValue(ReadGraph graph, final Resource relation, AsyncProcedure<T> user) {\r
+ \r
+ try {\r
+ RelationInfo info = graph.syncRequest(new AsyncRead<RelationInfo>() {\r
+\r
+ @Override\r
+ public void perform(AsyncReadGraph graph, AsyncProcedure<RelationInfo> procedure) {\r
+ forRelationInfo(graph, relation, procedure);\r
+ }\r
+\r
+ @Override\r
+ public int threadHash() {\r
+ return hashCode();\r
+ }\r
+\r
+ @Override\r
+ public int getFlags() {\r
+ return 0;\r
+ }\r
+\r
+ });\r
+ final int predicateKey = ((ResourceImpl)relation).id;\r
+ return new ForPossibleRelatedValueProcedure<T>(predicateKey, info, user);\r
+ } catch (DatabaseException e) {\r
+ return null;\r
+ } \r
+ \r
+ }\r
+\r
+ @Override\r
+ public <C, T> AsyncContextProcedure<C, T> compilePossibleRelatedValue(ReadGraph graph, final Resource relation, AsyncContextProcedure<C, T> user) {\r
+ \r
+ try {\r
+ RelationInfo info = graph.syncRequest(new AsyncRead<RelationInfo>() {\r
+\r
+ @Override\r
+ public void perform(AsyncReadGraph graph, AsyncProcedure<RelationInfo> procedure) {\r
+ forRelationInfo(graph, relation, procedure);\r
+ }\r
+\r
+ @Override\r
+ public int threadHash() {\r
+ return hashCode();\r
+ }\r
+\r
+ @Override\r
+ public int getFlags() {\r
+ return 0;\r
+ }\r
+\r
+ });\r
+ final int predicateKey = ((ResourceImpl)relation).id;\r
+ return new ForPossibleRelatedValueContextProcedure<C, T>(predicateKey, info, user);\r
+ } catch (DatabaseException e) {\r
+ return null;\r
+ } \r
+ \r
+ }\r
+ \r
+ @Override\r
+ public void forEachObjectCompiled(AsyncReadGraph graph, Resource subject, final AsyncMultiProcedure<Resource> procedure) {\r
+ \r
+ assert(subject != null);\r
+ \r
+ final ForEachObjectProcedure proc = (ForEachObjectProcedure)procedure;\r
+// final RelationInfo info = proc.info;\r
+\r
+ final ReadGraphImpl impl = (ReadGraphImpl)graph;\r
+ final int subjectId = ((ResourceImpl)subject).id;\r
+\r
+// int callerThread = impl.callerThread;\r
+// int suggestSchedule = (subjectId>>16) & queryProvider2.THREAD_MASK;\r
+ \r
+// impl.inc();\r
+ \r
+// if(callerThread == suggestSchedule) {\r
+ \r
+// if(info.isFunctional) {\r
+// querySupport.getObjects4(impl, subjectId, proc);\r
+// } else {\r
+ session.querySupport.getObjects4(impl, subjectId, proc);\r
+// }\r
+ \r
+// } else {\r
+// \r
+// impl.state.barrier.inc();\r
+// impl.state.barrier.dec(callerThread);\r
+// \r
+// queryProvider2.schedule(callerThread, new SessionTask(suggestSchedule) {\r
+// \r
+// @Override\r
+// public void run(int thread) {\r
+// \r
+// impl.state.barrier.inc(thread);\r
+// impl.state.barrier.dec();\r
+//\r
+// if(info.isFunctional) {\r
+// querySupport.getObjects4(impl.newAsync(thread), subjectId, proc);\r
+// } else {\r
+// querySupport.getObjects4(impl.newAsync(thread), subjectId, proc);\r
+// }\r
+// \r
+// }\r
+// \r
+// @Override\r
+// public String toString() {\r
+// return "gaff8";\r
+// }\r
+// \r
+// });\r
+// \r
+// }\r
+ \r
+ }\r
+\r
+ @Override\r
+ public <C> void forEachObjectCompiled(AsyncReadGraph graph, Resource subject, C context, final AsyncContextMultiProcedure<C, Resource> procedure) {\r
+ \r
+ assert(subject != null);\r
+\r
+ final ForEachObjectContextProcedure<C> proc = (ForEachObjectContextProcedure<C>)procedure;\r
+ final RelationInfo info = proc.info;\r
+\r
+ final ReadGraphImpl impl = (ReadGraphImpl)graph;\r
+ final int subjectId = ((ResourceImpl)subject).id;\r
+\r
+// int callerThread = impl.callerThread;\r
+// int suggestSchedule = (subjectId>>16) & queryProvider2.THREAD_MASK;\r
+\r
+// impl.inc();\r
+\r
+ if(info.isFunctional) {\r
+ session.querySupport.getObjects4(impl, subjectId, context, proc);\r
+ } else {\r
+ session.querySupport.getObjects4(impl, subjectId, context, proc);\r
+ }\r
+ \r
+ }\r
+ \r
+ @Override\r
+ public <T> void forPossibleRelatedValueCompiled(AsyncReadGraph graph, Resource subject, final AsyncProcedure<T> procedure) {\r
+ \r
+ assert(subject != null);\r
+\r
+ final ForPossibleRelatedValueProcedure<T> proc = (ForPossibleRelatedValueProcedure<T>)procedure;\r
+ final RelationInfo info = proc.info;\r
+ \r
+ final ReadGraphImpl impl = (ReadGraphImpl)graph;\r
+ final int subjectId = ((ResourceImpl)subject).id;\r
+ \r
+// int callerThread = impl.callerThread;\r
+// int suggestSchedule = (subjectId>>16) & session.queryProvider2.THREAD_MASK;\r
+ \r
+// impl.inc();\r
+ \r
+// if(callerThread == suggestSchedule) {\r
+ \r
+ if(info.isFunctional) {\r
+ getRelatedValue4(impl, subjectId, proc);\r
+ } else {\r
+ getRelatedValue4(impl, subjectId, proc);\r
+ }\r
+ \r
+// } else {\r
+// \r
+// impl.state.barrier.inc();\r
+// impl.state.barrier.dec(callerThread);\r
+// \r
+// queryProvider2.schedule(callerThread, new SessionTask(suggestSchedule) {\r
+// \r
+// @Override\r
+// public void run(int thread) {\r
+//\r
+// impl.state.barrier.inc(thread);\r
+// impl.state.barrier.dec();\r
+// \r
+// if(info.isFunctional) {\r
+// getRelatedValue4(impl.newAsync(thread), subjectId, proc);\r
+// } else {\r
+// getRelatedValue4(impl.newAsync(thread), subjectId, proc);\r
+// }\r
+// \r
+// }\r
+// \r
+// @Override\r
+// public String toString() {\r
+// return "gaff11";\r
+// }\r
+// \r
+// });\r
+// \r
+// }\r
+ \r
+ }\r
+\r
+ @Override\r
+ public <C, T> void forPossibleRelatedValueCompiled(AsyncReadGraph graph, Resource subject, C context, final AsyncContextProcedure<C, T> procedure) {\r
+ \r
+ assert(subject != null);\r
+\r
+ final ForPossibleRelatedValueContextProcedure<C, T> proc = (ForPossibleRelatedValueContextProcedure<C, T>)procedure;\r
+ final RelationInfo info = proc.info;\r
+ \r
+ final ReadGraphImpl impl = (ReadGraphImpl)graph;\r
+ final int subjectId = ((ResourceImpl)subject).id;\r
+ \r
+// int callerThread = impl.callerThread;\r
+// int suggestSchedule = (subjectId>>16) & session.queryProvider2.THREAD_MASK;\r
+ \r
+// impl.inc();\r
+ \r
+ if(info.isFunctional) {\r
+ getRelatedValue4(impl, subjectId, context, proc);\r
+ } else {\r
+ getRelatedValue4(impl, subjectId, context, proc);\r
+ }\r
+ \r
+ }\r
+ \r
+ @Override\r
+ public <T> void forPossibleType(final AsyncReadGraph graph, Resource subject, final AsyncProcedure<Resource> procedure) {\r
+ \r
+ assert(subject != null);\r
+\r
+ final ReadGraphImpl impl = (ReadGraphImpl)graph;\r
+ final int subjectId = ((ResourceImpl)subject).id;\r
+\r
+ try {\r
+ \r
+ final ClusterI cluster = session.clusterTable.getClusterByResourceKey(subjectId);\r
+ if(!cluster.isLoaded()) {\r
+\r
+// impl.state.inc(0);\r
+ \r
+ session.queryProvider2.requestCluster(impl, cluster.getClusterId(), new Runnable() {\r
+ \r
+ @Override\r
+ public void run() {\r
+\r
+ try {\r
+\r
+ int result = cluster.getCompleteObjectKey(subjectId, session.clusterTranslator);\r
+ procedure.execute(graph, new ResourceImpl(session.resourceSupport, result));\r
+\r
+// impl.state.dec(0); \r
+ \r
+ } catch (DatabaseException e) {\r
+ e.printStackTrace();\r
+ }\r
+ \r
+ }\r
+ \r
+ });\r
+ \r
+ } else {\r
+\r
+ int result = cluster.getCompleteObjectKey(subjectId, session.clusterTranslator);\r
+ procedure.execute(graph, new ResourceImpl(session.resourceSupport, result));\r
+ \r
+ }\r
+ \r
+ } catch (DatabaseException e) {\r
+ e.printStackTrace();\r
+ }\r
+ \r
+ \r
+ \r
+ }\r
+\r
+ @Override\r
+ public <C> void forPossibleDirectType(final AsyncReadGraph graph, Resource subject, final C context, final AsyncContextProcedure<C, Resource> procedure) {\r
+ \r
+ assert(subject != null);\r
+\r
+ final ReadGraphImpl impl = (ReadGraphImpl)graph;\r
+ final int subjectId = ((ResourceImpl)subject).id;\r
+ \r
+ try {\r
+ \r
+ final ClusterI cluster = session.clusterTable.getClusterByResourceKey(subjectId);\r
+ if(!cluster.isLoaded()) {\r
+\r
+// impl.state.inc(0);\r
+ \r
+ session.queryProvider2.requestCluster(impl, cluster.getClusterId(), new Runnable() {\r
+ \r
+ @Override\r
+ public void run() {\r
+\r
+ try {\r
+\r
+ ClusterI.CompleteTypeEnum type = cluster.getCompleteType(subjectId, session.clusterTranslator);\r
+ if(ClusterI.CompleteTypeEnum.InstanceOf == type) {\r
+ int result = cluster.getCompleteObjectKey(subjectId, session.clusterTranslator);\r
+ procedure.execute(graph, context, new ResourceImpl(session.resourceSupport, result));\r
+ } else {\r
+ procedure.execute(graph, context, null);\r
+ }\r
+\r
+// impl.state.dec(0);\r
+ \r
+ } catch (DatabaseException e) {\r
+ e.printStackTrace();\r
+ }\r
+ \r
+ }\r
+ \r
+ });\r
+ \r
+ } else {\r
+\r
+ ClusterI.CompleteTypeEnum type = cluster.getCompleteType(subjectId, session.clusterTranslator);\r
+ if(ClusterI.CompleteTypeEnum.InstanceOf == type) {\r
+ int result = cluster.getCompleteObjectKey(subjectId, session.clusterTranslator);\r
+ procedure.execute(graph, context, new ResourceImpl(session.resourceSupport, result));\r
+ } else {\r
+ procedure.execute(graph, context, null);\r
+ }\r
+ \r
+ }\r
+ \r
+ } catch (DatabaseException e) {\r
+ \r
+ procedure.execute(graph, context, null);\r
+ \r
+ } catch (Throwable t) {\r
+\r
+ t.printStackTrace();\r
+ procedure.execute(graph, context, null);\r
+ \r
+ }\r
+ \r
+ }\r
+ \r
+ \r
+ private <C, T> void getRelatedValue4(final ReadGraphImpl graph, final int subject, final C context, final ForPossibleRelatedValueContextProcedure<C, T> procedure) {\r
+ \r
+ int result = 0;\r
+ \r
+ final int predicate = procedure.predicateKey;\r
+\r
+ if(subject < 0) {\r
+\r
+ if(!SessionImplSocket.areVirtualStatementsLoaded(session.virtualGraphServerSupport, subject, predicate)) {\r
+ SessionImplSocket.loadVirtualStatements(session.virtualGraphServerSupport, graph, subject, predicate, new Callback<ReadGraphImpl>() {\r
+\r
+ @Override\r
+ public void run(ReadGraphImpl graph) {\r
+ getRelatedValue4(graph, subject, context, procedure);\r
+ }\r
+ \r
+ });\r
+ return;\r
+ }\r
+ \r
+ for(TransientGraph g : session.virtualGraphServerSupport.providers) {\r
+ for (int id : g.getObjects(subject, predicate)) {\r
+ if(result != 0) {\r
+ procedure.exception(graph, new DatabaseException("Multiple objects"));\r
+// graph.dec();\r
+ return;\r
+ } else {\r
+ result = id;\r
+ }\r
+ }\r
+ }\r
+ \r
+ if(result == 0) {\r
+ \r
+ procedure.exception(graph, new DatabaseException("No objects for " + subject ));\r
+// graph.dec();\r
+ return;\r
+ \r
+ } else {\r
+ \r
+ getValue4(graph, null, result, context, procedure);\r
+ return;\r
+ \r
+ }\r
+ \r
+ } \r
+ \r
+ final org.simantics.db.procore.cluster.ClusterImpl cluster = session.clusterTable.getClusterByResourceKey(subject);\r
+ if(!cluster.isLoaded()) {\r
+ cluster.load(session.clusterTranslator, new Runnable() {\r
+\r
+ @Override\r
+ public void run() {\r
+ getRelatedValue4(graph, subject, context, procedure);\r
+ }\r
+ \r
+ });\r
+ return;\r
+ }\r
+ \r
+ if(cluster.hasVirtual() && session.virtualGraphServerSupport.virtuals.contains(subject)) {\r
+ \r
+ if(!SessionImplSocket.areVirtualStatementsLoaded(session.virtualGraphServerSupport, subject, predicate)) {\r
+ SessionImplSocket.loadVirtualStatements(session.virtualGraphServerSupport, graph, subject, predicate, new Callback<ReadGraphImpl>() {\r
+\r
+ @Override\r
+ public void run(ReadGraphImpl graph) {\r
+ getRelatedValue4(graph, subject, context, procedure);\r
+ }\r
+ \r
+ });\r
+ return;\r
+ }\r
+ \r
+ for(TransientGraph g : session.virtualGraphServerSupport.providers) {\r
+ for (int id : g.getObjects(subject, predicate)) {\r
+ if(result != 0) {\r
+ procedure.exception(graph, new DatabaseException("Multiple objects"));\r
+// graph.dec();\r
+ return;\r
+ } else {\r
+ result = id;\r
+ }\r
+ }\r
+ }\r
+ \r
+ getRelatedDirectValue4(graph, cluster, subject, result, context, procedure);\r
+ \r
+ } else {\r
+ \r
+ getRelatedDirectValue4(graph, cluster, subject, 0, context, procedure);\r
+ \r
+ }\r
+ \r
+ }\r
+ \r
+ private <T> void getValue4(final ReadGraphImpl graph, final ClusterImpl containerCluster, final int subject, final ForPossibleRelatedValueProcedure<T> procedure) {\r
+ \r
+ Object result = null;\r
+ \r
+ if(subject < 0) {\r
+\r
+ if(!SessionImplSocket.areVirtualStatementsLoaded(session.virtualGraphServerSupport, subject)) {\r
+ SessionImplSocket.loadVirtualStatements(session.virtualGraphServerSupport, graph, subject, new Callback<ReadGraphImpl>() {\r
+\r
+ @Override\r
+ public void run(ReadGraphImpl graph) {\r
+ getValue4(graph, containerCluster, subject, procedure);\r
+ }\r
+ \r
+ });\r
+ return;\r
+ }\r
+ \r
+ for(TransientGraph g : session.virtualGraphServerSupport.providers) {\r
+ Object value = g.getValue(subject);\r
+ if(value != null) {\r
+ if(result != null) {\r
+ procedure.exception(graph, new DatabaseException("Multiple values"));\r
+// graph.dec();\r
+ return;\r
+ } else {\r
+ result = value;\r
+ }\r
+ }\r
+ }\r
+\r
+ procedure.execute(graph, (T)"name");\r
+// graph.dec();\r
+ return;\r
+\r
+ }\r
+ \r
+ ClusterImpl cluster = containerCluster;\r
+ if(!containerCluster.contains(subject)) {\r
+ cluster = session.clusterTable.getClusterByResourceKey(subject);\r
+ if(!cluster.isLoaded()) {\r
+ cluster.load(session.clusterTranslator, new Runnable() {\r
+\r
+ @Override\r
+ public void run() {\r
+ getValue4(graph, containerCluster, subject, procedure);\r
+ }\r
+\r
+ });\r
+ return;\r
+ }\r
+ }\r
+ \r
+ if(cluster.hasVirtual() && session.virtualGraphServerSupport.virtuals.contains(subject)) {\r
+\r
+ if(!SessionImplSocket.areVirtualStatementsLoaded(session.virtualGraphServerSupport, subject)) {\r
+ SessionImplSocket.loadVirtualStatements(session.virtualGraphServerSupport, graph, subject, new Callback<ReadGraphImpl>() {\r
+\r
+ @Override\r
+ public void run(ReadGraphImpl graph) {\r
+ getValue4(graph, containerCluster, subject, procedure);\r
+ }\r
+ \r
+ });\r
+ return;\r
+ }\r
+ \r
+ for(TransientGraph g : session.virtualGraphServerSupport.providers) {\r
+ Object value = g.getValue(subject);\r
+ if(value != null) {\r
+ if(result != null) {\r
+ procedure.exception(graph, new DatabaseException("Multiple values"));\r
+// graph.dec();\r
+ return;\r
+ } else {\r
+ result = value;\r
+ }\r
+ }\r
+ }\r
+ \r
+ if(result != null) {\r
+ \r
+ procedure.execute(graph, (T)result);\r
+// graph.state.barrier.dec();\r
+ \r
+ } else {\r
+ \r
+ if(ClusterTypeEnum.SMALL == cluster.getType())\r
+ getDirectValue4(graph, (ClusterSmall)cluster, subject, procedure);\r
+ else \r
+ getDirectValue4(graph, (ClusterBig)cluster, subject, procedure);\r
+ }\r
+\r
+ } else {\r
+\r
+ if(ClusterTypeEnum.SMALL == cluster.getType())\r
+ getDirectValue4(graph, (ClusterSmall)cluster, subject, procedure);\r
+ else \r
+ getDirectValue4(graph, (ClusterBig)cluster, subject, procedure);\r
+\r
+ }\r
+ \r
+ }\r
+ \r
+ private <C, T> void getValue4(final ReadGraphImpl graph, final ClusterImpl containerCluster, final int subject, final C context, final ForPossibleRelatedValueContextProcedure<C, T> procedure) {\r
+ \r
+ Object result = null;\r
+ \r
+ if(subject < 0) {\r
+\r
+ if(!SessionImplSocket.areVirtualStatementsLoaded(session.virtualGraphServerSupport, subject)) {\r
+ SessionImplSocket.loadVirtualStatements(session.virtualGraphServerSupport, graph, subject, new Callback<ReadGraphImpl>() {\r
+\r
+ @Override\r
+ public void run(ReadGraphImpl graph) {\r
+ getValue4(graph, containerCluster, subject, context, procedure);\r
+ }\r
+ \r
+ });\r
+ return;\r
+ }\r
+ \r
+ for(TransientGraph g : session.virtualGraphServerSupport.providers) {\r
+ Object value = g.getValue(subject);\r
+ if(value != null) {\r
+ if(result != null) {\r
+ procedure.exception(graph, new DatabaseException("Multiple values"));\r
+// graph.dec();\r
+ return;\r
+ } else {\r
+ result = value;\r
+ }\r
+ }\r
+ }\r
+\r
+ procedure.execute(graph, context, (T)"name");\r
+// graph.dec();\r
+ return;\r
+\r
+ }\r
+ \r
+ ClusterImpl cluster = containerCluster;\r
+ if(!containerCluster.contains(subject)) {\r
+ cluster = session.clusterTable.getClusterByResourceKey(subject);\r
+ if(!cluster.isLoaded()) {\r
+ cluster.load(session.clusterTranslator, new Runnable() {\r
+\r
+ @Override\r
+ public void run() {\r
+ getValue4(graph, containerCluster, subject, context, procedure);\r
+ }\r
+\r
+ });\r
+ return;\r
+ }\r
+ }\r
+ \r
+ if(cluster.hasVirtual() && session.virtualGraphServerSupport.virtuals.contains(subject)) {\r
+\r
+ if(!SessionImplSocket.areVirtualStatementsLoaded(session.virtualGraphServerSupport, subject)) {\r
+ SessionImplSocket.loadVirtualStatements(session.virtualGraphServerSupport, graph, subject, new Callback<ReadGraphImpl>() {\r
+\r
+ @Override\r
+ public void run(ReadGraphImpl graph) {\r
+ getValue4(graph, containerCluster, subject, context, procedure);\r
+ }\r
+ \r
+ });\r
+ return;\r
+ }\r
+ \r
+ for(TransientGraph g : session.virtualGraphServerSupport.providers) {\r
+ Object value = g.getValue(subject);\r
+ if(value != null) {\r
+ if(result != null) {\r
+ procedure.exception(graph, new DatabaseException("Multiple values"));\r
+// graph.dec();\r
+ return;\r
+ } else {\r
+ result = value;\r
+ }\r
+ }\r
+ }\r
+ \r
+ if(result != null) {\r
+ \r
+ procedure.execute(graph, context, (T)result);\r
+// graph.state.barrier.dec();\r
+ \r
+ } else {\r
+ \r
+ if(ClusterTypeEnum.SMALL == cluster.getType())\r
+ getDirectValue4(graph, (ClusterSmall)cluster, subject, context, procedure);\r
+ else \r
+ getDirectValue4(graph, (ClusterBig)cluster, subject, context, procedure);\r
+ }\r
+\r
+ } else {\r
+\r
+ if(ClusterTypeEnum.SMALL == cluster.getType())\r
+ getDirectValue4(graph, (ClusterSmall)cluster, subject, context, procedure);\r
+ else \r
+ getDirectValue4(graph, (ClusterBig)cluster, subject, context, procedure);\r
+\r
+ }\r
+ \r
+ }\r
+\r
+ private <T> void getRelatedDirectValue4(final ReadGraphImpl graph, final ClusterImpl cluster, final int subject, final int result, final ForPossibleRelatedValueProcedure<T> procedure) {\r
+\r
+ try {\r
+\r
+ int so = cluster.getSingleObject(subject, procedure, session.clusterTranslator);\r
+ if(so == 0) {\r
+ if(result == 0) {\r
+ procedure.exception(graph, new DatabaseException("No objects " + subject + " " + procedure.predicateKey));\r
+// graph.dec();\r
+ } else {\r
+ getValue4(graph, cluster, result, procedure);\r
+ }\r
+ } else {\r
+ if(result == 0) {\r
+ getValue4(graph, cluster, so, procedure);\r
+ } else {\r
+ procedure.exception(graph, new DatabaseException("Multiple objects"));\r
+// graph.dec();\r
+ }\r
+ }\r
+\r
+ } catch (DatabaseException e) {\r
+ e.printStackTrace();\r
+ }\r
+ \r
+ }\r
+\r
+ private <C, T> void getRelatedDirectValue4(final ReadGraphImpl graph, final ClusterImpl cluster, final int subject, final int result, final C context, final ForPossibleRelatedValueContextProcedure<C, T> procedure) {\r
+\r
+ try {\r
+\r
+ int so = cluster.getSingleObject(subject, procedure, session.clusterTranslator);\r
+ if(so == 0) {\r
+ if(result == 0) {\r
+ procedure.exception(graph, new DatabaseException("No objects " + subject + " " + procedure.predicateKey));\r
+// graph.dec();\r
+ } else {\r
+ getValue4(graph, cluster, result, context, procedure);\r
+ }\r
+ } else {\r
+ if(result == 0) {\r
+ getValue4(graph, cluster, so, context, procedure);\r
+ } else {\r
+ procedure.exception(graph, new DatabaseException("Multiple objects"));\r
+// graph.dec();\r
+ }\r
+ }\r
+\r
+ } catch (DatabaseException e) {\r
+ e.printStackTrace();\r
+ }\r
+ \r
+ }\r
+ \r
+ public <T> void getRelatedValue4(final ReadGraphImpl graph, final int subject, final ForPossibleRelatedValueProcedure<T> procedure) {\r
+ \r
+ int result = 0;\r
+ \r
+ final int predicate = procedure.predicateKey;\r
+\r
+ if(subject < 0) {\r
+\r
+ if(!SessionImplSocket.areVirtualStatementsLoaded(session.virtualGraphServerSupport, subject, predicate)) {\r
+ SessionImplSocket.loadVirtualStatements(session.virtualGraphServerSupport, graph, subject, predicate, new Callback<ReadGraphImpl>() {\r
+\r
+ @Override\r
+ public void run(ReadGraphImpl graph) {\r
+ getRelatedValue4(graph, subject, procedure);\r
+ }\r
+ \r
+ });\r
+ return;\r
+ }\r
+ \r
+ for(TransientGraph g : session.virtualGraphServerSupport.providers) {\r
+ for (int id : g.getObjects(subject, predicate)) {\r
+ if(result != 0) {\r
+ procedure.exception(graph, new DatabaseException("Multiple objects"));\r
+// graph.dec();\r
+ return;\r
+ } else {\r
+ result = id;\r
+ }\r
+ }\r
+ }\r
+ \r
+ if(result == 0) {\r
+ \r
+ procedure.exception(graph, new DatabaseException("No objects for " + subject ));\r
+// graph.dec();\r
+ return;\r
+ \r
+ } else {\r
+ \r
+ getValue4(graph, null, result, procedure);\r
+ return;\r
+ \r
+ }\r
+ \r
+ } \r
+ \r
+ final org.simantics.db.procore.cluster.ClusterImpl cluster = session.clusterTable.getClusterByResourceKey(subject);\r
+ if(!cluster.isLoaded()) {\r
+ cluster.load(session.clusterTranslator, new Runnable() {\r
+\r
+ @Override\r
+ public void run() {\r
+ getRelatedValue4(graph, subject, procedure);\r
+ }\r
+ \r
+ });\r
+ return;\r
+ }\r
+ \r
+ if(cluster.hasVirtual() && session.virtualGraphServerSupport.virtuals.contains(subject)) {\r
+ \r
+ if(!SessionImplSocket.areVirtualStatementsLoaded(session.virtualGraphServerSupport, subject, predicate)) {\r
+ SessionImplSocket.loadVirtualStatements(session.virtualGraphServerSupport, graph, subject, predicate, new Callback<ReadGraphImpl>() {\r
+\r
+ @Override\r
+ public void run(ReadGraphImpl graph) {\r
+ getRelatedValue4(graph, subject, procedure);\r
+ }\r
+ \r
+ });\r
+ return;\r
+ }\r
+ \r
+ for(TransientGraph g : session.virtualGraphServerSupport.providers) {\r
+ for (int id : g.getObjects(subject, predicate)) {\r
+ if(result != 0) {\r
+ procedure.exception(graph, new DatabaseException("Multiple objects"));\r
+// graph.dec();\r
+ return;\r
+ } else {\r
+ result = id;\r
+ }\r
+ }\r
+ }\r
+ \r
+ getRelatedDirectValue4(graph, cluster, subject, result, procedure);\r
+ \r
+ } else {\r
+ \r
+ getRelatedDirectValue4(graph, cluster, subject, 0, procedure);\r
+ \r
+ }\r
+ \r
+ }\r
+ \r
+ private <C, T> void getDirectValue4(final ReadGraphImpl graph, final ClusterSmall cluster, final int subject, final C context, final ForPossibleRelatedValueContextProcedure<C, T> procedure) {\r
+ \r
+ try {\r
+ byte[] bytes = cluster.getValue(subject, session.clusterTranslator);\r
+ T value = (T)utf(bytes);\r
+ procedure.execute(graph, context, value);\r
+ } catch (DatabaseException e) {\r
+ procedure.execute(graph, context, null);\r
+ }\r
+\r
+// graph.dec();\r
+ \r
+ }\r
+\r
+ private <T> void getDirectValue4(final ReadGraphImpl graph, final ClusterBig cluster, final int subject, final ForPossibleRelatedValueProcedure<T> procedure) {\r
+ \r
+ try {\r
+ byte[] bytes = cluster.getValue(subject, session.clusterTranslator);\r
+ T value = (T)utf(bytes);\r
+ procedure.execute(graph, value);\r
+ } catch (DatabaseException e) {\r
+ procedure.execute(graph, null);\r
+ }\r
+\r
+// graph.dec();\r
+ \r
+ }\r
+\r
+ private <C, T> void getDirectValue4(final ReadGraphImpl graph, final ClusterBig cluster, final int subject, final C context, final ForPossibleRelatedValueContextProcedure<C, T> procedure) {\r
+ \r
+ try {\r
+ byte[] bytes = cluster.getValue(subject, session.clusterTranslator);\r
+ if(bytes == null) {\r
+ procedure.execute(graph, context, null);\r
+ } else {\r
+ T value = (T)utf(bytes);\r
+ procedure.execute(graph, context, value);\r
+ }\r
+ } catch (DatabaseException e) {\r
+ procedure.execute(graph, context, null);\r
+ }\r
+\r
+// graph.dec();\r
+ \r
+ }\r
+ \r
+ private final char[] chars = new char[1024];\r
+ \r
+ private <T> void getDirectValue4(final ReadGraphImpl graph, final ClusterSmall cluster, final int subject, final ForPossibleRelatedValueProcedure<T> procedure) {\r
+\r
+ ResourceTableSmall rt = cluster.resourceTable;\r
+ ValueTableSmall vt = cluster.valueTable;\r
+\r
+ byte[] bs = vt.table;\r
+ long[] ls = rt.table;\r
+\r
+ int index = ((subject&0xFFFF) << 1) - 1 + rt.offset;\r
+\r
+ int valueIndex = (int)(ls[index] >>> 24) & 0x3FFFFF + vt.offset;\r
+\r
+ int size = (int)bs[valueIndex++]-1;\r
+ valueIndex++;\r
+ for(int i=0;i<size;i++) {\r
+ chars[i] = (char)bs[valueIndex++];\r
+ }\r
+\r
+ T value = (T)new String(chars, 0, size);\r
+\r
+ procedure.execute(graph, value);\r
+// graph.dec();\r
+ \r
+ }\r
+\r
+ final private String utf(byte[] bytes) {\r
+ \r
+ if(bytes == null) return null;\r
+ \r
+ int index = 0;\r
+ int length = bytes[index++]&0xff; \r
+ if(length >= 0x80) {\r
+ if(length >= 0xc0) {\r
+ if(length >= 0xe0) {\r
+ if(length >= 0xf0) {\r
+ length &= 0x0f;\r
+ length += ((bytes[index++]&0xff)<<3);\r
+ length += ((bytes[index++]&0xff)<<11);\r
+ length += ((bytes[index++]&0xff)<<19);\r
+ length += 0x10204080;\r
+ }\r
+ else {\r
+ length &= 0x1f;\r
+ length += ((bytes[index++]&0xff)<<4);\r
+ length += ((bytes[index++]&0xff)<<12);\r
+ length += ((bytes[index++]&0xff)<<20);\r
+ length += 0x204080;\r
+ }\r
+ }\r
+ else {\r
+ length &= 0x3f;\r
+ length += ((bytes[index++]&0xff)<<5);\r
+ length += ((bytes[index++]&0xff)<<13);\r
+ length += 0x4080;\r
+ }\r
+ }\r
+ else {\r
+ length &= 0x7f;\r
+ length += ((bytes[index++]&0xff)<<6);\r
+ length += 0x80;\r
+ }\r
+ }\r
+ \r
+ int i = 0;\r
+ int target = length+index;\r
+ while(index < target) {\r
+ int c = bytes[index++]&0xff;\r
+ if(c <= 0x7F) {\r
+ chars[i++] = (char)(c&0x7F);\r
+ } else if (c > 0x07FF) {\r
+ int c2 = bytes[index++]&0xff;\r
+ int c3 = bytes[index++]&0xff;\r
+ chars[i++] = (char)(((c&0xf)<<12) + ((c2&0x3f)<<6) + (c3&0x3f)); \r
+ } else {\r
+ int c2 = bytes[index++]&0xff;\r
+ chars[i++] = (char)(((c&0x1f)<<6) + (c2&0x3f)); \r
+ }\r
+ \r
+ \r
+// if (!((c >= 0x0001) && (c <= 0x007F))) {\r
+// } else {\r
+// }\r
+// \r
+// if ((c >= 0x0001) && (c <= 0x007F)) {\r
+// bytearr[byteIndex++] = (byte)( c );\r
+// } else if (c > 0x07FF) {\r
+// bytearr[byteIndex++] = (byte)(0xE0 | ((c >> 12) & 0x0F));\r
+// bytearr[byteIndex++] = (byte)(0x80 | ((c >> 6) & 0x3F));\r
+// bytearr[byteIndex++] = (byte)(0x80 | ((c >> 0) & 0x3F));\r
+// } else {\r
+// bytearr[byteIndex++] = (byte)(0xC0 | ((c >> 6) & 0x1F));\r
+// bytearr[byteIndex++] = (byte)(0x80 | ((c >> 0) & 0x3F));\r
+// }\r
+// }\r
+ \r
+ \r
+ }\r
+ return new String(chars, 0, i);\r
+ }\r
+ \r
+}\r