]> gerrit.simantics Code Review - simantics/platform.git/blob - bundles/org.simantics.db.impl/src/org/simantics/db/impl/graph/ReadGraphImpl.java
e3e7d50ecbc04998d62a650a9695ce939b6667ac
[simantics/platform.git] / bundles / org.simantics.db.impl / src / org / simantics / db / impl / graph / ReadGraphImpl.java
1 /*******************************************************************************
2  * Copyright (c) 2007, 2010 Association for Decentralized Information Management
3  * in Industry THTH ry.
4  * All rights reserved. This program and the accompanying materials
5  * are made available under the terms of the Eclipse Public License v1.0
6  * which accompanies this distribution, and is available at
7  * http://www.eclipse.org/legal/epl-v10.html
8  *
9  * Contributors:
10  *     VTT Technical Research Centre of Finland - initial API and implementation
11  *******************************************************************************/
12 package org.simantics.db.impl.graph;
13
14 import java.io.BufferedOutputStream;
15 import java.io.File;
16 import java.io.FileOutputStream;
17 import java.io.IOException;
18 import java.io.PrintStream;
19 import java.lang.reflect.Array;
20 import java.lang.reflect.InvocationTargetException;
21 import java.nio.BufferUnderflowException;
22 import java.util.ArrayList;
23 import java.util.Collection;
24 import java.util.Collections;
25 import java.util.IdentityHashMap;
26 import java.util.Iterator;
27 import java.util.List;
28 import java.util.ListIterator;
29 import java.util.Set;
30 import java.util.function.Consumer;
31
32 import org.eclipse.core.runtime.Platform;
33 import org.simantics.databoard.Accessors;
34 import org.simantics.databoard.Bindings;
35 import org.simantics.databoard.accessor.Accessor;
36 import org.simantics.databoard.accessor.error.AccessorConstructionException;
37 import org.simantics.databoard.adapter.AdaptException;
38 import org.simantics.databoard.binding.Binding;
39 import org.simantics.databoard.binding.error.RuntimeBindingConstructionException;
40 import org.simantics.databoard.binding.impl.ObjectVariantBinding;
41 import org.simantics.databoard.binding.mutable.Variant;
42 import org.simantics.databoard.serialization.Serializer;
43 import org.simantics.databoard.type.Datatype;
44 import org.simantics.databoard.util.binary.BinaryFile;
45 import org.simantics.databoard.util.binary.RandomAccessBinary;
46 import org.simantics.db.AsyncReadGraph;
47 import org.simantics.db.DevelopmentKeys;
48 import org.simantics.db.ExternalValue;
49 import org.simantics.db.ExternalValueSupport;
50 import org.simantics.db.ReadGraph;
51 import org.simantics.db.RelationContext;
52 import org.simantics.db.Resource;
53 import org.simantics.db.Session;
54 import org.simantics.db.Statement;
55 import org.simantics.db.adaption.AdaptionService;
56 import org.simantics.db.common.primitiverequest.Adapter;
57 import org.simantics.db.common.primitiverequest.Builtin;
58 import org.simantics.db.common.primitiverequest.DatatypeBinding;
59 import org.simantics.db.common.primitiverequest.ForEachAssertedObject;
60 import org.simantics.db.common.primitiverequest.ForEachAssertedStatement;
61 import org.simantics.db.common.primitiverequest.HasStatement;
62 import org.simantics.db.common.primitiverequest.HasStatementSubject;
63 import org.simantics.db.common.primitiverequest.HasStatementSubjectObject;
64 import org.simantics.db.common.primitiverequest.HasValue;
65 import org.simantics.db.common.primitiverequest.Inverse;
66 import org.simantics.db.common.primitiverequest.IsInheritedFrom;
67 import org.simantics.db.common.primitiverequest.IsInstanceOf;
68 import org.simantics.db.common.primitiverequest.IsSubrelationOf;
69 import org.simantics.db.common.primitiverequest.OrderedSet;
70 import org.simantics.db.common.primitiverequest.PossibleAdapter;
71 import org.simantics.db.common.primitiverequest.PossibleInverse;
72 import org.simantics.db.common.primitiverequest.PossibleObject;
73 import org.simantics.db.common.primitiverequest.PossibleRelatedValue;
74 import org.simantics.db.common.primitiverequest.PossibleRelatedValueImplied;
75 import org.simantics.db.common.primitiverequest.PossibleStatement;
76 import org.simantics.db.common.primitiverequest.PossibleType;
77 import org.simantics.db.common.primitiverequest.PossibleUniqueAdapter;
78 import org.simantics.db.common.primitiverequest.PossibleValue;
79 import org.simantics.db.common.primitiverequest.PossibleValueImplied;
80 import org.simantics.db.common.primitiverequest.RelatedValue;
81 import org.simantics.db.common.primitiverequest.RelatedValueImplied;
82 import org.simantics.db.common.primitiverequest.SingleObject;
83 import org.simantics.db.common.primitiverequest.SingleStatement;
84 import org.simantics.db.common.primitiverequest.SingleType;
85 import org.simantics.db.common.primitiverequest.SingleTypeAny;
86 import org.simantics.db.common.primitiverequest.Types;
87 import org.simantics.db.common.primitiverequest.UniqueAdapter;
88 import org.simantics.db.common.primitiverequest.Value;
89 import org.simantics.db.common.primitiverequest.ValueImplied;
90 import org.simantics.db.common.primitiverequest.VariantValueImplied;
91 import org.simantics.db.common.procedure.adapter.AsyncMultiProcedureAdapter;
92 import org.simantics.db.common.procedure.adapter.ProcedureAdapter;
93 import org.simantics.db.common.procedure.adapter.TransientCacheAsyncListener;
94 import org.simantics.db.common.procedure.adapter.TransientCacheListener;
95 import org.simantics.db.common.procedure.single.SyncReadProcedure;
96 import org.simantics.db.common.procedure.single.wrapper.DeepSingleOrErrorProcedure;
97 import org.simantics.db.common.procedure.single.wrapper.DeepSingleOrNullProcedure;
98 import org.simantics.db.common.procedure.single.wrapper.ExceptionToNullProcedure;
99 import org.simantics.db.common.procedure.single.wrapper.NullSingleOrNullProcedure;
100 import org.simantics.db.common.procedure.single.wrapper.SingleFunctionalOrNullProcedure;
101 import org.simantics.db.common.procedure.single.wrapper.SingleOrErrorProcedure;
102 import org.simantics.db.common.procedure.single.wrapper.SingleOrNullProcedure;
103 import org.simantics.db.common.procedure.wrapper.NoneToAsyncListener;
104 import org.simantics.db.common.procedure.wrapper.NoneToAsyncMultiListener;
105 import org.simantics.db.common.procedure.wrapper.NoneToAsyncMultiProcedure;
106 import org.simantics.db.common.procedure.wrapper.NoneToAsyncProcedure;
107 import org.simantics.db.common.procedure.wrapper.NoneToAsyncSetProcedure;
108 import org.simantics.db.common.procedure.wrapper.SyncToAsyncListener;
109 import org.simantics.db.common.procedure.wrapper.SyncToAsyncMultiListener;
110 import org.simantics.db.common.procedure.wrapper.SyncToAsyncMultiProcedure;
111 import org.simantics.db.common.procedure.wrapper.SyncToAsyncProcedure;
112 import org.simantics.db.common.procedure.wrapper.SyncToAsyncSetProcedure;
113 import org.simantics.db.common.request.AdaptValue;
114 import org.simantics.db.common.request.ResourceRead;
115 import org.simantics.db.common.utils.Logger;
116 import org.simantics.db.common.utils.NameUtils;
117 import org.simantics.db.common.validation.L0Validations;
118 import org.simantics.db.exception.AdaptionException;
119 import org.simantics.db.exception.ArgumentException;
120 import org.simantics.db.exception.AssumptionException;
121 import org.simantics.db.exception.BindingException;
122 import org.simantics.db.exception.DatabaseException;
123 import org.simantics.db.exception.DoesNotContainValueException;
124 import org.simantics.db.exception.EmptyResourceException;
125 import org.simantics.db.exception.InternalException;
126 import org.simantics.db.exception.InvalidLiteralException;
127 import org.simantics.db.exception.ManyObjectsForFunctionalRelationException;
128 import org.simantics.db.exception.NoInverseException;
129 import org.simantics.db.exception.NoSingleResultException;
130 import org.simantics.db.exception.ResourceNotFoundException;
131 import org.simantics.db.exception.ServiceException;
132 import org.simantics.db.exception.ValidationException;
133 import org.simantics.db.impl.RelationContextImpl;
134 import org.simantics.db.impl.ResourceImpl;
135 import org.simantics.db.impl.internal.RandomAccessValueSupport;
136 import org.simantics.db.impl.internal.ResourceData;
137 import org.simantics.db.impl.procedure.CallWrappedSingleQueryProcedure4;
138 import org.simantics.db.impl.procedure.ResultCallWrappedQueryProcedure4;
139 import org.simantics.db.impl.procedure.ResultCallWrappedSingleQueryProcedure4;
140 import org.simantics.db.impl.query.CacheEntry;
141 import org.simantics.db.impl.query.QueryCache;
142 import org.simantics.db.impl.query.QueryProcessor;
143 import org.simantics.db.impl.query.QuerySupport;
144 import org.simantics.db.impl.query.TripleIntProcedure;
145 import org.simantics.db.impl.support.ResourceSupport;
146 import org.simantics.db.procedure.AsyncListener;
147 import org.simantics.db.procedure.AsyncMultiListener;
148 import org.simantics.db.procedure.AsyncMultiProcedure;
149 import org.simantics.db.procedure.AsyncProcedure;
150 import org.simantics.db.procedure.AsyncSetListener;
151 import org.simantics.db.procedure.Listener;
152 import org.simantics.db.procedure.ListenerBase;
153 import org.simantics.db.procedure.MultiListener;
154 import org.simantics.db.procedure.MultiProcedure;
155 import org.simantics.db.procedure.Procedure;
156 import org.simantics.db.procedure.SetListener;
157 import org.simantics.db.procedure.StatementProcedure;
158 import org.simantics.db.procedure.SyncListener;
159 import org.simantics.db.procedure.SyncMultiListener;
160 import org.simantics.db.procedure.SyncMultiProcedure;
161 import org.simantics.db.procedure.SyncProcedure;
162 import org.simantics.db.procedure.SyncSetListener;
163 import org.simantics.db.request.AsyncMultiRead;
164 import org.simantics.db.request.AsyncRead;
165 import org.simantics.db.request.DelayedWrite;
166 import org.simantics.db.request.DelayedWriteResult;
167 import org.simantics.db.request.ExternalRead;
168 import org.simantics.db.request.MultiRead;
169 import org.simantics.db.request.Read;
170 import org.simantics.db.request.ReadInterface;
171 import org.simantics.db.request.RequestFlags;
172 import org.simantics.db.request.Write;
173 import org.simantics.db.request.WriteInterface;
174 import org.simantics.db.request.WriteOnly;
175 import org.simantics.db.request.WriteOnlyResult;
176 import org.simantics.db.request.WriteResult;
177 import org.simantics.layer0.Layer0;
178 import org.simantics.scl.compiler.types.Type;
179 import org.simantics.scl.compiler.types.exceptions.SCLTypeParseException;
180 import org.simantics.scl.reflection.ReflectionUtils;
181 import org.simantics.scl.reflection.ValueNotFoundException;
182 import org.simantics.scl.runtime.function.Function3;
183 import org.simantics.utils.DataContainer;
184 import org.simantics.utils.Development;
185 import org.simantics.utils.datastructures.Pair;
186 import org.simantics.utils.datastructures.collections.CollectionUtils;
187
188 import gnu.trove.map.hash.TObjectIntHashMap;
189
190 public class ReadGraphImpl implements ReadGraph {
191
192     final static boolean EMPTY_RESOURCE_CHECK = false;
193     
194         final public CacheEntry parent;
195         final public QueryProcessor processor;
196         
197         final static Binding DATA_TYPE_BINDING_INTERNAL = Bindings.getBindingUnchecked(Datatype.class);
198         final static Serializer DATA_TYPE_SERIALIZER = Bindings.getSerializerUnchecked(DATA_TYPE_BINDING_INTERNAL);
199
200         final public static TObjectIntHashMap<String> counters = new TObjectIntHashMap<String>(); 
201         
202         public static void resetCounters() {
203                 counters.clear();
204         }
205         
206         public static String listCounters(File file) throws IOException {
207                 
208                 PrintStream b = new PrintStream(new BufferedOutputStream(new FileOutputStream(file)));
209
210                 for(Pair<String,Integer> p : CollectionUtils.valueSortedEntries(counters)) {
211                         b.print(-p.second + " " + p.first + "\n");
212                 }
213
214                 b.close();
215
216                 return "Dumped " + counters.size() + " queries.";
217                 
218         }
219         
220         /*
221          * Implementation of the interface ReadGraph
222          */
223         final public String getURI(final Resource resource)     throws AssumptionException, ValidationException, ServiceException {
224                 
225                 assert (resource != null);
226
227                 try {
228
229                         return syncRequest(new org.simantics.db.common.uri.ResourceToURI(resource));
230
231                 } catch (AssumptionException e) {
232
233                         throw new AssumptionException(e);
234
235                 } catch (ValidationException e) {
236
237                         throw new ValidationException(e);
238
239                 } catch (ServiceException e) {
240
241                         throw new ServiceException(e);
242
243                 } catch (DatabaseException e) {
244
245                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
246
247                 }
248
249         }
250         
251         final public String getPossibleURI(final Resource resource)     throws ValidationException,     ServiceException {
252
253                 assert (resource != null);
254
255                 try {
256
257                         return syncRequest(new org.simantics.db.common.uri.ResourceToPossibleURI(resource));
258
259                 } catch (ValidationException e) {
260
261                         throw new ValidationException(e);
262
263                 } catch (ServiceException e) {
264
265                         throw new ServiceException(e);
266
267                 } catch (DatabaseException e) {
268
269                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
270
271                 }
272
273         }
274
275         final public Resource getResource(final String id)
276                         throws ResourceNotFoundException, ValidationException,
277                         ServiceException {
278
279                 assert (id != null);
280
281                 try {
282
283                         return syncRequest(new org.simantics.db.common.primitiverequest.Resource(
284                                         id));
285
286                 } catch (ResourceNotFoundException e) {
287
288                         throw new ResourceNotFoundException(id, e);
289
290                 } catch (ValidationException e) {
291
292                         throw new ValidationException(e);
293
294                 } catch (ServiceException e) {
295
296                         throw new ServiceException(e);
297
298                 } catch (DatabaseException e) {
299
300                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
301
302                 }
303
304         }
305
306         final public Resource getPossibleResource(final String id)
307         throws ResourceNotFoundException, ValidationException,
308         ServiceException {
309
310                 assert (id != null);
311
312                 try {
313
314                         return syncRequest(new org.simantics.db.common.primitiverequest.Resource(
315                                         id));
316
317                 } catch (ResourceNotFoundException e) {
318                         
319                         return null;
320
321                 } catch (ValidationException e) {
322
323                         throw new ValidationException(e);
324
325                 } catch (ServiceException e) {
326
327                         throw new ServiceException(e);
328
329                 } catch (DatabaseException e) {
330
331                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
332
333                 }
334
335         }
336
337         final public Resource getRootLibrary() {
338                 return processor.getRootLibraryResource();
339         }
340         
341         final public Resource getBuiltin(final String id)
342                         throws ResourceNotFoundException, ServiceException {
343
344                 assert (id != null);
345
346                 try {
347
348                         return syncRequest(new Builtin(id));
349
350                 } catch (ResourceNotFoundException e) {
351
352                         throw new ResourceNotFoundException(id, e);
353
354                 } catch (ServiceException e) {
355
356                         throw new ServiceException(e);
357
358                 } catch (DatabaseException e) {
359
360                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
361
362                 }
363
364         }
365
366         static class StatementReadProcedure extends TIntArrayListInternal implements StatementProcedure {
367
368                 private static Throwable DONE = new Throwable();
369                 
370                 Throwable exception = null;
371                 
372                 final ResourceSupport support;
373                 
374                 public StatementReadProcedure(ResourceSupport support) {
375                         this.support = support;
376                 }
377                 
378                 @Override
379                 public synchronized void execute(AsyncReadGraph graph, int s, int p, int o) {
380                         add(s);
381                         add(p);
382                         add(o);
383                 }
384                 
385                 @Override
386                 public void finished(AsyncReadGraph graph) {
387                         exception = DONE;
388                 }
389
390                 @Override
391                 public void exception(AsyncReadGraph graph, Throwable t) {
392                         exception = t;
393                 }
394                 
395                 public void checkAndThrow() throws DatabaseException {
396                         if(exception != DONE) {
397                                 if (exception instanceof DatabaseException)
398                                         throw (DatabaseException) exception;
399                                 else
400                                         throw new DatabaseException(
401                                                         "Unexpected exception in ReadGraph.syncRequest(AsyncMultiRead)",
402                                                         exception);
403                         }
404                 }
405                 
406                 public boolean done() {
407                         return exception != null;
408                 }
409
410                 @Override
411                 public boolean contains(Object obj) {
412                     if(!(obj instanceof InternalStatement))
413                         return false;
414                     InternalStatement statement = (InternalStatement)obj;
415                     int s = statement.s;
416                     int p = statement.p;
417                     int o = statement.o;
418                     for(int i=0;i<sizeInternal();i+=3)
419                 if(s==getQuick(i) && p==getQuick(i+1) && o==getQuick(i+2))
420                     return true;
421                     return false;
422                 }
423
424                 @SuppressWarnings("unchecked")
425         @Override
426                 public <T> T[] toArray(T[] a) {
427                     int length = sizeInternal() / 3;
428                     if(length > a.length) {
429                         Class<?> arrayType = a.getClass();
430                         a = (arrayType == Object[].class) 
431                                 ? (T[]) new Object[length]
432                                 : (T[]) Array.newInstance(arrayType.getComponentType(), length);
433                     }
434                     else {
435                         for(int i=length;i<a.length;++i)
436                             a[i] = null;
437                     }
438             for(int i=0,j=0;i<sizeInternal();i+=3,++j)
439                 a[j] = (T)new InternalStatement(support, getQuick(i), getQuick(i+1), getQuick(i+2));
440             return a;
441                 }
442
443                 @Override
444                 public boolean add(Statement e) {
445                         throw new UnsupportedOperationException();
446                 }
447
448                 @Override
449                 public boolean remove(Object o) {
450                         throw new UnsupportedOperationException();
451                 }
452
453                 @Override
454                 public boolean addAll(Collection<? extends Statement> c) {
455                         throw new UnsupportedOperationException();
456                 }
457
458                 class IteratorImpl implements ListIterator<Statement> {
459             
460             int index;
461             
462             public IteratorImpl(int index) {
463                 this.index = index;
464             }
465
466             @Override
467             public boolean hasNext() {
468                 return index < sizeInternal(); 
469             }
470
471             @Override
472             public Statement next() {
473                 Statement result = new InternalStatement(support, getQuick(index), getQuick(index+1), getQuick(index+2)); 
474                 index += 3;
475                 return result;
476             }
477
478             @Override
479             public void remove() {
480                 throw new Error("Not supported");
481             }
482
483             @Override
484             public boolean hasPrevious() {
485                 return index > 0;
486             }
487
488             @Override
489             public Statement previous() {
490                 index -= 3;
491                 Statement result = new InternalStatement(support, getQuick(index), getQuick(index+1), getQuick(index+2)); 
492                 return result;
493             }
494
495             @Override
496             public int nextIndex() {
497                 return index/3;
498             }
499
500             @Override
501             public int previousIndex() {
502                 return index/3-1;
503             }
504
505             @Override
506             public void set(Statement e) {
507                 throw new UnsupportedOperationException();
508             }
509
510             @Override
511             public void add(Statement e) {
512                 throw new UnsupportedOperationException();
513             }
514             
515         };
516         
517                 @Override
518                 public Iterator<Statement> iterator() {
519                         return new IteratorImpl(0);
520                 }
521                 
522                 @Override
523                 public int size() {
524                         return sizeInternal() / 3;
525                 }
526
527                 @Override
528                 public Object[] toArray() {
529                     Object[] result = new Object[sizeInternal() / 3];
530                     for(int i=0,j=0;j<sizeInternal();i++,j+=3)
531                         result[i] = new InternalStatement(support, getQuick(j), getQuick(j+1), getQuick(j+2));
532                         return result;
533                 }
534
535         @Override
536         public boolean addAll(int index, Collection<? extends Statement> c) {
537             throw new UnsupportedOperationException();
538         }
539
540         @Override
541         public Statement get(int index) {
542             index += 3;
543             if(index < 0 || index >= sizeInternal())
544                 throw new IndexOutOfBoundsException();
545             return new InternalStatement(support, getQuick(index), getQuick(index+1), getQuick(index+2));
546         }
547
548         @Override
549         public Statement set(int index, Statement element) {
550             throw new UnsupportedOperationException();
551         }
552
553         @Override
554         public void add(int index, Statement element) {
555             throw new UnsupportedOperationException();
556         }
557
558         @Override
559         public Statement remove(int index) {
560             throw new UnsupportedOperationException();
561         }
562
563         @Override
564         public int indexOf(Object obj) {
565             if(!(obj instanceof InternalStatement))
566                 return -1;
567             InternalStatement statement = (InternalStatement)obj;
568             int s = statement.s;
569             int p = statement.p;
570             int o = statement.o;
571             for(int i=0;i<sizeInternal();i+=3)
572                 if(s==getQuick(i) && p==getQuick(i+1) && o==getQuick(i+2))
573                     return i/3;
574             return -1;
575         }
576
577         @Override
578         public int lastIndexOf(Object obj) {
579             if(!(obj instanceof InternalStatement))
580                 return -1;
581             InternalStatement statement = (InternalStatement)obj;
582             int s = statement.s;
583             int p = statement.p;
584             int o = statement.o;
585             for(int i=sizeInternal()-3;i>=0;i-=3)
586                 if(s==getQuick(i) && p==getQuick(i+1) && o==getQuick(i+2))
587                     return i/3;
588             return -1;
589         }
590
591         @Override
592         public ListIterator<Statement> listIterator() {
593             return new IteratorImpl(0);
594         }
595
596         @Override
597         public ListIterator<Statement> listIterator(int index) {
598             return new IteratorImpl(index*3);
599         }
600
601         @Override
602         public List<Statement> subList(int fromIndex, int toIndex) {
603             if(fromIndex < 0 || toIndex*3 >= sizeInternal() || fromIndex > toIndex)
604                 throw new IndexOutOfBoundsException();
605             return new RandomAccessSubList<Statement>(this, fromIndex, toIndex-fromIndex);
606         }
607         }
608         
609         @Override
610         final public Collection<Statement> getStatements(final Resource subject,
611                         final Resource relation)
612                         throws ManyObjectsForFunctionalRelationException, ServiceException {
613
614                 assert (subject != null);
615                 assert (relation != null);
616
617                 try {
618
619                         StatementReadProcedure procedure = new StatementReadProcedure(getResourceSupport());
620                         processor.forEachStatement(this, subject, relation, procedure);
621                         procedure.checkAndThrow();
622                         return procedure;
623                         
624                 } catch (DatabaseException e) {
625
626                         System.err.println(INTERNAL_ERROR_STRING + " getStatements " + subject + " " + relation);
627
628                         StatementReadProcedure procedure = new StatementReadProcedure(getResourceSupport());
629                         processor.forEachStatement(this, subject, relation, procedure);
630                         
631                         return Collections.emptyList();
632                 
633 //                      throw new ServiceException(INTERNAL_ERROR_STRING + " getStatements " + subject + " " + relation, e);
634
635                 }
636
637         }
638
639         @Override
640         final public Collection<Statement> getAssertedStatements(final Resource subject, final Resource relation)
641                         throws ManyObjectsForFunctionalRelationException, ServiceException {
642
643                 assert (subject != null);
644                 assert (relation != null);
645
646                 try {
647
648                         return syncRequest(new ForEachAssertedStatement(subject, relation));
649
650                 } catch (ManyObjectsForFunctionalRelationException e) {
651
652                         throw new ManyObjectsForFunctionalRelationException(e);
653
654                 } catch (ServiceException e) {
655
656                         throw new ServiceException(e);
657
658                 } catch (DatabaseException e) {
659
660                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
661
662                 }
663
664         }
665
666         @Override
667         final public Collection<Resource> getPredicates(final Resource subject) throws ServiceException {
668
669                 assert (subject != null);
670
671                 try {
672
673                         return processor.getPredicates(this, subject);
674
675 //                      AsyncMultiReadProcedure<Resource> procedure = new AsyncMultiReadProcedure<Resource>();
676 //                      processor.forEachPredicate(this, subject, procedure);
677 //                      procedure.checkAndThrow();
678 //                      return procedure;
679
680                 } catch (ServiceException e) {
681
682                         throw new ServiceException(e);
683
684                 } catch (DatabaseException e) {
685
686                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
687
688                 }  catch (Throwable e) {
689
690             throw new ServiceException(e);
691
692                 }
693
694         }
695
696         @Override
697         final public Collection<Resource> getPrincipalTypes(final Resource subject)
698                         throws ServiceException {
699
700                 assert (subject != null);
701
702                 try {
703
704                         AsyncMultiReadProcedure<Resource> procedure = new AsyncMultiReadProcedure<Resource>();
705                         processor.forEachPrincipalType(this, subject, procedure);
706                         procedure.checkAndThrow();
707                         return procedure;
708                         
709                 } catch (ServiceException e) {
710
711                         throw new ServiceException(e);
712
713                 } catch (DatabaseException e) {
714
715                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
716
717                 }
718
719         }
720
721         @Override
722         final public Set<Resource> getTypes(final Resource subject) throws ServiceException {
723
724                 assert (subject != null);
725
726                 try {
727                         
728                         return processor.getTypes(this, subject);
729                         
730                 } catch (ServiceException e) {
731
732                         throw new ServiceException(e);
733                         
734                 } catch (DatabaseException e) {
735
736                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
737
738         } catch (Throwable e) {
739
740             throw new ServiceException(e);
741
742                 }
743
744         }
745
746         @Override
747         final public Set<Resource> getSupertypes(final Resource subject)
748                         throws ServiceException {
749
750                 assert (subject != null);
751
752                 try {
753
754                         SyncReadProcedure<Set<Resource>> procedure = new SyncReadProcedure<Set<Resource>>();
755                         processor.forSupertypes(this, subject, procedure);
756                         procedure.checkAndThrow();
757                         return procedure.result;
758
759                 } catch (ServiceException e) {
760
761                         throw new ServiceException(e);
762
763                 } catch (DatabaseException e) {
764
765                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
766
767                 }
768
769         }
770
771         @Override
772         final public Set<Resource> getSuperrelations(final Resource subject)
773                         throws ServiceException {
774
775                 assert (subject != null);
776
777                 try {
778
779                         SyncReadProcedure<Set<Resource>> procedure = new SyncReadProcedure<Set<Resource>>();
780                         processor.forSuperrelations(this, subject, procedure);
781                         procedure.checkAndThrow();
782                         return procedure.result;
783
784                 } catch (ServiceException e) {
785
786                         throw new ServiceException(e);
787
788                 } catch (DatabaseException e) {
789
790                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
791
792                 }
793
794         }
795         
796         @Override
797         public Resource getPossibleSuperrelation(Resource subject) throws ServiceException {
798                 
799                 try {
800
801                         SyncReadProcedure<Resource> procedure = new SyncReadProcedure<Resource>();
802                         processor.forPossibleSuperrelation(this, subject, procedure);
803                         procedure.checkAndThrow();
804                         return procedure.result;
805
806                 } catch (ServiceException e) {
807
808                         throw new ServiceException(e);
809
810                 } catch (DatabaseException e) {
811
812                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
813
814                 }
815
816         }
817
818         @Override
819         final public Collection<Resource> getObjects(final Resource subject, final Resource relation)
820                         throws ServiceException {
821
822                 assert (subject != null);
823                 assert (relation != null);
824
825                 if(Development.DEVELOPMENT) {
826             if(Development.isTrue(DevelopmentKeys.READGRAPH_COUNT)) {
827                 counters.adjustOrPutValue("objects $" + subject.getResourceId() + " $" + relation.getResourceId(), 1, 1);
828             }
829             //if(subject.getResourceId()==xx && relation.getResourceId()==xx) new Exception().printStackTrace();
830                 }
831                 
832                 try {
833
834                         AsyncMultiReadProcedure<Resource> procedure = new AsyncMultiReadProcedure<Resource>();
835                         processor.forEachObject(this, subject, relation, procedure);
836                         procedure.checkAndThrow();
837                         return procedure;
838                         
839                 } catch (DatabaseException e) {
840
841                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
842
843                 }
844
845         }
846
847         @Override
848         final public Collection<Resource> getAssertedObjects(
849                         final Resource subject, final Resource relation)
850                         throws ManyObjectsForFunctionalRelationException, ServiceException {
851
852         if (subject == null)
853             throw new ArgumentException("Subject must not be null.");
854         if (relation == null)
855             throw new ArgumentException("Relation must not be null. Subject=" + subject);
856
857                 try {
858
859                         return syncRequest(new ForEachAssertedObject(subject, relation));
860
861                 } catch (ManyObjectsForFunctionalRelationException e) {
862
863                         throw new ManyObjectsForFunctionalRelationException(e);
864
865                 } catch (ServiceException e) {
866
867                         throw new ServiceException(e);
868
869                 } catch (DatabaseException e) {
870
871                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
872
873                 }
874
875         }
876
877         @Override
878         final public Resource getInverse(final Resource relation) throws NoInverseException, ServiceException {
879
880                 assert (relation != null);
881
882                 try {
883
884                         return getSingleObject(relation, processor.querySupport.getResource(processor.getInverseOf()));
885
886                 } catch (NoSingleResultException e) {
887
888                         throw new NoInverseException(e);
889
890                 } catch (ServiceException e) {
891
892                         throw new ServiceException(e);
893
894                 }
895
896         }
897
898         @Override
899         final public Resource getSingleObject(final Resource subject, final Resource relation) throws NoSingleResultException, ServiceException {
900
901                 if( subject == null) throw new IllegalArgumentException("subject can not be null");
902                 if( relation == null) throw new IllegalArgumentException("relation can not be null");
903
904                 try {
905                         int single = processor.getSingleObject(this, subject, relation);
906                         if (single == 0) {
907                                 if (EMPTY_RESOURCE_CHECK) {
908                                         if (!hasStatement(subject)) {
909                                                 throw new EmptyResourceException("Resource " + debugString(subject));
910                                         }
911                                 }
912                                 throw new NoSingleResultException("No single object for subject " + debugString(subject)
913                                                 + " and relation " + debugString(relation), single);
914                         }
915                         return processor.querySupport.getResource(single);
916                 } catch (NoSingleResultException e) {
917                         throw e;
918                 } catch (DatabaseException e) {
919                         throw new ServiceException(e);
920                 } 
921         }
922
923         @Override
924         final public Statement getSingleStatement(final Resource subject, final Resource relation) throws NoSingleResultException, ManyObjectsForFunctionalRelationException, ServiceException {
925                 assert (subject != null);
926                 assert (relation != null);
927                 try {
928                         Collection<Statement> statements = getStatements(subject, relation);
929                         if (statements.size() == 1) {
930                                 return statements.iterator().next();
931                         } else {
932                                 if (EMPTY_RESOURCE_CHECK)
933                                         if (!hasStatement(subject))
934                                                 throw new EmptyResourceException("Resource " + debugString(subject));
935                                 throw new NoSingleResultException("No single statement for subject " + debugString(subject)
936                                                 + " and relation " + debugString(relation), statements.size());
937                         }
938                 } catch (ServiceException e) {
939                         throw new ServiceException(e);
940                 } 
941         }
942
943         @Override
944         final public Resource getSingleType(final Resource subject) throws NoSingleResultException, ServiceException {
945                 assert (subject != null);
946                 try {
947                         ArrayList<Resource> principalTypes = (ArrayList<Resource>)getPrincipalTypes(subject);
948                         if (principalTypes.size() == 1) {
949                             return principalTypes.get(0);
950                         } else {
951                             throw new NoSingleResultException("No single type for subject " + debugString(subject), principalTypes.size());
952                         }
953                 } catch (ServiceException e) {
954                         throw new ServiceException(e);
955                 } 
956         }
957
958         @Override
959         final public Resource getSingleType(final Resource subject,
960                         final Resource baseType) throws NoSingleResultException,
961                         ServiceException {
962
963                 assert (subject != null);
964                 assert (baseType != null);
965
966                 try {
967                         return syncRequest(new SingleType(subject, baseType));
968                 } catch (DatabaseException e) {
969                     throw new NoSingleResultException("subject=" + subject + ", baseType=" + baseType, 0, e);
970                 }
971         }
972
973         @Override
974         final public <T> T getValue(final Resource subject) throws DoesNotContainValueException, ServiceException {
975
976                 assert (subject != null);
977
978                 try {
979
980                         Layer0 L0 = processor.getL0(this);
981             int object = processor.getSingleObject(this, subject, L0.HasDataType);
982             if(object == 0) throw new DoesNotContainValueException("No data type for " + subject);
983             
984             if(processor.isImmutable(object)) {
985                 Binding binding = syncRequest(new DatatypeBinding(processor.querySupport.getResource(object)), TransientCacheListener.<Binding>instance()); 
986                         return getValue(subject, binding);
987             } else {
988                     byte[] dt = processor.getValue(this, object);
989                     if(dt == null) throw new ServiceException("No data type for " + subject);
990                     Datatype datatype = (Datatype)DATA_TYPE_SERIALIZER.deserialize(dt);
991                     Binding binding = Bindings.getBinding(datatype);
992                     return getValue(subject, binding);
993             }
994                         
995         } catch (IOException e) {
996
997             throw new ServiceException(e);
998
999                 } catch (DoesNotContainValueException e) {
1000
1001                         throw new DoesNotContainValueException(e, subject);
1002
1003                 } catch (ServiceException e) {
1004
1005                         throw new ServiceException(e);
1006
1007                 } catch (DatabaseException e) {
1008
1009                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
1010
1011         }
1012
1013         }
1014
1015     @Override
1016     final public Variant getVariantValue(final Resource subject) throws DoesNotContainValueException, ServiceException {
1017
1018         assert (subject != null);
1019
1020         try {
1021
1022             Layer0 L0 = processor.getL0(this);
1023             int object = processor.getSingleObject(this, subject, L0.HasDataType);
1024             if(object == 0) throw new DoesNotContainValueException("No data type for " + subject);
1025             
1026             if(processor.isImmutable(object)) {
1027                 Binding binding = syncRequest(new DatatypeBinding(processor.querySupport.getResource(object)), TransientCacheListener.<Binding>instance()); 
1028                 return new Variant(binding, getValue(subject, binding));
1029             } else {
1030                 byte[] dt = processor.getValue(this, object);
1031                 if(dt == null) throw new ServiceException("No data type for " + subject);
1032                 Datatype datatype = (Datatype)DATA_TYPE_SERIALIZER.deserialize(dt);
1033                 Binding binding = Bindings.getBinding(datatype);
1034                 return new Variant(binding, getValue(subject, binding));
1035             }
1036             
1037         } catch (IOException e) {
1038
1039             throw new ServiceException(e);
1040
1041         } catch (DoesNotContainValueException e) {
1042
1043             throw new DoesNotContainValueException(e, subject);
1044
1045         } catch (ServiceException e) {
1046
1047             throw new ServiceException(e);
1048
1049         } catch (DatabaseException e) {
1050
1051             throw new ServiceException(INTERNAL_ERROR_STRING, e);
1052
1053         }               
1054         }
1055
1056         static final IdentityHashMap<Binding,Serializer> serializers = new IdentityHashMap<Binding,Serializer>();
1057         
1058         static {
1059                 serializers.put(Bindings.STRING, Bindings.STRING.serializer());
1060         }
1061         
1062         final protected Serializer getSerializer(Binding binding) {
1063             return binding.serializer();
1064         }
1065         
1066         @Override
1067         final public <T> T getValue(final Resource subject, final Binding binding) throws DoesNotContainValueException, BindingException,
1068                         ServiceException {
1069
1070                 assert (subject != null);
1071
1072                 try {
1073                         
1074                         byte[] bytes = processor.getValue(this, subject);
1075                         if (bytes == null) throw new DoesNotContainValueException("No value for resource " + subject);
1076
1077                         Serializer serializer = getSerializer(binding);
1078                         return (T)serializer.deserialize(bytes);
1079
1080                 } catch (DoesNotContainValueException e) {
1081
1082                         throw new DoesNotContainValueException(e);
1083
1084                 } catch (IOException e) {
1085
1086                         throw new ServiceException(e);
1087
1088                 } catch (DatabaseException e) {
1089                     
1090             throw new ServiceException(e);
1091             
1092         } catch (BufferUnderflowException e) {
1093             // This is sometimes thrown when deserialize fails because wrong format.
1094             // For callers of this method this is just an service exception.
1095             throw new ServiceException(e);
1096         }
1097
1098         }
1099
1100         @Override
1101         final public <T> T getRelatedValue(final Resource subject, final Resource relation) throws NoSingleResultException,
1102                         DoesNotContainValueException, ServiceException {
1103
1104                 assert (subject != null);
1105                 assert (relation != null);
1106
1107                 try {
1108                         Resource object = getSingleObject(subject, relation);
1109                         return getValue(object);
1110                 } catch (NoSingleResultException e) {
1111                         throw new NoSingleResultException("No single value found for subject " + debugString(subject) + " and relation " + debugString(relation), e.getResultCount(), e);
1112                 } catch (DoesNotContainValueException e) {
1113                         try {
1114                                 Layer0 L0 = processor.getL0(this);
1115                                 Resource object = getPossibleObject(subject, relation);
1116                                 if(isInstanceOf(object, L0.Value)) {
1117                                         if(isInstanceOf(object, L0.Literal)) {
1118                                                 throw new DoesNotContainValueException(e);
1119                                         } else {
1120                                                 throw new InvalidLiteralException("The object " + object + " is not an instance of L0.Literal (use getRelatedValue2 instead)", e);
1121                                         }
1122                                 } else {
1123                                         throw new DoesNotContainValueException("The object " + object + " is not an instance of L0.Value", e);
1124                                 }
1125                         } catch (DoesNotContainValueException e2) {
1126                                 throw e2;
1127                         } catch (DatabaseException e2) {
1128                                 throw new InternalException("The client failed to analyse the cause of the following exception", e);
1129                         }
1130                 } catch (ServiceException e) {
1131                         throw new ServiceException(e);
1132                 }
1133         }
1134
1135     @Override
1136     final public Variant getRelatedVariantValue(final Resource subject, final Resource relation) throws NoSingleResultException,
1137             DoesNotContainValueException, ServiceException {
1138
1139         assert (subject != null);
1140         assert (relation != null);
1141
1142         try {
1143             Resource object = getSingleObject(subject, relation);
1144             return getVariantValue(object);
1145         } catch (NoSingleResultException e) {
1146             throw new NoSingleResultException("No single object for subject " + debugString(subject) + " and relation " + debugString(relation), e.getResultCount(), e);
1147         } catch (DoesNotContainValueException e) {
1148             try {
1149                 Layer0 L0 = processor.getL0(this);
1150                 Resource object = getPossibleObject(subject, relation);
1151                 if(isInstanceOf(object, L0.Value)) {
1152                     if(isInstanceOf(object, L0.Literal)) {
1153                         throw new DoesNotContainValueException(e);
1154                     } else {
1155                         throw new InvalidLiteralException("The object " + object + " is not an instance of L0.Literal (use getRelatedValue2 instead)", e);
1156                     }
1157                 } else {
1158                     throw new DoesNotContainValueException("The object " + object + " is not an instance of L0.Value", e);
1159                 }
1160             } catch (DoesNotContainValueException e2) {
1161                 throw e2;
1162             } catch (DatabaseException e2) {
1163                 throw new InternalException("The client failed to analyse the cause of the following exception", e);
1164             }
1165         } catch (ServiceException e) {
1166             throw new ServiceException(e);
1167         } 
1168     }
1169     
1170         @Override
1171         final public <T> T getRelatedValue(final Resource subject, final Resource relation, final Binding binding)
1172                         throws NoSingleResultException, DoesNotContainValueException, BindingException, ServiceException {
1173
1174                 assert (subject != null);
1175                 assert (relation != null);
1176
1177                 try {
1178                         Resource object = getSingleObject(subject, relation);
1179                         return getValue(object, binding);
1180                 } catch (NoSingleResultException e) {
1181                     String message = "";
1182                     try {
1183                     String subjectName = NameUtils.getSafeName(this, subject, true);
1184                     String relationName = NameUtils.getSafeName(this, relation, true);
1185                     message = "Subject: " + subjectName + ", Relation: " + relationName;
1186                     } catch (DatabaseException e2) {
1187                         
1188                     }
1189             throw new NoSingleResultException(message, e.getResultCount(), e);
1190                 } catch (DoesNotContainValueException e) {
1191                         throw new DoesNotContainValueException(e);
1192                 } catch (ServiceException e) {
1193                         throw new ServiceException(e);
1194                 }
1195         }
1196
1197         @Override
1198         final public <T> T adapt(final Resource resource, final Class<T> clazz)
1199                         throws AdaptionException, ValidationException, ServiceException {
1200
1201                 assert (resource != null);
1202                 assert (clazz != null);
1203
1204                 try {
1205
1206                         return syncRequest(new Adapter<T>(resource, clazz));
1207
1208                 } catch (AdaptionException e) {
1209
1210                         throw new AdaptionException(e);
1211
1212                 } catch (ValidationException e) {
1213
1214                         throw new ValidationException(e);
1215
1216                 } catch (ServiceException e) {
1217
1218                         throw new ServiceException(e);
1219
1220                 } catch (DatabaseException e) {
1221
1222                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
1223
1224                 }
1225
1226         }
1227
1228         @Override
1229         final public <T,C> T adaptContextual(final Resource resource, final C context, final Class<C> contextClass, final Class<T> clazz)
1230                         throws AdaptionException, ValidationException, ServiceException {
1231
1232                 assert (resource != null);
1233                 assert (context != null);
1234
1235                 class ContextualAdapter implements AsyncRead<T> {
1236
1237                         final private Resource resource;
1238                         final private C context;
1239                     final private Class<T> clazz;
1240                     
1241                     @Override
1242                     public int hashCode() {
1243                         return resource.hashCode() + 31 * (clazz.hashCode() + 41 * context.hashCode());
1244                     }
1245                     
1246                     @Override
1247                     final public int threadHash() {
1248                         return resource.getThreadHash();
1249                     }
1250                     
1251                     @Override
1252                     public boolean equals(Object object) {
1253                         if (this == object)
1254                             return true;
1255                         else if (object == null)
1256                             return false;
1257                         else if (getClass() != object.getClass())
1258                             return false;
1259                         ContextualAdapter r = (ContextualAdapter)object;
1260                         return resource.equals(r.resource) && context.equals(r.context) && clazz.equals(r.clazz);
1261                     }
1262
1263                     @Override
1264                     public int getFlags() {
1265                         return 0;
1266                     }
1267                     
1268                     public ContextualAdapter(Resource resource, C context, Class<T> clazz) {
1269                         this.resource = resource;
1270                         this.context = context;
1271                         this.clazz = clazz;
1272                     }
1273
1274                     @Override
1275                     public void perform(AsyncReadGraph graph, AsyncProcedure<T> procedure) {
1276                         
1277                                 final AdaptionService service = getSession().peekService(AdaptionService.class);
1278                                 if (service == null)
1279                                         procedure.exception(graph, new ServiceException("No AdaptionService available")); 
1280                                 else
1281                                         service.adapt(graph, resource, context, contextClass, clazz, false, procedure); 
1282                         
1283                     }
1284
1285                     @Override
1286                     public String toString() {
1287                         return "Adapter for (" + resource + "," + context + ") as " + clazz.getName();
1288                     }
1289                     
1290                 }
1291                 
1292                 try {
1293
1294                         return syncRequest(new ContextualAdapter(resource, context, clazz));
1295
1296                 } catch (AdaptionException e) {
1297
1298                         throw new AdaptionException(e);
1299
1300                 } catch (ValidationException e) {
1301
1302                         throw new ValidationException(e);
1303
1304                 } catch (ServiceException e) {
1305
1306                         throw new ServiceException(e);
1307
1308                 } catch (DatabaseException e) {
1309
1310                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
1311
1312                 }
1313
1314         }
1315         
1316         @Override
1317         final public <T> T adaptRelated(final Resource resource, final Resource relation, final Class<T> clazz)
1318                         throws AdaptionException, NoSingleResultException, ValidationException, ServiceException {
1319
1320                 assert (resource != null);
1321                 assert (clazz != null);
1322
1323                 Statement stm = getSingleStatement(resource, relation);
1324                 
1325                 return adaptContextual(stm.getObject(), new RelationContextImpl(resource, stm), RelationContext.class, clazz);
1326                 
1327         }
1328
1329         @Override
1330         final public <T> T getPossibleRelatedAdapter(final Resource resource, final Resource relation, final Class<T> clazz)
1331                         throws ValidationException, ServiceException {
1332
1333                 try {
1334                         return adaptRelated(resource, relation, clazz);
1335                 } catch (DatabaseException e) {
1336                         return null;
1337                 }
1338                 
1339         }
1340
1341         @Override
1342         final public <T,C> T getPossibleContextualAdapter(final Resource resource, final C context, final Class<C> contextClass, final Class<T> clazz)
1343                         throws ValidationException, ServiceException {
1344
1345                 assert (resource != null);
1346                 assert (context != null);
1347
1348                 class PossibleContextualAdapter implements AsyncRead<T> {
1349
1350                         final private Resource resource;
1351                         final private C context;
1352                     final private Class<T> clazz;
1353                     
1354                     @Override
1355                     public int hashCode() {
1356                         return resource.hashCode() + 31 * (clazz.hashCode() + 41 * context.hashCode());
1357                     }
1358                     
1359                     @Override
1360                     final public int threadHash() {
1361                         return resource.getThreadHash();
1362                     }
1363                     
1364                     @Override
1365                     public boolean equals(Object object) {
1366                         if (this == object)
1367                             return true;
1368                         else if (object == null)
1369                             return false;
1370                         else if (getClass() != object.getClass())
1371                             return false;
1372                         PossibleContextualAdapter r = (PossibleContextualAdapter)object;
1373                         return resource.equals(r.resource) && context.equals(r.context) && clazz.equals(r.clazz);
1374                     }
1375
1376                     @Override
1377                     public int getFlags() {
1378                         return 0;
1379                     }
1380                     
1381                     public PossibleContextualAdapter(Resource resource, C context, Class<T> clazz) {
1382                         this.resource = resource;
1383                         this.context = context;
1384                         this.clazz = clazz;
1385                     }
1386
1387                     @Override
1388                     public void perform(AsyncReadGraph graph, AsyncProcedure<T> procedure) {
1389                         
1390                                 final AdaptionService service = getSession().peekService(AdaptionService.class);
1391                                 if (service == null)
1392                                         procedure.exception(graph, new ServiceException("No AdaptionService available")); 
1393                                 else
1394                                         service.adapt(graph, resource, context, contextClass, clazz, true, procedure); 
1395                         
1396                     }
1397
1398                     @Override
1399                     public String toString() {
1400                         return "Possible adapter for (" + resource + "," + context + ") as " + clazz.getName();
1401                     }
1402                     
1403                 }
1404                 
1405                 try {
1406
1407                         return syncRequest(new PossibleContextualAdapter(resource, context, clazz));
1408
1409                 } catch (ValidationException e) {
1410
1411                         throw new ValidationException(e);
1412
1413                 } catch (ServiceException e) {
1414
1415                         throw new ServiceException(e);
1416
1417                 } catch (DatabaseException e) {
1418
1419                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
1420
1421                 }
1422                 
1423         }
1424
1425         @Override
1426         final public <T> T adaptUnique(final Resource resource, final Class<T> clazz)
1427                         throws AdaptionException, ValidationException, ServiceException {
1428
1429                 assert (resource != null);
1430                 assert (clazz != null);
1431
1432                 try {
1433
1434                         return syncRequest(new UniqueAdapter<T>(resource, clazz));
1435
1436                 } catch (AdaptionException e) {
1437
1438                         throw new AdaptionException(e);
1439
1440                 } catch (ValidationException e) {
1441
1442                         throw new ValidationException(e);
1443
1444                 } catch (ServiceException e) {
1445
1446                         throw new ServiceException(e);
1447
1448                 } catch (DatabaseException e) {
1449
1450                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
1451
1452                 }
1453
1454         }
1455
1456         @Override
1457         final public Resource getPossibleInverse(final Resource relation)
1458                         throws ServiceException {
1459
1460                 assert (relation != null);
1461
1462                 try {
1463
1464                         return getPossibleObject(relation, processor.querySupport.getResource(processor.getInverseOf()));
1465
1466                 } catch (ServiceException e) {
1467
1468                         throw new ServiceException(e);
1469
1470                 } catch (DatabaseException e) {
1471
1472                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
1473
1474                 }
1475
1476         }
1477
1478         @Override
1479         public Resource getPossibleObject(final Resource subject, final Resource relation)
1480                         throws ManyObjectsForFunctionalRelationException, ServiceException {
1481
1482                 assert (subject != null);
1483                 assert (relation != null);
1484
1485                 try {
1486
1487                     int result = processor.getSingleObject(this, subject, relation);
1488                     if(result == 0) return null;
1489                     
1490                     return processor.querySupport.getResource(result);
1491
1492              } catch (ManyObjectsForFunctionalRelationException e) {
1493
1494                  throw new ManyObjectsForFunctionalRelationException("subject=" + subject + ", relation=" + relation, e);
1495                  
1496                 } catch (DatabaseException e) {
1497
1498                         throw new ServiceException(e);
1499
1500                 }
1501                 
1502         }
1503
1504         @Override
1505         final public Statement getPossibleStatement(final Resource subject, final Resource relation)
1506                         throws ManyObjectsForFunctionalRelationException, ServiceException {
1507
1508                 assert (subject != null);
1509                 assert (relation != null);
1510
1511                 try {
1512
1513                         Collection<Statement> statements = getStatements(subject, relation);
1514                         if(statements.size() == 1) return statements.iterator().next();
1515                         else return null;
1516
1517                 } catch (ManyObjectsForFunctionalRelationException e) {
1518
1519                         throw new ManyObjectsForFunctionalRelationException("Many objects in " + subject + " for functional relation " + relation);
1520
1521                 } catch (ServiceException e) {
1522
1523                         throw new ServiceException(e);
1524
1525                 } 
1526
1527         }
1528
1529         @Override
1530         final public Resource getPossibleType(final Resource subject, final Resource baseType) throws ServiceException {
1531
1532                 assert (subject != null);
1533                 assert (baseType != null);
1534
1535                 try {
1536
1537                         AsyncReadProcedure<Resource> procedure = new AsyncReadProcedure<Resource>();
1538                         forPossibleType(subject, baseType, procedure);
1539                         procedure.checkAndThrow();
1540                         return procedure.result;                        
1541
1542                 } catch (ServiceException e) {
1543
1544                         throw new ServiceException(e);
1545
1546                 } catch (DatabaseException e) {
1547
1548                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
1549
1550                 }
1551
1552         }
1553
1554         @Override
1555         final public <T> T getPossibleValue(final Resource subject) throws ServiceException {
1556
1557                 assert (subject != null);
1558
1559                 try {
1560                     
1561                     int object = processor.getSingleObject(this, subject, processor.getL0(this).HasDataType);
1562                     if(object == 0) return null;
1563                     
1564             if(processor.isImmutable(object)) {
1565                 Binding binding = syncRequest(new DatatypeBinding(processor.querySupport.getResource(object)), TransientCacheListener.<Binding>instance()); 
1566                         return getPossibleValue(subject, binding);
1567             } else {
1568                     byte[] dt = processor.getValue(this, object);
1569                     if(dt == null) return null;
1570                     Datatype datatype = (Datatype)DATA_TYPE_SERIALIZER.deserialize(dt);
1571                     Binding binding = Bindings.getBinding(datatype);
1572                     return getPossibleValue(subject, binding);
1573             }
1574                     
1575         } catch (IOException e) {
1576             
1577             throw new ServiceException(e);
1578             
1579                 } catch (ServiceException e) {
1580
1581                         throw new ServiceException(e);
1582
1583                 } catch (DatabaseException e) {
1584
1585                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
1586
1587         }
1588
1589         }
1590
1591         @Override
1592         final public <T> T getPossibleValue(final Resource subject, final Binding binding) throws BindingException, ServiceException {
1593
1594                 assert (subject != null);
1595                 assert (binding != null);
1596
1597                 try {
1598
1599             byte[] dt = processor.getValue(this, subject);
1600             if(dt == null) return null;
1601                         Serializer serializer = getSerializer(binding);
1602             return (T)serializer.deserialize(dt);
1603
1604         } catch (IOException e) {
1605
1606             throw new ServiceException(e);
1607             
1608                 } catch (BindingException e) {
1609
1610                         throw new BindingException(e);
1611
1612                 } catch (ServiceException e) {
1613
1614                         throw new ServiceException(e);
1615
1616                 } catch (DatabaseException e) {
1617                         e.printStackTrace();
1618                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
1619         }
1620
1621         }
1622
1623         @Override
1624         public <T> T getPossibleRelatedValue(final Resource subject, final Resource relation)
1625                         throws ManyObjectsForFunctionalRelationException, ServiceException {
1626
1627                 assert (subject != null);
1628                 assert (relation != null);
1629
1630                 try {
1631
1632                         Resource object = getPossibleObject(subject, relation);
1633                         if(object == null) return null;
1634                         else return getPossibleValue(object);
1635
1636                 } catch (ManyObjectsForFunctionalRelationException e) {
1637
1638                         throw new ManyObjectsForFunctionalRelationException(e);
1639
1640                 } catch (ServiceException e) {
1641
1642                         throw new ServiceException(e);
1643
1644                 } 
1645
1646         }
1647
1648         @Override
1649         public <T> T getPossibleRelatedValue(final Resource subject, final Resource relation, final Binding binding)
1650                         throws ManyObjectsForFunctionalRelationException, BindingException, ServiceException {
1651
1652                 assert (subject != null);
1653                 assert (relation != null);
1654                 assert (binding != null);
1655
1656                 try {
1657
1658                         Resource object = getPossibleObject(subject, relation);
1659                         if(object == null) return null;
1660                         else return getPossibleValue(object, binding);
1661
1662                 } catch (ManyObjectsForFunctionalRelationException e) {
1663
1664                         throw new ManyObjectsForFunctionalRelationException(e);
1665
1666                 } catch (BindingException e) {
1667
1668                         throw new BindingException(e);
1669
1670                 } catch (ServiceException e) {
1671
1672                         throw new ServiceException(e);
1673
1674                 }
1675
1676         }
1677
1678         @Override
1679         public <T> T getPossibleAdapter(Resource resource, Class<T> clazz) throws ValidationException, ServiceException {
1680
1681                 assert (resource != null);
1682                 assert (clazz != null);
1683
1684                 try {
1685
1686                         return syncRequest(new PossibleAdapter<T>(resource, clazz));
1687
1688                 } catch (ValidationException e) {
1689
1690                         throw new ValidationException(e);
1691
1692                 } catch (AdaptionException e) {
1693
1694                         return null;
1695
1696                 } catch (DatabaseException e) {
1697
1698                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
1699
1700                 }
1701         }
1702
1703         @Override
1704         public <T> T getPossibleUniqueAdapter(Resource resource, Class<T> clazz) throws ValidationException, ServiceException {
1705
1706                 assert (resource != null);
1707                 assert (clazz != null);
1708
1709                 try {
1710
1711                         return syncRequest(new PossibleUniqueAdapter<T>(resource, clazz));
1712
1713                 } catch (AdaptionException e) {
1714
1715                         return null;
1716
1717                 } catch (ValidationException e) {
1718
1719                         throw new ValidationException(e);
1720
1721                 } catch (DatabaseException e) {
1722
1723                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
1724
1725                 }
1726
1727         }
1728
1729     @Override
1730     final public boolean isInstanceOf(final Resource resource, final Resource type) throws ServiceException {
1731
1732         assert (resource != null);
1733         assert (type != null);
1734
1735         Set<Resource> resources = getTypes(resource);
1736         // This check was necessary because some of the callers of this method got stuck when the NPE was thrown from here.
1737         if (null == resources)
1738             return false;
1739         
1740         if(EMPTY_RESOURCE_CHECK) {
1741             if (resources.isEmpty()) {
1742                 if(!hasStatement(resource)) throw new EmptyResourceException("Resource " + debugString(resource));
1743             }
1744         }
1745         
1746         return resources.contains(type);
1747
1748     }
1749
1750         @Override
1751         final public boolean isInheritedFrom(final Resource resource, final Resource type) throws ServiceException {
1752
1753                 assert (resource != null);
1754                 assert (type != null);
1755
1756                 try {
1757
1758                         if(resource.equals(type)) return true;
1759                         
1760                         return getSupertypes(resource).contains(type);
1761
1762                 } catch (ServiceException e) {
1763
1764                         throw new ServiceException(e);
1765
1766                 } 
1767                 
1768         }
1769
1770         @Override
1771         final public boolean isSubrelationOf(final Resource resource, final Resource type) throws ServiceException {
1772
1773                 assert (resource != null);
1774                 assert (type != null);
1775
1776                 try {
1777
1778                         if(resource.equals(type)) return true;
1779                         
1780                         return getSuperrelations(resource).contains(type);
1781
1782                 } catch (ServiceException e) {
1783
1784                         throw new ServiceException(e);
1785
1786                 } 
1787
1788         }
1789
1790         @Override
1791         final public boolean hasStatement(final Resource subject) throws ServiceException {
1792
1793                 assert (subject != null);
1794
1795                 try {
1796
1797                         SyncReadProcedure<Boolean> procedure = new SyncReadProcedure<Boolean>();
1798                         processor.forHasStatement(this, subject, procedure);
1799                         procedure.checkAndThrow();
1800                         return procedure.result;
1801
1802                 } catch (ServiceException e) {
1803
1804                         throw new ServiceException(e);
1805
1806                 } catch (DatabaseException e) {
1807
1808                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
1809
1810                 }
1811
1812         }
1813
1814         @Override
1815         final public boolean hasStatement(final Resource subject, final Resource relation) throws ServiceException {
1816
1817                 assert (subject != null);
1818                 assert (relation != null);
1819
1820                 try {
1821
1822                         Collection<Resource> objects = getObjects(subject, relation);
1823                         return !objects.isEmpty();
1824
1825                 } catch (ServiceException e) {
1826
1827                         throw new ServiceException(e);
1828
1829                 } 
1830                 
1831         }
1832
1833         @Override
1834         final public boolean hasStatement(final Resource subject, final Resource relation, final Resource object) throws ServiceException {
1835
1836                 assert (subject != null);
1837                 assert (relation != null);
1838                 assert (object != null);
1839
1840                 try {
1841
1842                         for(Resource o : getObjects(subject, relation)) {
1843                                 if(object.equals(o)) return true;
1844                         }
1845                         
1846                         return false;
1847
1848                 } catch (ServiceException e) {
1849
1850                         throw new ServiceException(e);
1851
1852                 }
1853
1854         }
1855
1856         @Override
1857         final public boolean hasValue(final Resource subject) throws ServiceException {
1858
1859                 assert (subject != null);
1860
1861                 try {
1862
1863                         SyncReadProcedure<Boolean> procedure = new SyncReadProcedure<Boolean>();
1864                         processor.forHasValue(this, subject, procedure);
1865                         procedure.checkAndThrow();
1866                         return procedure.result;
1867
1868                 } catch (ServiceException e) {
1869
1870                         throw new ServiceException(e);
1871
1872                 } catch (DatabaseException e) {
1873
1874                         throw new ServiceException(INTERNAL_ERROR_STRING, e);
1875
1876                 }
1877
1878         }
1879
1880         final AsyncProcedure<?> NONE = new AsyncProcedure<Object>() {
1881
1882                 @Override
1883                 public void execute(AsyncReadGraph graph, Object result) {
1884                 }
1885
1886                 @Override
1887                 public void exception(AsyncReadGraph graph, Throwable throwable) {
1888                 }
1889                 
1890         };
1891         
1892         /*
1893          * Implementation of the interface RequestProcessor
1894          */
1895
1896         @Override
1897         public <T> T syncRequest(final Read<T> request) throws DatabaseException {
1898
1899                 assert (request != null);
1900
1901                 return QueryCache.resultReadEntry(this, request, parent, null, null);
1902                 
1903                 //return processor.query(this, request, parent, null, null);
1904
1905 //              if (parent != null) {
1906 //
1907 //                      try {
1908 //                      } catch (Throwable e) {
1909 //                              if(e instanceof DatabaseException) throw (DatabaseException)e;
1910 //                              else throw new DatabaseException(e);
1911 //                      }
1912 //
1913 //              } else {
1914 //
1915 //                      try {
1916 //
1917 //                              return processor.tryQuery(this, request);
1918 //
1919 //                      } catch (Throwable throwable) {
1920 //
1921 //                              //Logger.defaultLogError("Internal read request failure", throwable);
1922 //
1923 //                              if (throwable instanceof DatabaseException)
1924 //                                      throw (DatabaseException) throwable;
1925 //                              else
1926 //                                      throw new DatabaseException(
1927 //                                                      "Unexpected exception in ReadGraph.syncRequest(Read,Procedure)",
1928 //                                                      throwable);
1929 //
1930 //                      }
1931 //
1932 //              }
1933                 
1934         }
1935
1936         @Override
1937         public <T> T syncRequest(Read<T> request, SyncListener<T> procedure)
1938                         throws DatabaseException {
1939                 return syncRequest(request, new SyncToAsyncListener<T>(procedure));
1940         }
1941
1942         @Override
1943         public <T> T syncRequest(Read<T> request, final Listener<T> procedure)
1944                         throws DatabaseException {
1945                 return syncRequest(request, new NoneToAsyncListener<T>(procedure));
1946         }
1947
1948         @Override
1949         public <T> T syncRequest(final Read<T> request, final AsyncProcedure<T> procedure) throws DatabaseException {
1950
1951                 assert (request != null);
1952
1953                 ListenerBase listener = procedure != null ? getListenerBase(procedure) : null;
1954
1955                 return QueryCache.resultReadEntry(this, request, parent, listener, procedure);
1956                 
1957 //        return processor.query(this, request, parent, procedure, listener);
1958         
1959
1960 //              if (parent != null || listener != null) {
1961 //                      
1962 //                      try {
1963 //            } catch (Throwable e) {
1964 //                if(e instanceof DatabaseException) throw (DatabaseException)e;
1965 //                else throw new DatabaseException(e);
1966 //            }
1967 //
1968 //              } else {
1969 //
1970 //                      try {
1971 //
1972 //                              T t = processor.tryQuery(this, request);
1973 //                              if(procedure != null)
1974 //                                      procedure.execute(this, t);
1975 //
1976 //                              return t;
1977 //
1978 //                      } catch (Throwable throwable) {
1979 //
1980 //                              Logger.defaultLogError("Internal read request failure", throwable);
1981 //
1982 //                              if(procedure != null)
1983 //                                      procedure.exception(this, throwable);
1984 //                              
1985 //                              if (throwable instanceof DatabaseException)
1986 //                                      throw (DatabaseException) throwable;
1987 //                              else
1988 //                                      throw new DatabaseException(
1989 //                                                      "Unexpected exception in ReadGraph.syncRequest(Read,Procedure)",
1990 //                                                      throwable);
1991 //
1992 //                      }
1993 //
1994 //              }
1995
1996         }
1997
1998         @Override
1999         public <T> T syncRequest(final Read<T> request,
2000                         final SyncProcedure<T> procedure) throws DatabaseException {
2001                 return syncRequest(request, new SyncToAsyncProcedure<T>(procedure));
2002         }
2003
2004         @Override
2005         public <T> T syncRequest(Read<T> request, Procedure<T> procedure)
2006                         throws DatabaseException {
2007                 return syncRequest(request, new NoneToAsyncProcedure<T>(procedure));
2008         }
2009
2010         static class AsyncReadProcedure<T> implements AsyncProcedure<T> {
2011
2012                 private static Throwable DONE = new Throwable();
2013                 
2014                 T result = null;
2015                 Throwable exception = null;
2016                 
2017                 @Override
2018                 public void execute(AsyncReadGraph graph, T t) {
2019                         result = t;
2020                         exception = DONE;
2021                 }
2022
2023                 @Override
2024                 public void exception(AsyncReadGraph graph, Throwable t) {
2025                         exception = t;
2026                 }
2027                 
2028                 public void checkAndThrow() throws DatabaseException {
2029                         if(exception != DONE) {
2030                                 if (exception instanceof DatabaseException)
2031                                         throw (DatabaseException) exception;
2032                                 else
2033                                         throw new DatabaseException(
2034                                                         "Unexpected exception in ReadGraph.syncRequest(AsyncMultiRead)",
2035                                                         exception);
2036                         }
2037                 }
2038                 
2039                 public boolean done() {
2040                         return exception != null;
2041                 }
2042                 
2043         }
2044         
2045         @Override
2046         public <T> T syncRequest(final AsyncRead<T> request)
2047                         throws DatabaseException {
2048
2049                 assert (request != null);
2050                 AsyncReadProcedure<T> procedure = new AsyncReadProcedure<T>();
2051                 syncRequest(request, procedure);
2052                 procedure.checkAndThrow();
2053                 return procedure.result;
2054                 
2055 //              return syncRequest(request, new AsyncProcedureAdapter<T>());
2056
2057         }
2058
2059         @Override
2060         public <T> T syncRequest(AsyncRead<T> request, AsyncListener<T> procedure)
2061                         throws DatabaseException {
2062                 return syncRequest(request, (AsyncProcedure<T>) procedure);
2063         }
2064
2065         @Override
2066         public <T> T syncRequest(AsyncRead<T> request, SyncListener<T> procedure)
2067                         throws DatabaseException {
2068                 return syncRequest(request, new SyncToAsyncListener<T>(procedure));
2069         }
2070
2071         @Override
2072         public <T> T syncRequest(AsyncRead<T> request, Listener<T> procedure)
2073                         throws DatabaseException {
2074                 return syncRequest(request, new NoneToAsyncListener<T>(procedure));
2075         }
2076
2077         @Override
2078         final public <T> T syncRequest(final AsyncRead<T> request,
2079                         final AsyncProcedure<T> procedure) throws DatabaseException {
2080
2081                 assert (request != null);
2082
2083                 ListenerBase listener = getListenerBase(procedure);
2084
2085                 final ResultCallWrappedSingleQueryProcedure4<T> wrapper = new ResultCallWrappedSingleQueryProcedure4<T>(
2086                                 procedure, request);
2087                 
2088                 QueryCache.runnerAsyncReadEntry(this, request, parent, listener, wrapper);
2089                 
2090                 //processor.query(this, request, parent, wrapper, listener);
2091                 
2092                 return wrapper.getResult();
2093
2094 //              if (parent != null || listener != null || ((request.getFlags() & RequestFlags.SCHEDULE) > 0)) {
2095 //
2096 ////                    Object syncParent = request;
2097 //
2098 ////                    final ReadGraphImpl newGraph = newSync();
2099 //
2100 //
2101 ////                    newGraph.waitAsync(syncParent);
2102 //                      
2103 //                      Throwable e = wrapper.getException();
2104 //                      if (e != null) {
2105 //                              // The request was async - produce meaningful stack trace by
2106 //                              // wrapping
2107 //                              if (e instanceof DatabaseException)
2108 //                                      throw (DatabaseException) e;
2109 //                              else
2110 //                                      throw new DatabaseException(e);
2111 //                      }
2112 //                      
2113 //                      return wrapper.getResult();
2114 //
2115 //              } else {
2116 //
2117 //                      // System.out.println("direct call " + request );
2118 //
2119 //                      // Do not set the sync state.parent for external threads
2120 ////                    Object syncParent = request;
2121 //
2122 ////                    final ReadGraphImpl newGraph = newSync();
2123 //
2124 //                      final ResultCallWrappedSingleQueryProcedure4<T> wrapper = new ResultCallWrappedSingleQueryProcedure4<T>(
2125 //                                      procedure, request);
2126 //
2127 //                      try {
2128 //
2129 //                              processor.tryQuery(this, request, wrapper);
2130 //
2131 //                      } catch (Throwable t) {
2132 //
2133 //                              wrapper.exception(this, t);
2134 //
2135 //                      }
2136 //
2137 //                      Throwable e = wrapper.getException();
2138 //                      if (e != null) {
2139 //                              // The request was async - produce meaningful stack trace by
2140 //                              // wrapping
2141 //                              if (e instanceof DatabaseException)
2142 //                                      throw (DatabaseException) e;
2143 //                              else
2144 //                                      throw new DatabaseException(e);
2145 //                      }
2146 //                      
2147 //                      return wrapper.getResult();
2148 //
2149 //              }
2150
2151         }
2152
2153         final private <T> void syncRequest(final AsyncRead<T> request, final AsyncReadProcedure<T> procedure) throws DatabaseException {
2154
2155                 assert (request != null);
2156
2157                 ListenerBase listener = getListenerBase(procedure);
2158                 assert(listener == null);
2159
2160 //              final ResultCallWrappedSingleQueryProcedure4<T> wrapper = new ResultCallWrappedSingleQueryProcedure4<T>(
2161 //                              procedure, request);
2162
2163                 QueryCache.runnerAsyncReadEntry(this, request, parent, listener, procedure);
2164
2165         }
2166
2167         @Override
2168         public <T> T syncRequest(AsyncRead<T> request,
2169                         final SyncProcedure<T> procedure) throws DatabaseException {
2170                 return syncRequest(request, new SyncToAsyncProcedure<T>(procedure));
2171         }
2172
2173         @Override
2174         final public <T> T syncRequest(final AsyncRead<T> request,
2175                         final Procedure<T> procedure) throws DatabaseException {
2176                 return syncRequest(request, new NoneToAsyncProcedure<T>(procedure));
2177         }
2178
2179         @Override
2180         public <T> Collection<T> syncRequest(final MultiRead<T> request)
2181                         throws DatabaseException {
2182
2183                 assert (request != null);
2184
2185                 final ArrayList<T> result = new ArrayList<T>();
2186                 final DataContainer<Throwable> exception = new DataContainer<Throwable>();
2187
2188                 syncRequest(request, new AsyncMultiProcedure<T>() {
2189
2190                         @Override
2191                         public void execute(AsyncReadGraph graph, T t) {
2192                                 synchronized (result) {
2193                                         result.add(t);
2194                                 }
2195                         }
2196
2197                         @Override
2198                         public void finished(AsyncReadGraph graph) {
2199                         }
2200
2201                         @Override
2202                         public void exception(AsyncReadGraph graph, Throwable t) {
2203                                 exception.set(t);
2204                         }
2205
2206                         @Override
2207                         public String toString() {
2208                                 return "syncRequest(MultiRead) -> " + request;
2209                         }
2210
2211                 });
2212
2213                 Throwable t = exception.get();
2214                 if (t != null) {
2215                         if (t instanceof DatabaseException)
2216                                 throw (DatabaseException) t;
2217                         else
2218                                 throw new DatabaseException(
2219                                                 "Unexpected exception in ReadGraph.syncRequest(Read)",
2220                                                 t);
2221                 }
2222
2223                 return result;
2224
2225         }
2226
2227         @Override
2228         public <T> Collection<T> syncRequest(MultiRead<T> request,
2229                         AsyncMultiListener<T> procedure) {
2230                 return syncRequest(request, (AsyncMultiProcedure<T>) procedure);
2231         }
2232
2233         @Override
2234         public <T> Collection<T> syncRequest(MultiRead<T> request,
2235                         SyncMultiListener<T> procedure) {
2236                 return syncRequest(request, new SyncToAsyncMultiListener<T>(procedure));
2237         }
2238
2239         @Override
2240         public <T> Collection<T> syncRequest(MultiRead<T> request,
2241                         MultiListener<T> procedure) {
2242                 return syncRequest(request, new NoneToAsyncMultiListener<T>(procedure));
2243         }
2244
2245         @Override
2246         public <T> Collection<T> syncRequest(MultiRead<T> request,
2247                         AsyncMultiProcedure<T> procedure) {
2248
2249                 assert (request != null);
2250
2251                 ListenerBase listener = getListenerBase(procedure);
2252
2253                 if (parent != null || listener != null) {
2254
2255 //                      Object syncParent = request;
2256
2257 //                      final ReadGraphImpl newGraph = newSync();
2258
2259                         processor.query(this, request, parent, procedure, listener);
2260
2261 //                      newGraph.waitAsync(syncParent);
2262
2263                 } else {
2264
2265 //                      Object syncParent = request;
2266
2267 //                      final ReadGraphImpl newGraph = newSync();
2268
2269                         final ResultCallWrappedQueryProcedure4<T> wrapper = new ResultCallWrappedQueryProcedure4<T>(procedure);
2270
2271                         try {
2272
2273                                 request.perform(this, wrapper);
2274
2275                         } catch (Throwable t) {
2276
2277                                 wrapper.exception(this, t);
2278 //                              newGraph.waitAsync(syncParent);
2279
2280                         }
2281
2282                 }
2283
2284                 // TODO
2285                 return null;
2286
2287         }
2288
2289         @Override
2290         public <T> Collection<T> syncRequest(MultiRead<T> request,
2291                         SyncMultiProcedure<T> procedure) {
2292                 return syncRequest(request, new SyncToAsyncMultiProcedure<T>(procedure));
2293         }
2294
2295         @Override
2296         public <T> Collection<T> syncRequest(MultiRead<T> request,
2297                         MultiProcedure<T> procedure) {
2298                 return syncRequest(request, new NoneToAsyncMultiProcedure<T>(procedure));
2299         }
2300
2301         static class AsyncMultiReadProcedure<T> extends ArrayList<T> implements AsyncMultiProcedure<T> {
2302
2303                 private static Throwable DONE = new Throwable();
2304                 
2305                 private static final long serialVersionUID = -6494230465108115812L;
2306                 
2307                 Throwable exception = null;
2308                 
2309                 @Override
2310                 public synchronized void execute(AsyncReadGraph graph, T t) {
2311                         add(t);
2312                 }
2313
2314                 @Override
2315                 public void finished(AsyncReadGraph graph) {
2316                         exception = DONE;
2317                 }
2318
2319                 @Override
2320                 public void exception(AsyncReadGraph graph, Throwable t) {
2321                         exception = t;
2322                 }
2323                 
2324                 public void checkAndThrow() throws DatabaseException {
2325                         if(exception != DONE) {
2326                                 if (exception instanceof DatabaseException)
2327                                         throw (DatabaseException) exception;
2328                                 else
2329                                         throw new DatabaseException(
2330                                                         "Unexpected exception in ReadGraph.syncRequest(AsyncMultiRead)",
2331                                                         exception);
2332                         }
2333                 }
2334                 
2335                 public boolean done() {
2336                         return exception != null;
2337                 }
2338                 
2339         }
2340
2341         @Override
2342         final public <T> Collection<T> syncRequest(AsyncMultiRead<T> request)
2343                         throws DatabaseException {
2344
2345                 assert (request != null);
2346
2347                 final AsyncMultiReadProcedure<T> procedure = new AsyncMultiReadProcedure<T>();
2348                 
2349                 syncRequest(request, procedure);
2350                 
2351                 procedure.checkAndThrow();
2352                 return procedure;
2353
2354         }
2355
2356         @Override
2357         public <T> Collection<T> syncRequest(AsyncMultiRead<T> request,
2358                         AsyncMultiListener<T> procedure) {
2359                 return syncRequest(request, (AsyncMultiProcedure<T>) procedure);
2360         }
2361
2362         @Override
2363         public <T> Collection<T> syncRequest(AsyncMultiRead<T> request,
2364                         SyncMultiListener<T> procedure) {
2365                 return syncRequest(request, new SyncToAsyncMultiListener<T>(procedure));
2366         }
2367
2368         @Override
2369         public <T> Collection<T> syncRequest(AsyncMultiRead<T> request,
2370                         MultiListener<T> procedure) {
2371                 return syncRequest(request, new NoneToAsyncMultiListener<T>(procedure));
2372         }
2373
2374         final private <T> void syncRequest(final AsyncMultiRead<T> request,
2375                         final AsyncMultiReadProcedure<T> procedure) {
2376
2377                 assert (request != null);
2378                 assert (procedure != null);
2379
2380                 ListenerBase listener = getListenerBase(procedure);
2381
2382                 if (parent != null || listener != null) {
2383
2384 //                      Object syncParent = request;
2385
2386 //                      final ReadGraphImpl newGraph = newSync();
2387
2388                         processor.query(this, request, parent, procedure, listener);
2389
2390 //                      newGraph.waitAsync(syncParent);
2391                         waitAsyncProcedure(procedure);
2392
2393                 } else {
2394
2395 //                      Object syncParent = callerThread == Integer.MIN_VALUE ? null
2396 //                                      : request;
2397 //
2398 //                      final ReadGraphImpl newGraph = newSyncAsync(syncParent);
2399
2400                         try {
2401
2402 //                              inc();
2403 //                              ReadGraphImpl sync = newSync();
2404                                 request.perform(this, procedure);
2405 //                              sync.waitAsync(null);
2406                                 waitAsyncProcedure(procedure);
2407 //                              dec();
2408
2409                         } catch (Throwable t) {
2410
2411                                 waitAsyncProcedure(procedure);
2412 //                              dec();
2413
2414                         }
2415
2416                 }
2417
2418         }
2419         
2420         
2421         @Override
2422         final public <T> Collection<T> syncRequest(final AsyncMultiRead<T> request,
2423                         final AsyncMultiProcedure<T> procedure) {
2424
2425                 assert (request != null);
2426                 assert (procedure != null);
2427
2428                 ListenerBase listener = getListenerBase(procedure);
2429
2430                 if (parent != null || listener != null) {
2431
2432 //                      Object syncParent = request;
2433
2434 //                      final ReadGraphImpl newGraph = newSync();
2435
2436                         processor.query(this, request, parent, procedure, listener);
2437
2438 //                      newGraph.waitAsync(syncParent);
2439
2440                 } else {
2441
2442 //                      Object syncParent = request;
2443
2444 //                      final ReadGraphImpl newGraph = newSync();
2445
2446                         try {
2447
2448                                 request.perform(this, new AsyncMultiProcedure<T>() {
2449
2450                                         @Override
2451                                         public void execute(AsyncReadGraph graph, T result) {
2452                                                 procedure.execute(graph, result);
2453                                         }
2454
2455                                         @Override
2456                                         public void finished(AsyncReadGraph graph) {
2457                                                 procedure.finished(graph);
2458                                         }
2459
2460                                         @Override
2461                                         public void exception(AsyncReadGraph graph, Throwable t) {
2462                                                 procedure.exception(graph, t);
2463                                         }
2464
2465                                         @Override
2466                                         public String toString() {
2467                                                 return "syncRequest(AsyncMultiRead) -> " + procedure;
2468                                         }
2469
2470                                 });
2471
2472                         } catch (Throwable t) {
2473
2474                         }
2475
2476                 }
2477
2478                 // TODO!!
2479                 return null;
2480
2481         }
2482
2483         @Override
2484         public <T> Collection<T> syncRequest(AsyncMultiRead<T> request,
2485                         final SyncMultiProcedure<T> procedure) {
2486                 return syncRequest(request, new SyncToAsyncMultiProcedure<T>(procedure));
2487         }
2488
2489         @Override
2490         final public <T> Collection<T> syncRequest(final AsyncMultiRead<T> request,
2491                         final MultiProcedure<T> procedure) {
2492                 return syncRequest(request, new NoneToAsyncMultiProcedure<T>(procedure));
2493         }
2494
2495         @Override
2496         public <T> T syncRequest(final ExternalRead<T> request)
2497                         throws DatabaseException {
2498
2499                 assert (request != null);
2500
2501                 return syncRequest(request, new Procedure<T>() {
2502
2503                         @Override
2504                         public void execute(T t) {
2505                         }
2506
2507                         @Override
2508                         public void exception(Throwable t) {
2509                         }
2510
2511                         @Override
2512                         public String toString() {
2513                                 return "syncRequest(AsyncRead) -> " + request;
2514                         }
2515
2516                 });
2517
2518         }
2519
2520         @Override
2521         public <T> T syncRequest(ExternalRead<T> request, Listener<T> procedure) throws DatabaseException {
2522                 return syncRequest(request, (Procedure<T>) procedure);
2523         }
2524
2525         @Override
2526         final public <T> T syncRequest(final ExternalRead<T> request,
2527                         final Procedure<T> procedure) throws DatabaseException {
2528
2529                 assert (request != null);
2530
2531                 ListenerBase listener = getListenerBase(procedure);
2532                 
2533                 final DataContainer<Throwable> exception = new DataContainer<Throwable>();
2534                 final DataContainer<T> result = new DataContainer<T>();
2535
2536                 processor.query(this, request, parent, new Procedure<T>() {
2537
2538                         @Override
2539                         public void exception(Throwable throwable) {
2540                                 exception.set(throwable);
2541                                 procedure.exception(throwable);
2542                         }
2543
2544                         @Override
2545                         public void execute(T t) {
2546                                 result.set(t);
2547                                 procedure.execute(t);
2548                         }
2549
2550                 }, listener);
2551                 
2552
2553
2554 //              if (parent != null || listener != null) {
2555 //
2556 ////                    final ReadGraphImpl newGraph = newSync();
2557 //                      
2558 //
2559 ////                    newGraph.waitAsync(request);
2560 //
2561 //              } else {
2562 //
2563 //                      try {
2564 //
2565 //                              T t = processor.tryQuery(this, request);
2566 //                              result.set(t);
2567 //                              procedure.execute(t);
2568 //
2569 //                      } catch (Throwable t) {
2570 //
2571 //                          if (t instanceof DatabaseException) {
2572 //                              exception.set((DatabaseException)t);
2573 //                              procedure.exception(exception.get());
2574 //                          } else {
2575 //                              exception.set(new DatabaseException(
2576 //                                      "Unexpected exception in ReadGraph.syncRequest(Read)",
2577 //                                      t));
2578 //                              procedure.exception(exception.get());
2579 //                          }
2580 //
2581 //                      }
2582 //
2583 //              }
2584
2585                 Throwable t = exception.get();
2586                 if (t != null) {
2587                         if (t instanceof DatabaseException)
2588                                 throw (DatabaseException) t;
2589                         else
2590                                 throw new DatabaseException(
2591                                                 "Unexpected exception in ReadGraph.syncRequest(Read)",
2592                                                 t);
2593                 }
2594
2595                 return result.get();            
2596
2597         }
2598
2599         @Override
2600         public void syncRequest(final Write request) throws DatabaseException {
2601
2602                 assert (request != null);
2603
2604                 throw new DatabaseException(
2605                                 "Write operations are not supported during read transactions!");
2606
2607         }
2608
2609         @Override
2610         public <T> T syncRequest(final WriteResult<T> request) throws DatabaseException {
2611
2612                 assert (request != null);
2613
2614                 throw new DatabaseException(
2615                                 "Write operations are not supported during read transactions!");
2616
2617         }
2618
2619         @Override
2620         public void syncRequest(final DelayedWrite request)
2621                         throws DatabaseException {
2622
2623                 assert (request != null);
2624
2625                 throw new DatabaseException(
2626                                 "Write operations are not supported during read transactions!");
2627
2628         }
2629
2630         @Override
2631         public <T> T syncRequest(final DelayedWriteResult<T> request) throws DatabaseException {
2632
2633                 assert (request != null);
2634
2635                 throw new DatabaseException(
2636                                 "Write operations are not supported during read transactions!");
2637
2638         }
2639         
2640         @Override
2641         public void syncRequest(final WriteOnly request) throws DatabaseException {
2642
2643                 assert (request != null);
2644
2645                 throw new DatabaseException(
2646                                 "Write operations are not supported during read transactions!");
2647
2648         }
2649
2650         @Override
2651         public <T> T syncRequest(final WriteOnlyResult<T> request) throws DatabaseException {
2652
2653                 assert (request != null);
2654
2655                 throw new DatabaseException(
2656                                 "Write operations are not supported during read transactions!");
2657
2658         }
2659         
2660         @Override
2661         public <T> void async(ReadInterface<T> r, AsyncProcedure<T> procedure) {
2662                 r.request(this, procedure);
2663         }
2664         
2665         @Override
2666         public <T> void async(ReadInterface<T> r, Procedure<T> procedure) {
2667                 r.request(this, procedure);
2668         }
2669         
2670         @Override
2671         public <T> void async(ReadInterface<T> r, SyncProcedure<T> procedure) {
2672                 r.request(this, procedure);
2673         }
2674         
2675         @Override
2676         public <T> void async(ReadInterface<T> r, AsyncListener<T> procedure) {
2677                 r.request(this, procedure);
2678         }
2679         
2680         @Override
2681         public <T> void async(ReadInterface<T> r, Listener<T> procedure) {
2682                 r.request(this, procedure);
2683         }
2684         
2685         @Override
2686         public <T> void async(ReadInterface<T> r, SyncListener<T> procedure) {
2687                 r.request(this, procedure);
2688         }
2689
2690         @Override
2691         public <T> T sync(ReadInterface<T> r) throws DatabaseException {
2692                 return r.request(this);
2693         }
2694         
2695         @Override
2696         public <T> T sync(WriteInterface<T> r) throws DatabaseException {
2697                 return r.request(this);
2698         }
2699         
2700         @Override
2701         public <T> void async(WriteInterface<T> r, Procedure<T> procedure) {
2702                 r.request(this, procedure);
2703         }
2704
2705         @Override
2706         public <T> void async(WriteInterface<T> r) {
2707                 r.request(this, new ProcedureAdapter<T>());
2708         }
2709
2710         /*
2711          * Implementation of the interface AsyncReadGraph
2712          */
2713
2714         @Override
2715         public void forURI(Resource resource, AsyncListener<String> listener) {
2716                 asyncRequest(new org.simantics.db.common.uri.ResourceToURI(resource),
2717                                 listener);
2718         }
2719
2720         @Override
2721         public void forURI(Resource resource, SyncListener<String> listener) {
2722                 asyncRequest(new org.simantics.db.common.uri.ResourceToURI(resource),
2723                                 listener);
2724         }
2725
2726         @Override
2727         public void forURI(Resource resource, Listener<String> listener) {
2728                 asyncRequest(new org.simantics.db.common.uri.ResourceToURI(resource),
2729                                 listener);
2730         }
2731
2732         @Override
2733         final public void forURI(final Resource resource,
2734                         final AsyncProcedure<String> procedure) {
2735
2736                 assert (resource != null);
2737                 assert (procedure != null);
2738
2739                 asyncRequest(new org.simantics.db.common.uri.ResourceToURI(resource),
2740                                 procedure);
2741
2742         }
2743
2744         @Override
2745         public void forURI(Resource resource, SyncProcedure<String> procedure) {
2746                 forURI(resource, new SyncToAsyncProcedure<String>(procedure));
2747         }
2748
2749         @Override
2750         public void forURI(Resource resource, Procedure<String> procedure) {
2751                 forURI(resource, new NoneToAsyncProcedure<String>(procedure));
2752         }
2753         
2754         @Override
2755         public void forResource(String id, AsyncListener<Resource> listener) {
2756                 asyncRequest(new org.simantics.db.common.primitiverequest.Resource(id),
2757                                 listener);
2758         }
2759
2760         @Override
2761         public void forResource(String id, SyncListener<Resource> listener) {
2762                 asyncRequest(new org.simantics.db.common.primitiverequest.Resource(id),
2763                                 listener);
2764         }
2765
2766         @Override
2767         public void forResource(String id, Listener<Resource> listener) {
2768                 asyncRequest(new org.simantics.db.common.primitiverequest.Resource(id),
2769                                 listener);
2770         }
2771
2772         @Override
2773         final public void forResource(final String id,
2774                         final AsyncProcedure<Resource> procedure) {
2775
2776                 assert (id != null);
2777                 assert (procedure != null);
2778
2779                 processor.forResource(this, id, procedure);
2780
2781         }
2782
2783         @Override
2784         public void forResource(String id, SyncProcedure<Resource> procedure) {
2785                 forResource(id, new SyncToAsyncProcedure<Resource>(procedure));
2786         }
2787
2788         @Override
2789         public void forResource(String id, Procedure<Resource> procedure) {
2790                 forResource(id, new NoneToAsyncProcedure<Resource>(procedure));
2791         }
2792
2793         @Override
2794         public void forBuiltin(String id, AsyncListener<Resource> listener) {
2795                 asyncRequest(new Builtin(id), listener);
2796         }
2797
2798         @Override
2799         public void forBuiltin(String id, SyncListener<Resource> listener) {
2800                 asyncRequest(new Builtin(id), listener);
2801         }
2802
2803         @Override
2804         public void forBuiltin(String id, Listener<Resource> listener) {
2805                 asyncRequest(new Builtin(id), listener);
2806         }
2807
2808         @Override
2809         final public void forBuiltin(final String id,
2810                         final AsyncProcedure<Resource> procedure) {
2811
2812                 assert (id != null);
2813                 assert (procedure != null);
2814
2815                 processor.forBuiltin(this, id, procedure);
2816
2817         }
2818
2819         @Override
2820         public void forBuiltin(String id, SyncProcedure<Resource> procedure) {
2821                 forBuiltin(id, new SyncToAsyncProcedure<Resource>(procedure));
2822         }
2823
2824         @Override
2825         public void forBuiltin(String id, Procedure<Resource> procedure) {
2826                 forBuiltin(id, new NoneToAsyncProcedure<Resource>(procedure));
2827         }
2828
2829         @Override
2830         final public void forEachStatement(Resource subject, Resource relation,
2831                         AsyncMultiProcedure<Statement> procedure) {
2832
2833                 assert (subject != null);
2834                 assert (relation != null);
2835                 assert (procedure != null);
2836
2837                 processor.forEachStatement(this, subject, relation, procedure);
2838
2839         }
2840
2841         @Override
2842         public void forEachStatement(Resource subject, Resource relation,
2843                         SyncMultiProcedure<Statement> procedure) {
2844                 forEachStatement(subject, relation,
2845                                 new SyncToAsyncMultiProcedure<Statement>(procedure));
2846         }
2847
2848         @Override
2849         final public void forEachStatement(Resource subject, Resource relation,
2850                         MultiProcedure<Statement> procedure) {
2851
2852                 assert (subject != null);
2853                 assert (relation != null);
2854                 assert (procedure != null);
2855
2856                 processor.forEachStatement(this, subject, relation, procedure);
2857
2858         }
2859
2860         @Override
2861         final public void forStatementSet(Resource subject, Resource relation,
2862                         AsyncSetListener<Statement> procedure) {
2863
2864                 assert (subject != null);
2865                 assert (relation != null);
2866                 assert (procedure != null);
2867
2868                 processor.forStatementSet(this, subject, relation, procedure);
2869
2870         }
2871
2872         @Override
2873         final public void forStatementSet(Resource subject, Resource relation,
2874                         SyncSetListener<Statement> procedure) {
2875                 forStatementSet(subject, relation,
2876                                 new SyncToAsyncSetProcedure<Statement>(procedure));
2877         }
2878
2879         @Override
2880         public void forStatementSet(Resource subject, Resource relation,
2881                         SetListener<Statement> listener) {
2882                 forStatementSet(subject, relation,
2883                                 new NoneToAsyncSetProcedure<Statement>(listener));
2884         }
2885
2886         @Override
2887         final public void forEachAssertedStatement(final Resource subject,
2888                         final Resource relation,
2889                         final AsyncMultiProcedure<Statement> procedure) {
2890
2891                 assert (subject != null);
2892                 assert (relation != null);
2893                 assert (procedure != null);
2894
2895                 processor.forEachAssertedStatement(this, subject, relation, procedure);
2896
2897         }
2898
2899         @Override
2900         public void forEachAssertedStatement(Resource subject, Resource relation,
2901                         SyncMultiProcedure<Statement> procedure) {
2902                 forEachAssertedStatement(subject, relation,
2903                                 new SyncToAsyncMultiProcedure<Statement>(procedure));
2904         }
2905
2906         @Override
2907         public void forEachAssertedStatement(Resource subject, Resource relation,
2908                         MultiProcedure<Statement> procedure) {
2909                 forEachAssertedStatement(subject, relation,
2910                                 new NoneToAsyncMultiProcedure<Statement>(procedure));
2911         }
2912
2913         @Override
2914         public void forAssertedStatementSet(Resource subject, Resource relation,
2915                         AsyncSetListener<Statement> procedure) {
2916
2917                 assert (subject != null);
2918                 assert (relation != null);
2919                 assert (procedure != null);
2920
2921                 processor.forAssertedStatementSet(this, subject, relation, procedure);
2922
2923         }
2924
2925         @Override
2926         public void forAssertedStatementSet(Resource subject, Resource relation,
2927                         SyncSetListener<Statement> procedure) {
2928
2929                 assert (subject != null);
2930                 assert (relation != null);
2931                 assert (procedure != null);
2932
2933                 forAssertedStatementSet(subject, relation,
2934                                 new SyncToAsyncSetProcedure<Statement>(procedure));
2935
2936         }
2937
2938         @Override
2939         public void forAssertedStatementSet(Resource subject, Resource relation,
2940                         SetListener<Statement> procedure) {
2941
2942                 assert (subject != null);
2943                 assert (relation != null);
2944                 assert (procedure != null);
2945
2946                 forAssertedStatementSet(subject, relation,
2947                                 new NoneToAsyncSetProcedure<Statement>(procedure));
2948
2949         }
2950
2951         @Override
2952         final public void forEachPredicate(final Resource subject,
2953                         final AsyncMultiProcedure<Resource> procedure) {
2954
2955                 assert (subject != null);
2956                 assert (procedure != null);
2957
2958                 processor.forEachPredicate(this, subject, procedure);
2959
2960         }
2961
2962         @Override
2963         public void forEachPredicate(Resource subject,
2964                         SyncMultiProcedure<Resource> procedure) {
2965                 forEachPredicate(subject, new SyncToAsyncMultiProcedure<Resource>(
2966                                 procedure));
2967         }
2968
2969         @Override
2970         final public void forEachPredicate(final Resource subject,
2971                         final MultiProcedure<Resource> procedure) {
2972
2973                 assert (subject != null);
2974                 assert (procedure != null);
2975
2976                 processor.forEachPredicate(this, subject, procedure);
2977
2978         }
2979
2980         @Override
2981         final public void forPredicateSet(final Resource subject,
2982                         final AsyncSetListener<Resource> procedure) {
2983
2984                 assert (subject != null);
2985                 assert (procedure != null);
2986
2987                 processor.forPredicateSet(this, subject, procedure);
2988
2989         }
2990
2991         @Override
2992         final public void forPredicateSet(final Resource subject,
2993                         final SyncSetListener<Resource> procedure) {
2994
2995                 assert (subject != null);
2996                 assert (procedure != null);
2997
2998                 forPredicateSet(subject, new SyncToAsyncSetProcedure<Resource>(
2999                                 procedure));
3000
3001         }
3002
3003         @Override
3004         final public void forPredicateSet(final Resource subject,
3005                         final SetListener<Resource> procedure) {
3006
3007                 assert (subject != null);
3008                 assert (procedure != null);
3009
3010                 forPredicateSet(subject, new NoneToAsyncSetProcedure<Resource>(
3011                                 procedure));
3012
3013         }
3014
3015         @Override
3016         final public void forEachPrincipalType(final Resource subject,
3017                         final AsyncMultiProcedure<Resource> procedure) {
3018
3019                 assert (subject != null);
3020                 assert (procedure != null);
3021
3022                 processor.forEachPrincipalType(this, subject, procedure);
3023
3024         }
3025
3026         @Override
3027         public void forEachPrincipalType(Resource subject,
3028                         SyncMultiProcedure<Resource> procedure) {
3029                 forEachPrincipalType(subject, new SyncToAsyncMultiProcedure<Resource>(
3030                                 procedure));
3031         }
3032
3033         @Override
3034         final public void forEachPrincipalType(final Resource subject,
3035                         final MultiProcedure<Resource> procedure) {
3036
3037                 assert (subject != null);
3038                 assert (procedure != null);
3039
3040                 processor.forEachPrincipalType(this, subject, procedure);
3041
3042         }
3043
3044         @Override
3045         final public void forPrincipalTypeSet(final Resource subject,
3046                         final AsyncSetListener<Resource> procedure) {
3047
3048                 assert (subject != null);
3049                 assert (procedure != null);
3050
3051                 processor.forPrincipalTypeSet(this, subject, procedure);
3052
3053         }
3054
3055         @Override
3056         final public void forPrincipalTypeSet(final Resource subject,
3057                         final SyncSetListener<Resource> procedure) {
3058
3059                 assert (subject != null);
3060                 assert (procedure != null);
3061
3062                 forPrincipalTypeSet(subject, new SyncToAsyncSetProcedure<Resource>(
3063                                 procedure));
3064
3065         }
3066
3067         @Override
3068         final public void forPrincipalTypeSet(final Resource subject,
3069                         final SetListener<Resource> procedure) {
3070
3071                 assert (subject != null);
3072                 assert (procedure != null);
3073
3074                 forPrincipalTypeSet(subject, new NoneToAsyncSetProcedure<Resource>(
3075                                 procedure));
3076
3077         }
3078
3079         @Override
3080         public void forTypes(Resource subject, AsyncListener<Set<Resource>> listener) {
3081                 asyncRequest(new Types(subject), listener);
3082         }
3083
3084         @Override
3085         public void forTypes(Resource subject, SyncListener<Set<Resource>> listener) {
3086                 asyncRequest(new Types(subject), listener);
3087         }
3088
3089         @Override
3090         public void forTypes(Resource subject, Listener<Set<Resource>> listener) {
3091                 asyncRequest(new Types(subject), listener);
3092         }
3093
3094         @Override
3095         final public void forTypes(final Resource subject,
3096                         final AsyncProcedure<Set<Resource>> procedure) {
3097
3098                 assert (subject != null);
3099                 assert (procedure != null);
3100
3101                 processor.forTypes(this, subject, procedure);
3102
3103         }
3104
3105         @Override
3106         public void forTypes(Resource subject,
3107                         SyncProcedure<Set<Resource>> procedure) {
3108                 forTypes(subject, new SyncToAsyncProcedure<Set<Resource>>(procedure));
3109         }
3110
3111         @Override
3112         public void forTypes(Resource subject, Procedure<Set<Resource>> procedure) {
3113                 forTypes(subject, new NoneToAsyncProcedure<Set<Resource>>(procedure));
3114         }
3115
3116         @Override
3117         public void forSupertypes(Resource subject,
3118                         AsyncListener<Set<Resource>> listener) {
3119                 asyncRequest(new Types(subject), listener);
3120         }
3121
3122         @Override
3123         public void forSupertypes(Resource subject,
3124                         SyncListener<Set<Resource>> listener) {
3125                 asyncRequest(new Types(subject), listener);
3126         }
3127
3128         @Override
3129         public void forSupertypes(Resource subject, Listener<Set<Resource>> listener) {
3130                 asyncRequest(new Types(subject), listener);
3131         }
3132
3133         @Override
3134         final public void forSupertypes(final Resource subject,
3135                         final AsyncProcedure<Set<Resource>> procedure) {
3136
3137                 assert (subject != null);
3138                 assert (procedure != null);
3139
3140                 processor.forSupertypes(this, subject, procedure);
3141
3142         }
3143
3144         @Override
3145         public void forSupertypes(Resource subject,
3146                         SyncProcedure<Set<Resource>> procedure) {
3147                 forSupertypes(subject, new SyncToAsyncProcedure<Set<Resource>>(
3148                                 procedure));
3149         }
3150
3151         @Override
3152         public void forSupertypes(Resource subject,
3153                         Procedure<Set<Resource>> procedure) {
3154                 forSupertypes(subject, new NoneToAsyncProcedure<Set<Resource>>(
3155                                 procedure));
3156         }
3157
3158         @Override
3159         public void forDirectSuperrelations(Resource subject,
3160                         AsyncMultiProcedure<Resource> procedure) {
3161                 
3162                 assert (subject != null);
3163                 assert (procedure != null);
3164
3165                 processor.forDirectSuperrelations(this, subject, procedure);
3166                 
3167         }
3168
3169         @Override
3170         public void forPossibleSuperrelation(Resource subject, AsyncProcedure<Resource> procedure) {
3171                 
3172                 assert (subject != null);
3173                 assert (procedure != null);
3174
3175                 processor.forPossibleSuperrelation(this, subject, procedure);
3176                 
3177         }
3178
3179         @Override
3180         public void forSuperrelations(Resource subject,
3181                         AsyncListener<Set<Resource>> listener) {
3182                 asyncRequest(new Types(subject), listener);
3183         }
3184
3185         @Override
3186         public void forSuperrelations(Resource subject,
3187                         SyncListener<Set<Resource>> listener) {
3188                 asyncRequest(new Types(subject), listener);
3189         }
3190
3191         @Override
3192         public void forSuperrelations(Resource subject,
3193                         Listener<Set<Resource>> listener) {
3194                 asyncRequest(new Types(subject), listener);
3195         }
3196
3197         @Override
3198         final public void forSuperrelations(final Resource subject,
3199                         final AsyncProcedure<Set<Resource>> procedure) {
3200
3201                 assert (subject != null);
3202                 assert (procedure != null);
3203
3204                 processor.forSuperrelations(this, subject, procedure);
3205
3206         }
3207
3208         @Override
3209         public void forSuperrelations(Resource subject,
3210                         SyncProcedure<Set<Resource>> procedure) {
3211                 forSuperrelations(subject, new SyncToAsyncProcedure<Set<Resource>>(
3212                                 procedure));
3213         }
3214
3215         @Override
3216         public void forSuperrelations(Resource subject,
3217                         Procedure<Set<Resource>> procedure) {
3218                 forSuperrelations(subject, new NoneToAsyncProcedure<Set<Resource>>(
3219                                 procedure));
3220         }
3221
3222         @Override
3223         final public void forEachObject(final Resource subject, final Resource relation, final AsyncMultiProcedure<Resource> procedure) {
3224                 processor.forEachObject(this, subject, relation, procedure);
3225         }
3226
3227         @Override
3228         public void forEachObject(Resource subject, Resource relation,
3229                         SyncMultiProcedure<Resource> procedure) {
3230                 forEachObject(subject, relation,
3231                                 new SyncToAsyncMultiProcedure<Resource>(procedure));
3232         }
3233
3234         @Override
3235         public void forEachObject(Resource subject, Resource relation,
3236                         MultiProcedure<Resource> procedure) {
3237
3238                 processor.forEachObject(this, subject, relation, procedure);
3239
3240         }
3241
3242 //      @Override
3243 //      final public void forEachDirectObject(final Resource subject,
3244 //                      final Resource relation,
3245 //                      final AsyncMultiProcedure<Resource> procedure) {
3246 //
3247 //              processor.forEachDirectObject(this, subject, relation, procedure);
3248 //
3249 //      }
3250 //
3251 //      @Override
3252 //      public void forEachDirectObject(Resource subject, Resource relation,
3253 //                      SyncMultiProcedure<Resource> procedure) {
3254 //              forEachDirectObject(subject, relation,
3255 //                              new SyncToAsyncMultiProcedure<Resource>(procedure));
3256 //      }
3257 //
3258 //      @Override
3259 //      public void forEachDirectObject(Resource subject, Resource relation,
3260 //                      MultiProcedure<Resource> procedure) {
3261 //              forEachDirectObject(subject, relation,
3262 //                              new NoneToAsyncMultiProcedure<Resource>(procedure));
3263 //      }
3264         
3265         @Override
3266         final public void forEachDirectPredicate(final Resource subject, final AsyncMultiProcedure<Resource> procedure) {
3267                 processor.forEachDirectPredicate(this, subject, procedure);
3268         }
3269
3270         @Override
3271         public void forEachDirectPredicate(Resource subject, SyncMultiProcedure<Resource> procedure) {
3272                 forEachDirectPredicate(subject, new SyncToAsyncMultiProcedure<Resource>(procedure));
3273         }
3274
3275         @Override
3276         public void forEachDirectPredicate(Resource subject, MultiProcedure<Resource> procedure) {
3277                 forEachDirectPredicate(subject, new NoneToAsyncMultiProcedure<Resource>(procedure));
3278         }
3279
3280         @Override
3281         final public void forObjectSet(final Resource subject,
3282                         final Resource relation, final AsyncSetListener<Resource> procedure) {
3283
3284                 assert (subject != null);
3285                 assert (relation != null);
3286                 assert (procedure != null);
3287
3288                 processor.forObjectSet(this, subject, relation, procedure);
3289
3290         }
3291
3292         @Override
3293         final public void forObjectSet(final Resource subject,
3294                         final Resource relation, final SyncSetListener<Resource> procedure) {
3295
3296                 assert (subject != null);
3297                 assert (relation != null);
3298                 assert (procedure != null);
3299
3300                 forObjectSet(subject, relation, new SyncToAsyncSetProcedure<Resource>(
3301                                 procedure));
3302
3303         }
3304
3305         @Override
3306         final public void forObjectSet(final Resource subject,
3307                         final Resource relation, final SetListener<Resource> procedure) {
3308
3309                 assert (subject != null);
3310                 assert (relation != null);
3311                 assert (procedure != null);
3312
3313                 forObjectSet(subject, relation, new NoneToAsyncSetProcedure<Resource>(
3314                                 procedure));
3315
3316         }
3317
3318         @Override
3319         final public void forEachAssertedObject(final Resource subject,
3320                         final Resource relation,
3321                         final AsyncMultiProcedure<Resource> procedure) {
3322
3323                 assert (subject != null);
3324                 assert (relation != null);
3325                 assert (procedure != null);
3326
3327                 processor.forEachAssertedObject(this, subject, relation, procedure);
3328
3329         }
3330
3331         @Override
3332         public void forEachAssertedObject(Resource subject, Resource relation,
3333                         SyncMultiProcedure<Resource> procedure) {
3334
3335                 assert (subject != null);
3336                 assert (relation != null);
3337                 assert (procedure != null);
3338
3339                 forEachAssertedObject(subject, relation,
3340                                 new SyncToAsyncMultiProcedure<Resource>(procedure));
3341
3342         }
3343
3344         @Override
3345         public void forEachAssertedObject(Resource subject, Resource relation,
3346                         MultiProcedure<Resource> procedure) {
3347
3348                 assert (subject != null);
3349                 assert (relation != null);
3350                 assert (procedure != null);
3351
3352                 forEachAssertedObject(subject, relation,
3353                                 new NoneToAsyncMultiProcedure<Resource>(procedure));
3354
3355         }
3356
3357         @Override
3358         public void forAssertedObjectSet(Resource subject, Resource relation,
3359                         AsyncSetListener<Resource> procedure) {
3360
3361                 assert (subject != null);
3362                 assert (relation != null);
3363                 assert (procedure != null);
3364
3365                 processor.forAssertedObjectSet(this, subject, relation, procedure);
3366
3367         }
3368
3369         @Override
3370         public void forAssertedObjectSet(Resource subject, Resource relation,
3371                         SyncSetListener<Resource> procedure) {
3372
3373                 assert (subject != null);
3374                 assert (relation != null);
3375                 assert (procedure != null);
3376
3377                 forAssertedObjectSet(subject, relation,
3378                                 new SyncToAsyncSetProcedure<Resource>(procedure));
3379
3380         }
3381
3382         @Override
3383         public void forAssertedObjectSet(Resource subject, Resource relation,
3384                         SetListener<Resource> procedure) {
3385
3386                 assert (subject != null);
3387                 assert (relation != null);
3388                 assert (procedure != null);
3389
3390                 forAssertedObjectSet(subject, relation,
3391                                 new NoneToAsyncSetProcedure<Resource>(procedure));
3392
3393         }
3394
3395         @Override
3396         public void forInverse(Resource relation, AsyncListener<Resource> listener) {
3397                 asyncRequest(new Inverse(relation), listener);
3398         }
3399
3400         @Override
3401         public void forInverse(Resource relation, SyncListener<Resource> listener) {
3402                 asyncRequest(new Inverse(relation), listener);
3403         }
3404
3405         @Override
3406         public void forInverse(Resource relation, Listener<Resource> listener) {
3407                 asyncRequest(new Inverse(relation), listener);
3408         }
3409
3410         @Override
3411         final public void forInverse(final Resource relation,
3412                         final AsyncProcedure<Resource> procedure) {
3413
3414                 assert (relation != null);
3415                 assert (procedure != null);
3416
3417                 processor.forInverse(this, relation, new AsyncProcedure<Resource>() {
3418
3419                         @Override
3420                         public void execute(AsyncReadGraph graph, Resource result) {
3421                                 if (result != null)
3422                                         procedure.execute(graph, result);
3423                                 else {
3424                                         procedure.exception(graph, new NoInverseException(relation
3425                                                         .toString()));
3426                                 }
3427                         }
3428
3429                         @Override
3430                         public void exception(AsyncReadGraph graph, Throwable throwable) {
3431                                 procedure.exception(graph, throwable);
3432                         }
3433
3434                         @Override
3435                         public String toString() {
3436                                 return "forInverse -> " + procedure;
3437                         }
3438
3439                 });
3440
3441         }
3442
3443         @Override
3444         public void forInverse(Resource relation, SyncProcedure<Resource> procedure) {
3445                 forInverse(relation, new SyncToAsyncProcedure<Resource>(procedure));
3446         }
3447
3448         @Override
3449         public void forInverse(Resource relation, Procedure<Resource> procedure) {
3450                 forInverse(relation, new NoneToAsyncProcedure<Resource>(procedure));
3451         }
3452
3453         @Override
3454         public void forSingleObject(Resource subject, Resource relation,
3455                         AsyncListener<Resource> listener) {
3456                 asyncRequest(new SingleObject(subject, relation), listener);
3457         }
3458
3459         @Override
3460         public void forSingleObject(Resource subject, Resource relation,
3461                         SyncListener<Resource> listener) {
3462                 asyncRequest(new SingleObject(subject, relation), listener);
3463         }
3464
3465         @Override
3466         public void forSingleObject(Resource subject, Resource relation,
3467                         Listener<Resource> listener) {
3468                 asyncRequest(new SingleObject(subject, relation), listener);
3469         }
3470
3471         @Override
3472         final public void forSingleObject(final Resource subject,
3473                         final Resource relation, final AsyncProcedure<Resource> procedure) {
3474
3475                 assert (subject != null);
3476                 assert (relation != null);
3477                 assert (procedure != null);
3478
3479                 processor.forEachObject(this, subject, relation,
3480                                 new SingleOrErrorProcedure<Resource>(procedure));
3481
3482         }
3483
3484         @Override
3485         public void forSingleObject(Resource subject, Resource relation,
3486                         SyncProcedure<Resource> procedure) {
3487                 forSingleObject(subject, relation, new SyncToAsyncProcedure<Resource>(
3488                                 procedure));
3489         }
3490
3491         @Override
3492         public void forSingleObject(Resource subject, Resource relation,
3493                         Procedure<Resource> procedure) {
3494                 forSingleObject(subject, relation, new NoneToAsyncProcedure<Resource>(
3495                                 procedure));
3496         }
3497
3498         @Override
3499         public void forSingleStatement(Resource subject, Resource relation,
3500                         AsyncListener<Statement> listener) {
3501                 asyncRequest(new SingleStatement(subject, relation), listener);
3502         }
3503
3504         @Override
3505         public void forSingleStatement(Resource subject, Resource relation,
3506                         SyncListener<Statement> listener) {
3507                 asyncRequest(new SingleStatement(subject, relation), listener);
3508         }
3509
3510         @Override
3511         public void forSingleStatement(Resource subject, Resource relation,
3512                         Listener<Statement> listener) {
3513                 asyncRequest(new SingleStatement(subject, relation), listener);
3514         }
3515
3516         @Override
3517         final public void forSingleStatement(final Resource subject,
3518                         final Resource relation, final AsyncProcedure<Statement> procedure) {
3519
3520                 assert (subject != null);
3521                 assert (relation != null);
3522                 assert (procedure != null);
3523
3524                 processor.forEachStatement(this, subject, relation,
3525                                 new SingleOrErrorProcedure<Statement>(procedure));
3526
3527         }
3528
3529         @Override
3530         public void forSingleStatement(Resource subject, Resource relation,
3531                         SyncProcedure<Statement> procedure) {
3532                 forSingleStatement(subject, relation,
3533                                 new SyncToAsyncProcedure<Statement>(procedure));
3534         }
3535
3536         @Override
3537         public void forSingleStatement(Resource subject, Resource relation,
3538                         Procedure<Statement> procedure) {
3539                 forSingleStatement(subject, relation,
3540                                 new NoneToAsyncProcedure<Statement>(procedure));
3541         }
3542
3543         @Override
3544         public void forSingleType(Resource subject,
3545                         AsyncListener<Resource> listener) {
3546                 asyncRequest(new SingleTypeAny(subject), listener);
3547         }
3548
3549         @Override
3550         public void forSingleType(Resource subject,
3551                         SyncListener<Resource> listener) {
3552                 asyncRequest(new SingleTypeAny(subject), listener);
3553         }
3554
3555         @Override
3556         public void forSingleType(Resource subject,
3557                         Listener<Resource> listener) {
3558                 asyncRequest(new SingleTypeAny(subject), listener);
3559         }
3560
3561         @Override
3562         final public void forSingleType(final Resource subject, final AsyncProcedure<Resource> procedure) {
3563
3564                 assert (subject != null);
3565                 assert (procedure != null);
3566
3567                 final DeepSingleOrErrorProcedure<Resource> checkedProcedure = new DeepSingleOrErrorProcedure<Resource>(procedure);
3568
3569                 processor.forEachPrincipalType(this, subject, new AsyncMultiProcedureAdapter<Resource>() {
3570
3571                         @Override
3572                         public void execute(AsyncReadGraph graph, final Resource principalType) {
3573                                 checkedProcedure.offer(graph, principalType);
3574                         }
3575
3576                         @Override
3577                         public void finished(AsyncReadGraph graph) {
3578                                 checkedProcedure.dec(graph);
3579                         }
3580
3581                         @Override
3582                         public void exception(AsyncReadGraph graph, Throwable t) {
3583                                 checkedProcedure.exception(graph, t);
3584                         }
3585
3586                         @Override
3587                         public String toString() {
3588                                 return "forSingleType -> " + procedure;
3589                         }
3590
3591                 });
3592
3593         }
3594
3595         @Override
3596         public void forSingleType(Resource subject, SyncProcedure<Resource> procedure) {
3597                 forSingleType(subject, new SyncToAsyncProcedure<Resource>(
3598                                 procedure));
3599         }
3600
3601         @Override
3602         public void forSingleType(Resource subject, Procedure<Resource> procedure) {
3603                 forSingleType(subject, new NoneToAsyncProcedure<Resource>(
3604                                 procedure));
3605         }
3606
3607         @Override
3608         public void forSingleType(Resource subject, Resource relation,
3609                         AsyncListener<Resource> listener) {
3610                 asyncRequest(new SingleType(subject, relation), listener);
3611         }
3612
3613         @Override
3614         public void forSingleType(Resource subject, Resource relation,
3615                         SyncListener<Resource> listener) {
3616                 asyncRequest(new SingleType(subject, relation), listener);
3617         }
3618
3619         @Override
3620         public void forSingleType(Resource subject, Resource relation,
3621                         Listener<Resource> listener) {
3622                 asyncRequest(new SingleType(subject, relation), listener);
3623         }
3624
3625         @Override
3626         final public void forSingleType(final Resource subject,
3627                         final Resource baseType, final AsyncProcedure<Resource> procedure) {
3628
3629                 assert (subject != null);
3630                 assert (procedure != null);
3631
3632                 final DeepSingleOrErrorProcedure<Resource> checkedProcedure = new DeepSingleOrErrorProcedure<Resource>(procedure);
3633
3634                 processor.forEachPrincipalType(this, subject,
3635                                 new AsyncMultiProcedureAdapter<Resource>() {
3636
3637                                         @Override
3638                                         public void execute(AsyncReadGraph graph,
3639                                                         final Resource principalType) {
3640
3641                                                 checkedProcedure.inc();
3642
3643                                                 if(baseType == null) {
3644
3645                                                         checkedProcedure.offer(graph, principalType);
3646                                                         checkedProcedure.dec(graph);
3647
3648                                                 } else if(principalType.equals(baseType)) {
3649
3650                                                         checkedProcedure.offer(graph, principalType);
3651                                                         checkedProcedure.dec(graph);
3652
3653                                                 } else {
3654
3655                                                         processor.forSupertypes((ReadGraphImpl)graph, principalType,
3656                                                                         new AsyncProcedure<Set<Resource>>() {
3657
3658                                                                                 @Override
3659                                                                                 public void execute(
3660                                                                                                 AsyncReadGraph graph,
3661                                                                                                 Set<Resource> result) {
3662
3663                                                                                         if (result.contains(baseType))
3664                                                                                                 checkedProcedure.offer(graph,
3665                                                                                                                 principalType);
3666                                                                                         checkedProcedure.dec(graph);
3667
3668                                                                                 }
3669
3670                                                                                 @Override
3671                                                                                 public void exception(
3672                                                                                                 AsyncReadGraph graph,
3673                                                                                                 Throwable t) {
3674                                                                                         checkedProcedure
3675                                                                                                         .exception(graph, t);
3676                                                                                 }
3677
3678                                                                         });
3679
3680                                                 }
3681
3682                                         }
3683
3684                                         @Override
3685                                         public void finished(AsyncReadGraph graph) {
3686                                                 checkedProcedure.dec(graph);
3687                                         }
3688
3689                                         @Override
3690                                         public void exception(AsyncReadGraph graph, Throwable t) {
3691                                                 checkedProcedure.exception(graph, t);
3692                                         }
3693
3694                                         @Override
3695                                         public String toString() {
3696                                                 return "forSingleType -> " + procedure;
3697                                         }
3698
3699                                 });
3700
3701         }
3702
3703         @Override
3704         public void forSingleType(Resource subject, Resource relation,
3705                         SyncProcedure<Resource> procedure) {
3706                 forSingleType(subject, relation, new SyncToAsyncProcedure<Resource>(
3707                                 procedure));
3708         }
3709
3710         @Override
3711         public void forSingleType(Resource subject, Resource relation,
3712                         Procedure<Resource> procedure) {
3713                 forSingleType(subject, relation, new NoneToAsyncProcedure<Resource>(
3714                                 procedure));
3715         }
3716
3717         @Override
3718         public <T> void forValue(Resource subject, Binding binding,
3719                         AsyncListener<T> listener) {
3720                 asyncRequest(new Value<T>(subject, binding), listener);
3721         }
3722
3723         @Override
3724         public <T> void forValue(Resource subject, Binding binding,
3725                         SyncListener<T> listener) {
3726                 asyncRequest(new Value<T>(subject, binding), listener);
3727         }
3728
3729         @Override
3730         public <T> void forValue(Resource subject, Binding binding,
3731                         Listener<T> listener) {
3732                 asyncRequest(new Value<T>(subject, binding), listener);
3733         }
3734
3735         @Override
3736         public <T> void forValue(final Resource resource, final Binding binding,
3737                         final AsyncProcedure<T> procedure) {
3738
3739                 assert (resource != null);
3740                 assert (binding != null);
3741                 assert (procedure != null);
3742                 
3743                 processor.forValue(this, resource, new AsyncProcedure<byte[]>() {
3744
3745                         @Override
3746                         public void execute(AsyncReadGraph graph, byte[] result) {
3747                                 
3748                                 try {
3749
3750                                         if (result == null) {
3751                                                 procedure.exception(graph,
3752                                                                 new DoesNotContainValueException(
3753                                                                                 "No value for resource " + resource));
3754                                                 return;
3755                                         }
3756
3757                                         Serializer serializer = binding.serializer();
3758 //                                      Serializer serializer = Bindings.getSerializer( binding );
3759                                         Object obj = serializer.deserialize(result);
3760 //                                      if (!binding.isInstance(obj))
3761 //                                              procedure.exception(graph, new ClassCastException(
3762 //                                                              "Cannot get value " + obj + " with binding "
3763 //                                                                              + binding));
3764 //                                      else
3765                                                 procedure.execute(graph, (T) obj);
3766
3767                                 } catch (IOException e) {
3768                                         procedure.exception(graph, e);
3769                                 } catch (BufferUnderflowException e) {
3770                                         procedure.exception(graph, e);
3771                                 } catch (Throwable t) {
3772                                         procedure.exception(graph, t);
3773                                 }
3774
3775                         }
3776
3777                         @Override
3778                         public void exception(AsyncReadGraph graph, Throwable t) {
3779                                 try {
3780                                         procedure.exception(graph, t);
3781                                 } catch (Throwable t2) {
3782                                 Logger.defaultLogError(t2);
3783                                 }
3784                         }
3785
3786                         @Override
3787                         public String toString() {
3788                                 return "forValue -> " + procedure;
3789                         }
3790
3791                 });
3792
3793         }
3794
3795         @Override
3796         public <T> void forValue(Resource subject, Binding binding,
3797                         SyncProcedure<T> procedure) {
3798                 forValue(subject, binding, new SyncToAsyncProcedure<T>(procedure));
3799         }
3800
3801         @Override
3802         public <T> void forValue(Resource subject, Binding binding,
3803                         Procedure<T> procedure) {
3804                 forValue(subject, binding, new NoneToAsyncProcedure<T>(procedure));
3805         }
3806
3807         @Override
3808         public <T> void forValue(Resource subject, AsyncListener<T> listener) {
3809                 asyncRequest(new ValueImplied<T>(subject), listener);
3810         }
3811
3812         @Override
3813         public <T> void forValue(Resource subject, SyncListener<T> listener) {
3814                 asyncRequest(new ValueImplied<T>(subject), listener);
3815         }
3816
3817         @Override
3818         public <T> void forValue(Resource subject, Listener<T> listener) {
3819                 asyncRequest(new ValueImplied<T>(subject), listener);
3820         }
3821
3822         @Override
3823         final public <T> void forValue(final Resource subject, final AsyncProcedure<T> procedure) {
3824
3825                 assert (subject != null);
3826                 assert (procedure != null);
3827                 
3828                 forRelatedValue(subject, processor.getL0(this).HasDataType, DATA_TYPE_BINDING_INTERNAL, new AsyncProcedure<Datatype>() {
3829
3830                         @Override
3831                         public void execute(AsyncReadGraph graph, Datatype type) {
3832                                 // TODO: consider trying Bindings.getBeanBinding(type);
3833                                 Binding binding = Bindings.getBinding(type);
3834                                 graph.forValue(subject, binding, procedure);
3835                         }
3836
3837                         @Override
3838                         public void exception(AsyncReadGraph graph, Throwable throwable) {
3839                                 procedure.exception(graph, new DoesNotContainValueException("Invalid data type", throwable));
3840                         }
3841                         
3842                 });
3843
3844         }
3845
3846         @Override
3847         public <T> void forValue(Resource subject, SyncProcedure<T> procedure) {
3848                 forValue(subject, new SyncToAsyncProcedure<T>(procedure));
3849         }
3850
3851         @Override
3852         public <T> void forValue(Resource subject, Procedure<T> procedure) {
3853                 forValue(subject, new NoneToAsyncProcedure<T>(procedure));
3854         }
3855
3856         @Override
3857         public <T> void forRelatedValue(Resource subject, Resource relation,
3858                         AsyncListener<T> listener) {
3859                 asyncRequest(new RelatedValueImplied<T>(subject, relation), listener);
3860         }
3861
3862         @Override
3863         public <T> void forRelatedValue(Resource subject, Resource relation,
3864                         SyncListener<T> listener) {
3865                 asyncRequest(new RelatedValueImplied<T>(subject, relation), listener);
3866         }
3867
3868         @Override
3869         public <T> void forRelatedValue(Resource subject, Resource relation,
3870                         Listener<T> listener) {
3871                 asyncRequest(new RelatedValueImplied<T>(subject, relation), listener);
3872         }
3873
3874         @Override
3875         final public <T> void forRelatedValue(final Resource subject,
3876                         final Resource relation, final AsyncProcedure<T> procedure) {
3877
3878                 assert (subject != null);
3879                 assert (relation != null);
3880                 assert (procedure != null);
3881
3882                 final DeepSingleOrErrorProcedure<T> checkedProcedure = new DeepSingleOrErrorProcedure<T>(procedure);
3883
3884                 processor.forEachObject(this, subject, relation,
3885                                 new AsyncMultiProcedureAdapter<Resource>() {
3886
3887                                         @Override
3888                                         public void execute(AsyncReadGraph graph,
3889                                                         final Resource object) {
3890
3891                                                 checkedProcedure.inc();
3892
3893                                                 graph.forValue(object, new AsyncProcedure<Object>() {
3894
3895                                                         @Override
3896                                                         public void execute(AsyncReadGraph graph,
3897                                                                         Object result) {
3898                                                                 checkedProcedure.offer(graph, (T) result);
3899                                                                 checkedProcedure.dec(graph);
3900                                                         }
3901
3902                                                         @Override
3903                                                         public void exception(AsyncReadGraph graph,
3904                                                                         Throwable t) {
3905                                                                 checkedProcedure.exception(graph, t);
3906                                                         }
3907
3908                                                         @Override
3909                                                         public String toString() {
3910                                                                 return "forRelatedValue -> " + procedure;
3911                                                         }
3912
3913                                                 });
3914
3915                                         }
3916
3917                                         @Override
3918                                         public void finished(AsyncReadGraph graph) {
3919                                                 checkedProcedure.dec(graph);
3920                                         }
3921
3922                                         @Override
3923                                         public void exception(AsyncReadGraph graph, Throwable t) {
3924                                                 checkedProcedure.exception(graph, t);
3925                                         }
3926
3927                                 });
3928
3929         }
3930
3931         @Override
3932         public <T> void forRelatedValue(Resource subject, Resource relation,
3933                         SyncProcedure<T> procedure) {
3934                 forRelatedValue(subject, relation, new SyncToAsyncProcedure<T>(
3935                                 procedure));
3936         }
3937
3938         @Override
3939         public <T> void forRelatedValue(Resource subject, Resource relation,
3940                         Procedure<T> procedure) {
3941                 forRelatedValue(subject, relation, new NoneToAsyncProcedure<T>(
3942                                 procedure));
3943         }
3944
3945         @Override
3946         public <T> void forRelatedValue(Resource subject, Resource relation,
3947                         Binding binding, AsyncListener<T> listener) {
3948                 asyncRequest(new RelatedValue<T>(subject, relation, binding), listener);
3949         }
3950
3951         @Override
3952         public <T> void forRelatedValue(Resource subject, Resource relation,
3953                         Binding binding, SyncListener<T> listener) {
3954                 asyncRequest(new RelatedValue<T>(subject, relation, binding), listener);
3955         }
3956
3957         @Override
3958         public <T> void forRelatedValue(Resource subject, Resource relation,
3959                         Binding binding, Listener<T> listener) {
3960                 asyncRequest(new RelatedValue<T>(subject, relation, binding), listener);
3961         }
3962
3963         @Override
3964         final public <T> void forRelatedValue(final Resource subject,
3965                         final Resource relation, final Binding binding,
3966                         final AsyncProcedure<T> procedure) {
3967
3968                 assert (subject != null);
3969                 assert (relation != null);
3970                 assert (binding != null);
3971                 assert (procedure != null);
3972
3973                 final DeepSingleOrErrorProcedure<T> checkedProcedure = new DeepSingleOrErrorProcedure<T>(procedure);
3974                 
3975                 processor.forEachObject(this, subject, relation,
3976                                 new AsyncMultiProcedureAdapter<Resource>() {
3977
3978                                         @Override
3979                                         public void execute(AsyncReadGraph graph,
3980                                                         final Resource object) {
3981
3982                                                 checkedProcedure.inc();
3983
3984                                                 graph.forValue(object, binding, new AsyncProcedure<Object>() {
3985
3986                                                                         @Override
3987                                                                         public void execute(AsyncReadGraph graph,
3988                                                                                         Object result) {
3989                                                                                 
3990                                                                                 checkedProcedure.offer(graph,
3991                                                                                                 (T) result);
3992                                                                                 checkedProcedure.dec(graph);
3993                                                                         }
3994
3995                                                                         @Override
3996                                                                         public void exception(AsyncReadGraph graph,
3997                                                                                         Throwable t) {
3998                                                                                 checkedProcedure.exception(graph, t);
3999                                                                         }
4000
4001                                                                         @Override
4002                                                                         public String toString() {
4003                                                                                 return "forRelatedValue -> "
4004                                                                                                 + procedure;
4005                                                                         }
4006
4007                                                                 });
4008
4009                                         }
4010
4011                                         @Override
4012                                         public void finished(AsyncReadGraph graph) {
4013                                                 checkedProcedure.dec(graph);
4014                                         }
4015
4016                                         @Override
4017                                         public void exception(AsyncReadGraph graph, Throwable t) {
4018                                                 checkedProcedure.exception(graph, t);
4019                                         }
4020
4021                                 });
4022
4023         }
4024
4025         @Override
4026         public <T> void forRelatedValue(Resource subject, Resource relation,
4027                         Binding binding, SyncProcedure<T> procedure) {
4028                 forRelatedValue(subject, relation, binding,
4029                                 new SyncToAsyncProcedure<T>(procedure));
4030         }
4031
4032         @Override
4033         public <T> void forRelatedValue(Resource subject, Resource relation,
4034                         Binding binding, Procedure<T> procedure) {
4035                 forRelatedValue(subject, relation, binding,
4036                                 new NoneToAsyncProcedure<T>(procedure));
4037         }
4038
4039         @Override
4040         public <T> void forAdapted(Resource resource, Class<T> clazz,
4041                         AsyncListener<T> listener) {
4042                 asyncRequest(new Adapter<T>(resource, clazz), listener);
4043         }
4044
4045         @Override
4046         public <T> void forAdapted(Resource resource, Class<T> clazz,
4047                         SyncListener<T> listener) {
4048                 asyncRequest(new Adapter<T>(resource, clazz), listener);
4049         }
4050
4051         @Override
4052         public <T> void forAdapted(Resource resource, Class<T> clazz,
4053                         Listener<T> listener) {
4054                 asyncRequest(new Adapter<T>(resource, clazz), listener);
4055         }
4056
4057         @Override
4058         final public <T> void forAdapted(final Resource resource,
4059                         final Class<T> clazz, final AsyncProcedure<T> procedure) {
4060
4061                 assert (resource != null);
4062                 assert (clazz != null);
4063                 assert (procedure != null);
4064
4065                 final AdaptionService service = getSession().peekService(AdaptionService.class);
4066                 if (service == null)
4067                         procedure.exception(this, new ServiceException("No AdaptionService available")); 
4068                 else
4069                         service.adapt(this, resource, resource, Resource.class, clazz, false, procedure); 
4070
4071         }
4072
4073         @Override
4074         public <T> void forAdapted(Resource resource, Class<T> clazz,
4075                         SyncProcedure<T> procedure) {
4076                 forAdapted(resource, clazz, new SyncToAsyncProcedure<T>(procedure));
4077         }
4078
4079         @Override
4080         public <T> void forAdapted(Resource resource, Class<T> clazz,
4081                         Procedure<T> procedure) {
4082                 forAdapted(resource, clazz, new NoneToAsyncProcedure<T>(procedure));
4083         }
4084
4085         @Override
4086         public <T> void forUniqueAdapted(Resource resource, Class<T> clazz,
4087                         AsyncListener<T> listener) {
4088                 asyncRequest(new UniqueAdapter<T>(resource, clazz), listener);
4089         }
4090
4091         @Override
4092         public <T> void forUniqueAdapted(Resource resource, Class<T> clazz,
4093                         SyncListener<T> listener) {
4094                 asyncRequest(new UniqueAdapter<T>(resource, clazz), listener);
4095         }
4096
4097         @Override
4098         public <T> void forUniqueAdapted(Resource resource, Class<T> clazz,
4099                         Listener<T> listener) {
4100                 asyncRequest(new UniqueAdapter<T>(resource, clazz), listener);
4101         }
4102
4103         @Override
4104         final public <T> void forUniqueAdapted(final Resource resource,
4105                         final Class<T> clazz, final AsyncProcedure<T> procedure) {
4106
4107                 assert (resource != null);
4108                 assert (clazz != null);
4109                 assert (procedure != null);
4110
4111                 final AdaptionService service = getSession().peekService(AdaptionService.class);
4112                 if (service == null)
4113                         procedure.exception(this, new ServiceException("No AdaptionService available")); 
4114                 else
4115                         service.adaptNew(this, resource, clazz, false, procedure);
4116
4117         }
4118
4119         @Override
4120         public <T> void forUniqueAdapted(Resource resource, Class<T> clazz,
4121                         SyncProcedure<T> procedure) {
4122                 forUniqueAdapted(resource, clazz,
4123                                 new SyncToAsyncProcedure<T>(procedure));
4124         }
4125
4126         @Override
4127         public <T> void forUniqueAdapted(Resource resource, Class<T> clazz,
4128                         Procedure<T> procedure) {
4129                 forUniqueAdapted(resource, clazz,
4130                                 new NoneToAsyncProcedure<T>(procedure));
4131         }
4132
4133         @Override
4134         public void forPossibleInverse(Resource subject,
4135                         AsyncListener<Resource> listener) {
4136                 asyncRequest(new PossibleInverse(subject), listener);
4137         }
4138
4139         @Override
4140         public void forPossibleInverse(Resource subject,
4141                         SyncListener<Resource> listener) {
4142                 asyncRequest(new PossibleInverse(subject), listener);
4143         }
4144
4145         @Override
4146         public void forPossibleInverse(Resource subject, Listener<Resource> listener) {
4147                 asyncRequest(new PossibleInverse(subject), listener);
4148         }
4149
4150         @Override
4151         final public void forPossibleInverse(final Resource relation,
4152                         final AsyncProcedure<Resource> procedure) {
4153
4154                 assert (relation != null);
4155                 assert (procedure != null);
4156
4157                 processor.forInverse(this, relation, new ExceptionToNullProcedure<Resource>(procedure));
4158
4159         }
4160
4161         @Override
4162         public void forPossibleInverse(Resource subject,
4163                         SyncProcedure<Resource> procedure) {
4164                 forPossibleInverse(subject, new SyncToAsyncProcedure<Resource>(
4165                                 procedure));
4166         }
4167
4168         @Override
4169         public void forPossibleInverse(Resource subject,
4170                         Procedure<Resource> procedure) {
4171                 forPossibleInverse(subject, new NoneToAsyncProcedure<Resource>(
4172                                 procedure));
4173         }
4174
4175         @Override
4176         public void forPossibleObject(Resource subject, Resource relation,
4177                         AsyncListener<Resource> listener) {
4178                 asyncRequest(new PossibleObject(subject, relation), listener);
4179         }
4180
4181         @Override
4182         public void forPossibleObject(Resource subject, Resource relation,
4183                         SyncListener<Resource> listener) {
4184                 asyncRequest(new PossibleObject(subject, relation), listener);
4185         }
4186
4187         @Override
4188         public void forPossibleObject(Resource subject, Resource relation,
4189                         Listener<Resource> listener) {
4190                 asyncRequest(new PossibleObject(subject, relation), listener);
4191         }
4192
4193         @Override
4194         final public void forPossibleObject(final Resource subject,
4195                         final Resource relation, final AsyncProcedure<Resource> procedure) {
4196
4197                 assert (subject != null);
4198                 assert (relation != null);
4199                 assert (procedure != null);
4200
4201                 processor.forEachObject(this, subject, relation,
4202                                 new SingleOrNullProcedure<Resource>(procedure));
4203
4204         }
4205
4206         @Override
4207         public void forPossibleObject(Resource subject, Resource relation,
4208                         SyncProcedure<Resource> procedure) {
4209                 forPossibleObject(subject, relation,
4210                                 new SyncToAsyncProcedure<Resource>(procedure));
4211         }
4212
4213         @Override
4214         public void forPossibleObject(Resource subject, Resource relation,
4215                         Procedure<Resource> procedure) {
4216                 forPossibleObject(subject, relation,
4217                                 new NoneToAsyncProcedure<Resource>(procedure));
4218         }
4219
4220         @Override
4221         public void forPossibleStatement(Resource subject, Resource relation,
4222                         AsyncListener<Statement> listener) {
4223                 asyncRequest(new PossibleStatement(subject, relation), listener);
4224         }
4225
4226         @Override
4227         public void forPossibleStatement(Resource subject, Resource relation,
4228                         SyncListener<Statement> listener) {
4229                 asyncRequest(new PossibleStatement(subject, relation), listener);
4230         }
4231
4232         @Override
4233         public void forPossibleStatement(Resource subject, Resource relation,
4234                         Listener<Statement> listener) {
4235                 asyncRequest(new PossibleStatement(subject, relation), listener);
4236         }
4237
4238         @Override
4239         final public void forPossibleStatement(final Resource subject,
4240                         final Resource relation, final AsyncProcedure<Statement> procedure) {
4241
4242                 assert (subject != null);
4243                 assert (relation != null);
4244                 assert (procedure != null);
4245
4246                 processor.forEachStatement(this, subject, relation,
4247                                 new SingleFunctionalOrNullProcedure<Statement>(
4248                                                 "forPossibleStatement", procedure));
4249
4250         }
4251
4252         @Override
4253         public void forPossibleStatement(Resource subject, Resource relation,
4254                         SyncProcedure<Statement> procedure) {
4255                 forPossibleStatement(subject, relation,
4256                                 new SyncToAsyncProcedure<Statement>(procedure));
4257         }
4258
4259         @Override
4260         public void forPossibleStatement(Resource subject, Resource relation,
4261                         Procedure<Statement> procedure) {
4262                 forPossibleStatement(subject, relation,
4263                                 new NoneToAsyncProcedure<Statement>(procedure));
4264         }
4265
4266         @Override
4267         public void forPossibleType(Resource subject, Resource relation,
4268                         AsyncListener<Resource> listener) {
4269                 asyncRequest(new PossibleType(subject, relation), listener);
4270         }
4271
4272         @Override
4273         public void forPossibleType(Resource subject, Resource relation,
4274                         SyncListener<Resource> listener) {
4275                 asyncRequest(new PossibleType(subject, relation), listener);
4276         }
4277
4278         @Override
4279         public void forPossibleType(Resource subject, Resource relation,
4280                         Listener<Resource> listener) {
4281                 asyncRequest(new PossibleType(subject, relation), listener);
4282         }
4283
4284         @Override
4285         final public void forPossibleType(final Resource subject,
4286                         final Resource baseType, final AsyncProcedure<Resource> procedure) {
4287
4288                 assert (subject != null);
4289                 assert (procedure != null);
4290
4291                 final NullSingleOrNullProcedure<Resource> checkedProcedure = new NullSingleOrNullProcedure<Resource>(procedure);
4292
4293                 processor.forEachPrincipalType(this, subject, new AsyncMultiProcedureAdapter<Resource>() {
4294
4295                                         @Override
4296                                         public void execute(AsyncReadGraph graph,
4297                                                         final Resource principalType) {
4298
4299                                                 if (baseType == null) {
4300
4301                                                         checkedProcedure.offer(graph, principalType);
4302
4303                                                 } else if (principalType.equals(baseType)) {
4304
4305                                                         checkedProcedure.offer(graph, principalType);
4306
4307                                                 } else {
4308
4309                                                         checkedProcedure.inc();
4310
4311                                                         processor.forSupertypes((ReadGraphImpl)graph, principalType,
4312                                                                         new AsyncProcedure<Set<Resource>>() {
4313
4314                                                                                 @Override
4315                                                                                 public void execute(
4316                                                                                                 AsyncReadGraph graph,
4317                                                                                                 Set<Resource> result) {
4318
4319                                                                                         if (result.contains(baseType)) {
4320                                                                                                 checkedProcedure.offer(graph,
4321                                                                                                                 principalType);
4322                                                                                         }
4323
4324                                                                                         checkedProcedure.dec(graph);
4325
4326                                                                                 }
4327
4328                                                                                 @Override
4329                                                                                 public void exception(
4330                                                                                                 AsyncReadGraph graph,
4331                                                                                                 Throwable t) {
4332                                                                                         checkedProcedure.exception(graph, t);
4333                                                                                         checkedProcedure.dec(graph);
4334                                                                                 }
4335
4336                                                                                 @Override
4337                                                                                 public String toString() {
4338                                                                                         return "forPossibleType -> "
4339                                                                                                         + procedure;
4340                                                                                 }
4341
4342                                                                         });
4343
4344                                                 }
4345
4346                                         }
4347
4348                                         @Override
4349                                         public void finished(AsyncReadGraph graph) {
4350                                                 checkedProcedure.dec(graph);
4351                                         }
4352
4353                                         @Override
4354                                         public void exception(AsyncReadGraph graph, Throwable t) {
4355                                                 checkedProcedure.exception(graph, t);
4356                                                 checkedProcedure.dec(graph);
4357                                         }
4358
4359                                 });
4360
4361         }
4362
4363         @Override
4364         public void forPossibleType(Resource subject, Resource relation,
4365                         SyncProcedure<Resource> procedure) {
4366                 forPossibleType(subject, relation, new SyncToAsyncProcedure<Resource>(
4367                                 procedure));
4368         }
4369
4370         @Override
4371         public void forPossibleType(Resource subject, Resource relation,
4372                         Procedure<Resource> procedure) {
4373                 forPossibleType(subject, relation, new NoneToAsyncProcedure<Resource>(
4374                                 procedure));
4375         }
4376
4377         @Override
4378         public <T> void forPossibleValue(Resource subject, AsyncListener<T> listener) {
4379                 asyncRequest(new PossibleValueImplied<T>(subject), listener);
4380         }
4381
4382         @Override
4383         public <T> void forPossibleValue(Resource subject, SyncListener<T> listener) {
4384                 asyncRequest(new PossibleValueImplied<T>(subject), listener);
4385         }
4386
4387         @Override
4388         public <T> void forPossibleValue(Resource subject, Listener<T> listener) {
4389                 asyncRequest(new PossibleValueImplied<T>(subject), listener);
4390         }
4391
4392         @Override
4393         final public <T> void forPossibleValue(final Resource subject,
4394                         final AsyncProcedure<T> procedure) {
4395
4396                 assert (subject != null);
4397                 assert (procedure != null);
4398                 
4399                 forPossibleRelatedValue(subject, processor.getL0(this).HasDataType, DATA_TYPE_BINDING_INTERNAL, new AsyncProcedure<Datatype>() {
4400
4401                         @Override
4402                         public void execute(AsyncReadGraph graph, final Datatype type) {
4403                                 if (type == null) {
4404                                         procedure.execute(graph, null);
4405                                 } else {
4406                                         try {
4407                                                 // TODO: consider trying Bindings.getBeanBinding(type);
4408                                                 Binding binding = Bindings.getBinding(type);
4409                                                 graph.forPossibleValue(subject, binding, procedure);
4410                                         } catch (RuntimeBindingConstructionException e) {
4411                                                 procedure.exception(graph, e);
4412                                         }
4413                                 }
4414                         }
4415
4416                         @Override
4417                         public void exception(AsyncReadGraph graph, Throwable t) {
4418                                 procedure.exception(graph, t);
4419                         }
4420
4421                         @Override
4422                         public String toString() {
4423                                 return "forPossibleValue -> " + procedure;
4424                         }
4425
4426                 });
4427
4428         }
4429
4430         @Override
4431         public <T> void forPossibleValue(Resource subject,
4432                         SyncProcedure<T> procedure) {
4433                 forPossibleValue(subject, new SyncToAsyncProcedure<T>(procedure));
4434         }
4435
4436         @Override
4437         public <T> void forPossibleValue(Resource subject, Procedure<T> procedure) {
4438                 forPossibleValue(subject, new NoneToAsyncProcedure<T>(procedure));
4439         }
4440
4441         @Override
4442         public <T> void forPossibleValue(Resource subject, Binding binding,
4443                         AsyncListener<T> listener) {
4444                 asyncRequest(new PossibleValue<T>(subject, binding), listener);
4445         }
4446
4447         @Override
4448         public <T> void forPossibleValue(Resource subject, Binding binding,
4449                         SyncListener<T> listener) {
4450                 asyncRequest(new PossibleValue<T>(subject, binding), listener);
4451         }
4452
4453         @Override
4454         public <T> void forPossibleValue(Resource subject, Binding binding,
4455                         Listener<T> listener) {
4456                 asyncRequest(new PossibleValue<T>(subject, binding), listener);
4457         }
4458
4459         @Override
4460         final public <T> void forPossibleValue(final Resource resource,
4461                         final Binding binding, final AsyncProcedure<T> procedure) {
4462
4463                 assert (resource != null);
4464                 assert (binding != null);
4465                 assert (procedure != null);
4466
4467                 processor.forValue(this, resource, new AsyncProcedure<byte[]>() {
4468
4469                         @Override
4470                         public void execute(AsyncReadGraph graph, byte[] result) {
4471
4472                                 try {
4473
4474                                         if (result == null) {
4475                                                 procedure.execute(graph, null);
4476                                                 return;
4477                                         }
4478
4479                                         Serializer serializer = Bindings.getSerializer( binding );
4480                                         Object obj = serializer.deserialize(result);
4481                                         if (!binding.isInstance(obj))
4482                                                 procedure.exception(graph, new ClassCastException(
4483                                                                 "Cannot get value " + obj + " with binding "
4484                                                                                 + binding));
4485                                         else
4486                                                 procedure.execute(graph, (T) obj);
4487
4488                                 } catch (IOException e) {
4489                                         procedure.exception(graph, e);
4490                                 } catch (BufferUnderflowException e) {
4491                                         procedure.exception(graph, e);
4492                                 } catch (Throwable t) {
4493                                         procedure.exception(graph, t);
4494                                 }
4495
4496                         }
4497
4498                         @Override
4499                         public void exception(AsyncReadGraph graph, Throwable t) {
4500                                 try {
4501                                         procedure.exception(graph, t);
4502                                 } catch (Throwable t2) {
4503                                 Logger.defaultLogError(t2);
4504                                 }
4505                         }
4506
4507                         @Override
4508                         public String toString() {
4509                                 return "forPossibleValue -> " + procedure;
4510                         }
4511
4512                 });
4513
4514         }
4515
4516         @Override
4517         public <T> void forPossibleValue(Resource subject, Binding binding,
4518                         SyncProcedure<T> procedure) {
4519                 forPossibleValue(subject, binding, new SyncToAsyncProcedure<T>(
4520                                 procedure));
4521         }
4522
4523         @Override
4524         public <T> void forPossibleValue(Resource subject, Binding binding,
4525                         Procedure<T> procedure) {
4526                 forPossibleValue(subject, binding, new NoneToAsyncProcedure<T>(
4527                                 procedure));
4528         }
4529
4530         @Override
4531         public <T> void forPossibleRelatedValue(Resource subject,
4532                         Resource relation, AsyncListener<T> listener) {
4533                 asyncRequest(new PossibleRelatedValueImplied<T>(subject, relation),
4534                                 listener);
4535         }
4536
4537         @Override
4538         public <T> void forPossibleRelatedValue(Resource subject,
4539                         Resource relation, SyncListener<T> listener) {
4540                 asyncRequest(new PossibleRelatedValueImplied<T>(subject, relation),
4541                                 listener);
4542         }
4543
4544         @Override
4545         public <T> void forPossibleRelatedValue(Resource subject,
4546                         Resource relation, Listener<T> listener) {
4547                 asyncRequest(new PossibleRelatedValueImplied<T>(subject, relation),
4548                                 listener);
4549         }
4550
4551         @Override
4552         final public <T> void forPossibleRelatedValue(final Resource subject,
4553                         final Resource relation, final AsyncProcedure<T> procedure) {
4554
4555                 assert (subject != null);
4556                 assert (relation != null);
4557                 assert (procedure != null);
4558
4559                 final DeepSingleOrNullProcedure<T> checkedProcedure = new DeepSingleOrNullProcedure<T>(procedure);
4560                 
4561                 processor.forEachObject(this, subject, relation,
4562                                 new AsyncMultiProcedureAdapter<Resource>() {
4563
4564                                         @Override
4565                                         public void execute(AsyncReadGraph graph,
4566                                                         final Resource object) {
4567
4568                                                 checkedProcedure.inc();
4569
4570                                                 graph.forValue(object, new AsyncProcedure<Object>() {
4571
4572                                                         @Override
4573                                                         public void execute(AsyncReadGraph graph,
4574                                                                         Object result) {
4575                                                                 checkedProcedure.offer(graph, (T) result);
4576                                                                 checkedProcedure.dec(graph);
4577                                                         }
4578
4579                                                         @Override
4580                                                         public void exception(AsyncReadGraph graph,
4581                                                                         Throwable t) {
4582                                                                 checkedProcedure.exception(graph, t);
4583                                                                 checkedProcedure.dec(graph);
4584                                                         }
4585
4586                                                 });
4587
4588                                         }
4589
4590                                         @Override
4591                                         public void finished(AsyncReadGraph graph) {
4592
4593                                                 checkedProcedure.dec(graph);
4594                                         }
4595
4596                                         @Override
4597                                         public void exception(AsyncReadGraph graph, Throwable t) {
4598                                                 checkedProcedure.exception(graph, t);
4599                                                 checkedProcedure.dec(graph);
4600                                         }
4601
4602                                         @Override
4603                                         public String toString() {
4604                                                 return "forPossibleRelatedValue -> " + procedure;
4605                                         }
4606                                 });
4607
4608         }
4609
4610         @Override
4611         public <T> void forPossibleRelatedValue(Resource subject,
4612                         Resource relation, SyncProcedure<T> procedure) {
4613                 forPossibleRelatedValue(subject, relation, new SyncToAsyncProcedure<T>(
4614                                 procedure));
4615         }
4616
4617         @Override
4618         public <T> void forPossibleRelatedValue(Resource subject,
4619                         Resource relation, Procedure<T> procedure) {
4620                 forPossibleRelatedValue(subject, relation, new NoneToAsyncProcedure<T>(
4621                                 procedure));
4622         }
4623
4624         @Override
4625         public <T> void forPossibleRelatedValue(Resource subject,
4626                         Resource relation, Binding binding, AsyncListener<T> listener) {
4627                 asyncRequest(new PossibleRelatedValue<T>(subject, relation, binding),
4628                                 listener);
4629         }
4630
4631         @Override
4632         public <T> void forPossibleRelatedValue(Resource subject,
4633                         Resource relation, Binding binding, SyncListener<T> listener) {
4634                 asyncRequest(new PossibleRelatedValue<T>(subject, relation, binding),
4635                                 listener);
4636         }
4637
4638         @Override
4639         public <T> void forPossibleRelatedValue(Resource subject,
4640                         Resource relation, Binding binding, Listener<T> listener) {
4641                 asyncRequest(new PossibleRelatedValue<T>(subject, relation, binding),
4642                                 listener);
4643         }
4644
4645 //      @Override
4646 //      final public <T> void forPossibleRelatedValue(final Resource subject, final Resource relation, final Binding binding,
4647 //                      final AsyncProcedure<T> procedure) {
4648 //              
4649 //              forPossibleRelatedValue(subject, relation, binding, procedure, false);
4650 //              
4651 //      }
4652
4653         final public <T> void forPossibleRelatedValue(final Resource subject, final Resource relation, final Binding binding,
4654                         final AsyncProcedure<T> procedure) {
4655
4656                 assert (subject != null);
4657                 assert (relation != null);
4658                 assert (procedure != null);
4659
4660                 processor.forPossibleObject(this, subject, relation, new AsyncProcedure<Resource>() {
4661                         
4662                         @Override
4663                         public void execute(AsyncReadGraph graph, Resource object) {
4664                                 
4665                                 if(object == null) {
4666                                         procedure.execute(graph, null);
4667                                         return;
4668                                 }
4669
4670                                 processor.forPossibleValue((ReadGraphImpl)graph, object, new AsyncProcedure<byte[]>() {
4671
4672                                         @Override
4673                                         public void execute(AsyncReadGraph graph, byte[] bytes) {
4674
4675                                                 if(bytes != null) {
4676
4677                                                         try {
4678                                                         
4679                                                                 Serializer serializer = binding.serializer();
4680                                                                 Object obj = serializer.deserialize(bytes);
4681                                                                 if (!binding.isInstance(obj)) {
4682                                                                         procedure.exception(graph, new ClassCastException("Cannot get value " + obj + " with binding " + binding));
4683                                                                 } else {
4684                                                                         procedure.execute(graph, (T) obj);
4685                                                                 }
4686
4687                                                         } catch (Throwable t) {
4688                                                                 
4689                                                                 procedure.exception(graph, t);
4690                                                                 
4691                                                         }
4692                                                         
4693                                                 } else {
4694                                                         
4695                                                         procedure.execute(graph, null);
4696                                                         
4697                                                 }
4698                                                 
4699                                         }
4700
4701                                         @Override
4702                                         public void exception(AsyncReadGraph graph, Throwable t) {
4703                                                 procedure.exception(graph, t);
4704                                         }
4705
4706                                 });
4707                                 
4708                         }
4709                         
4710                         @Override
4711                         public void exception(AsyncReadGraph graph, Throwable throwable) {
4712                                 throwable.printStackTrace();
4713                                 procedure.exception(graph, throwable);
4714                         }
4715                         
4716                 });
4717
4718         }
4719
4720         @Override
4721         public <T> void forPossibleRelatedValue(Resource subject,
4722                         Resource relation, Binding binding, SyncProcedure<T> procedure) {
4723                 forPossibleRelatedValue(subject, relation, binding,
4724                                 new SyncToAsyncProcedure<T>(procedure));
4725         }
4726
4727         @Override
4728         public <T> void forPossibleRelatedValue(Resource subject,
4729                         Resource relation, Binding binding, Procedure<T> procedure) {
4730                 forPossibleRelatedValue(subject, relation, binding,
4731                                 new NoneToAsyncProcedure<T>(procedure));
4732         }
4733
4734         @Override
4735         public void forIsInstanceOf(Resource subject, Resource relation,
4736                         AsyncListener<Boolean> listener) {
4737                 asyncRequest(new IsInstanceOf(subject, relation), listener);
4738         }
4739
4740         @Override
4741         public void forIsInstanceOf(Resource subject, Resource relation,
4742                         SyncListener<Boolean> listener) {
4743                 asyncRequest(new IsInstanceOf(subject, relation), listener);
4744         }
4745
4746         @Override
4747         public void forIsInstanceOf(Resource subject, Resource relation,
4748                         Listener<Boolean> listener) {
4749                 asyncRequest(new IsInstanceOf(subject, relation), listener);
4750         }
4751
4752         @Override
4753         final public void forIsInstanceOf(final Resource resource,
4754                         final Resource type, final AsyncProcedure<Boolean> procedure) {
4755
4756                 assert (resource != null);
4757                 assert (type != null);
4758                 assert (procedure != null);
4759
4760                 forTypes(resource, new AsyncProcedure<Set<Resource>>() {
4761
4762                         @Override
4763                         public void execute(AsyncReadGraph graph, Set<Resource> result) {
4764                                 
4765                                 try {
4766                                         if (result.contains(type))
4767                                                 procedure.execute(graph, true);
4768                                         else
4769                                                 procedure.execute(graph, false);
4770                                 } catch (Throwable t) {
4771                                 Logger.defaultLogError(t);
4772                                 }
4773                         }
4774
4775                         @Override
4776                         public void exception(AsyncReadGraph graph, Throwable t) {
4777                                 try {
4778                                         procedure.exception(graph, t);
4779                                 } catch (Throwable t2) {
4780                                 Logger.defaultLogError(t2);
4781                                 }
4782                         }
4783
4784                         @Override
4785                         public String toString() {
4786                                 return "forIsInstanceOf -> " + procedure;
4787                         }
4788
4789                 });
4790
4791         }
4792
4793         @Override
4794         public void forIsInstanceOf(Resource subject, Resource relation,
4795                         SyncProcedure<Boolean> procedure) {
4796                 forIsInstanceOf(subject, relation, new SyncToAsyncProcedure<Boolean>(
4797                                 procedure));
4798         }
4799
4800         @Override
4801         public void forIsInstanceOf(Resource subject, Resource relation,
4802                         Procedure<Boolean> procedure) {
4803                 forIsInstanceOf(subject, relation, new NoneToAsyncProcedure<Boolean>(
4804                                 procedure));
4805         }
4806
4807         @Override
4808         public void forIsInheritedFrom(Resource subject, Resource relation,
4809                         AsyncListener<Boolean> listener) {
4810                 asyncRequest(new IsInheritedFrom(subject, relation), listener);
4811         }
4812
4813         @Override
4814         public void forIsInheritedFrom(Resource subject, Resource relation,
4815                         SyncListener<Boolean> listener) {
4816                 asyncRequest(new IsInheritedFrom(subject, relation), listener);
4817         }
4818
4819         @Override
4820         public void forIsInheritedFrom(Resource subject, Resource relation,
4821                         Listener<Boolean> listener) {
4822                 asyncRequest(new IsInheritedFrom(subject, relation), listener);
4823         }
4824
4825         @Override
4826         final public void forIsInheritedFrom(final Resource resource,
4827                         final Resource type, final AsyncProcedure<Boolean> procedure) {
4828
4829                 assert (resource != null);
4830                 assert (type != null);
4831                 assert (procedure != null);
4832
4833                 if (resource.equals(type)) {
4834                         try {
4835                                 procedure.execute(this, true);
4836                         } catch (Throwable t) {
4837                         Logger.defaultLogError(t);
4838                         }
4839                         return;
4840                 }
4841
4842                 forSupertypes(resource, new AsyncProcedure<Set<Resource>>() {
4843
4844                         @Override
4845                         public void execute(AsyncReadGraph graph, Set<Resource> result) {
4846                                 try {
4847                                         if (result.contains(type))
4848                                                 procedure.execute(graph, true);
4849                                         else
4850                                                 procedure.execute(graph, false);
4851                                 } catch (Throwable t) {
4852                                 Logger.defaultLogError(t);
4853                                 }
4854                         }
4855
4856                         @Override
4857                         public void exception(AsyncReadGraph graph, Throwable t) {
4858                                 try {
4859                                         procedure.exception(graph, t);
4860                                 } catch (Throwable t2) {
4861                                 Logger.defaultLogError(t2);
4862                                 }
4863                         }
4864
4865                         @Override
4866                         public String toString() {
4867                                 return "forIsInheritedFrom -> " + procedure;
4868                         }
4869
4870                 });
4871
4872         }
4873
4874         @Override
4875         public void forIsInheritedFrom(Resource subject, Resource relation,
4876                         SyncProcedure<Boolean> procedure) {
4877                 forIsInheritedFrom(subject, relation,
4878                                 new SyncToAsyncProcedure<Boolean>(procedure));
4879         }
4880
4881         @Override
4882         public void forIsInheritedFrom(Resource subject, Resource relation,
4883                         Procedure<Boolean> procedure) {
4884                 forIsInheritedFrom(subject, relation,
4885                                 new NoneToAsyncProcedure<Boolean>(procedure));
4886         }
4887
4888         @Override
4889         public void forIsSubrelationOf(Resource subject, Resource relation,
4890                         AsyncListener<Boolean> listener) {
4891                 asyncRequest(new IsSubrelationOf(subject, relation), listener);
4892         }
4893
4894         @Override
4895         public void forIsSubrelationOf(Resource subject, Resource relation,
4896                         SyncListener<Boolean> listener) {
4897                 asyncRequest(new IsSubrelationOf(subject, relation), listener);
4898         }
4899
4900         @Override
4901         public void forIsSubrelationOf(Resource subject, Resource relation,
4902                         Listener<Boolean> listener) {
4903                 asyncRequest(new IsSubrelationOf(subject, relation), listener);
4904         }
4905
4906         @Override
4907         final public void forIsSubrelationOf(final Resource resource,
4908                         final Resource relation, final AsyncProcedure<Boolean> procedure) {
4909
4910                 assert (resource != null);
4911                 assert (relation != null);
4912                 assert (procedure != null);
4913
4914                 if (resource.equals(relation)) {
4915                         procedure.execute(this, true);
4916                         return;
4917                 }
4918
4919                 forSuperrelations(resource, new AsyncProcedure<Set<Resource>>() {
4920
4921                         @Override
4922                         public void execute(AsyncReadGraph graph, Set<Resource> result) {
4923                                 try {
4924                                         if (result.contains(relation))
4925                                                 procedure.execute(graph, true);
4926                                         else
4927                                                 procedure.execute(graph, false);
4928                                 } catch (Throwable t) {
4929                                 Logger.defaultLogError(t);
4930                                 }
4931                         }
4932
4933                         @Override
4934                         public void exception(AsyncReadGraph graph, Throwable t) {
4935                                 try {
4936                                         procedure.exception(graph, t);
4937                                 } catch (Throwable t2) {
4938                                 Logger.defaultLogError(t2);
4939                                 }
4940                         }
4941
4942                         @Override
4943                         public String toString() {
4944                                 return "forIsSubrelationOf -> " + procedure;
4945                         }
4946
4947                 });
4948
4949         }
4950
4951         @Override
4952         public void forIsSubrelationOf(Resource subject, Resource relation,
4953                         SyncProcedure<Boolean> procedure) {
4954                 forIsSubrelationOf(subject, relation,
4955                                 new SyncToAsyncProcedure<Boolean>(procedure));
4956         }
4957
4958         @Override
4959         public void forIsSubrelationOf(Resource subject, Resource relation,
4960                         Procedure<Boolean> procedure) {
4961                 forIsSubrelationOf(subject, relation,
4962                                 new NoneToAsyncProcedure<Boolean>(procedure));
4963         }
4964
4965         @Override
4966         public void forHasStatement(Resource subject,
4967                         AsyncListener<Boolean> listener) {
4968                 asyncRequest(new HasStatementSubject(subject), listener);
4969         }
4970
4971         @Override
4972         public void forHasStatement(Resource subject, SyncListener<Boolean> listener) {
4973                 asyncRequest(new HasStatementSubject(subject), listener);
4974         }
4975
4976         @Override
4977         public void forHasStatement(Resource subject, Listener<Boolean> listener) {
4978                 asyncRequest(new HasStatementSubject(subject), listener);
4979         }
4980
4981         @Override
4982         final public void forHasStatement(final Resource subject,
4983                         final AsyncProcedure<Boolean> procedure) {
4984
4985                 assert (subject != null);
4986                 assert (procedure != null);
4987
4988                 processor.forHasStatement(this, subject, procedure);
4989
4990         }
4991
4992         @Override
4993         public void forHasStatement(Resource subject,
4994                         SyncProcedure<Boolean> procedure) {
4995                 forHasStatement(subject, new SyncToAsyncProcedure<Boolean>(procedure));
4996         }
4997
4998         @Override
4999         public void forHasStatement(Resource subject, Procedure<Boolean> procedure) {
5000                 forHasStatement(subject, new NoneToAsyncProcedure<Boolean>(procedure));
5001         }
5002
5003         @Override
5004         public void forHasStatement(Resource subject, Resource relation,
5005                         AsyncListener<Boolean> listener) {
5006                 asyncRequest(new HasStatement(subject, relation), listener);
5007         }
5008
5009         @Override
5010         public void forHasStatement(Resource subject, Resource relation,
5011                         SyncListener<Boolean> listener) {
5012                 asyncRequest(new HasStatement(subject, relation), listener);
5013         }
5014
5015         @Override
5016         public void forHasStatement(Resource subject, Resource relation,
5017                         Listener<Boolean> listener) {
5018                 asyncRequest(new HasStatement(subject, relation), listener);
5019         }
5020
5021         @Override
5022         final public void forHasStatement(final Resource subject,
5023                         final Resource relation, final AsyncProcedure<Boolean> procedure) {
5024
5025                 assert (subject != null);
5026                 assert (relation != null);
5027                 assert (procedure != null);
5028
5029                 processor.forHasStatement(this, subject, relation, procedure);
5030
5031         }
5032
5033         @Override
5034         public void forHasStatement(Resource subject, Resource relation,
5035                         SyncProcedure<Boolean> procedure) {
5036                 forHasStatement(subject, relation, new SyncToAsyncProcedure<Boolean>(
5037                                 procedure));
5038         }
5039
5040         @Override
5041         public void forHasStatement(Resource subject, Resource relation,
5042                         Procedure<Boolean> procedure) {
5043                 forHasStatement(subject, relation, new NoneToAsyncProcedure<Boolean>(
5044                                 procedure));
5045         }
5046
5047         @Override
5048         public void forHasStatement(Resource subject, Resource relation,
5049                         Resource object, AsyncListener<Boolean> listener) {
5050                 asyncRequest(new HasStatementSubjectObject(subject, relation, object),
5051                                 listener);
5052         }
5053
5054         @Override
5055         public void forHasStatement(Resource subject, Resource relation,
5056                         Resource object, SyncListener<Boolean> listener) {
5057                 asyncRequest(new HasStatementSubjectObject(subject, relation, object),
5058                                 listener);
5059         }
5060
5061         @Override
5062         public void forHasStatement(Resource subject, Resource relation,
5063                         Resource object, Listener<Boolean> listener) {
5064                 asyncRequest(new HasStatementSubjectObject(subject, relation, object),
5065                                 listener);
5066         }
5067
5068         @Override
5069         final public void forHasStatement(final Resource subject,
5070                         final Resource relation, final Resource object,
5071                         final AsyncProcedure<Boolean> procedure) {
5072
5073                 assert (subject != null);
5074                 assert (relation != null);
5075                 assert (object != null);
5076                 assert (procedure != null);
5077
5078                 processor.forHasStatement(this, subject, relation, object, procedure);
5079
5080         }
5081
5082         @Override
5083         public void forHasStatement(Resource subject, Resource relation,
5084                         Resource object, SyncProcedure<Boolean> procedure) {
5085                 forHasStatement(subject, relation, object,
5086                                 new SyncToAsyncProcedure<Boolean>(procedure));
5087         }
5088
5089         @Override
5090         public void forHasStatement(Resource subject, Resource relation,
5091                         Resource object, Procedure<Boolean> procedure) {
5092                 forHasStatement(subject, relation, object,
5093                                 new NoneToAsyncProcedure<Boolean>(procedure));
5094         }
5095
5096         @Override
5097         public void forHasValue(Resource subject, AsyncListener<Boolean> listener) {
5098                 asyncRequest(new HasValue(subject), listener);
5099         }
5100
5101         @Override
5102         public void forHasValue(Resource subject, SyncListener<Boolean> listener) {
5103                 asyncRequest(new HasValue(subject), listener);
5104         }
5105
5106         @Override
5107         public void forHasValue(Resource subject, Listener<Boolean> listener) {
5108                 asyncRequest(new HasValue(subject), listener);
5109         }
5110
5111         @Override
5112         final public void forHasValue(final Resource subject,
5113                         final AsyncProcedure<Boolean> procedure) {
5114
5115                 assert (subject != null);
5116                 assert (procedure != null);
5117
5118                 processor.forValue(this, subject, new AsyncProcedure<byte[]>() {
5119
5120                         @Override
5121                         public void execute(AsyncReadGraph graph, byte[] result) {
5122                                 try {
5123                                         if (result == null)
5124                                                 procedure.execute(graph, false);
5125                                         else
5126                                                 procedure.execute(graph, true);
5127                                 } catch (Throwable t) {
5128                                 Logger.defaultLogError(t);
5129                                 }
5130                         }
5131
5132                         @Override
5133                         public void exception(AsyncReadGraph graph, Throwable t) {
5134                                 try {
5135                                         procedure.exception(graph, t);
5136                                 } catch (Throwable t2) {
5137                                 Logger.defaultLogError(t2);
5138                                 }
5139                         }
5140
5141                         @Override
5142                         public String toString() {
5143                                 return "forHasValue -> " + procedure;
5144                         }
5145
5146                 });
5147
5148         }
5149
5150         @Override
5151         public void forHasValue(Resource subject, SyncProcedure<Boolean> procedure) {
5152                 forHasValue(subject, new SyncToAsyncProcedure<Boolean>(procedure));
5153         }
5154
5155         @Override
5156         public void forHasValue(Resource subject, Procedure<Boolean> procedure) {
5157                 forHasValue(subject, new NoneToAsyncProcedure<Boolean>(procedure));
5158         }
5159
5160         @Override
5161         public void forOrderedSet(Resource subject,
5162                         AsyncMultiListener<Resource> listener) {
5163                 asyncRequest(new OrderedSet(subject), listener);
5164         }
5165
5166         @Override
5167         public void forOrderedSet(Resource subject,
5168                         SyncMultiListener<Resource> listener) {
5169                 asyncRequest(new OrderedSet(subject), listener);
5170         }
5171
5172         @Override
5173         public void forOrderedSet(Resource subject, MultiListener<Resource> listener) {
5174                 asyncRequest(new OrderedSet(subject), listener);
5175         }
5176
5177         @Override
5178         final public void forOrderedSet(final Resource subject,
5179                         final AsyncMultiProcedure<Resource> procedure) {
5180
5181                 assert (subject != null);
5182                 assert (procedure != null);
5183
5184                 processor.forOrderedSet(this, subject,
5185                                 new AsyncMultiProcedure<Resource>() {
5186
5187                                         @Override
5188                                         public void finished(AsyncReadGraph graph) {
5189                                                 try {
5190                                                         procedure.finished(graph);
5191                                                 } catch (Throwable t) {
5192                                                 Logger.defaultLogError(t);
5193                                                 }
5194                                         }
5195
5196                                         @Override
5197                                         public void execute(AsyncReadGraph graph, Resource result) {
5198                                                 try {
5199                                                         procedure.execute(graph, result);
5200                                                 } catch (Throwable t) {
5201                                                 Logger.defaultLogError(t);
5202                                                 }
5203                                         }
5204
5205                                         @Override
5206                                         public void exception(AsyncReadGraph graph, Throwable t) {
5207                                                 try {
5208                                                         procedure.exception(graph, t);
5209                                                 } catch (Throwable t2) {
5210                                                 Logger.defaultLogError(t2);
5211                                                 }
5212                                         }
5213
5214                                         @Override
5215                                         public String toString() {
5216                                                 return "forOrderedSet -> " + procedure;
5217                                         }
5218
5219                                 });
5220
5221         }
5222
5223         @Override
5224         public void forOrderedSet(Resource subject,
5225                         SyncMultiProcedure<Resource> procedure) {
5226                 forOrderedSet(subject, new SyncToAsyncMultiProcedure<Resource>(
5227                                 procedure));
5228         }
5229
5230         @Override
5231         public void forOrderedSet(Resource subject,
5232                         MultiProcedure<Resource> procedure) {
5233                 forOrderedSet(subject, new NoneToAsyncMultiProcedure<Resource>(
5234                                 procedure));
5235         }
5236
5237         @Override
5238         public <T> void forPossibleAdapted(Resource resource, Class<T> clazz,
5239                         AsyncListener<T> listener) {
5240                 asyncRequest(new PossibleAdapter<T>(resource, clazz), listener);
5241         }
5242
5243         @Override
5244         public <T> void forPossibleAdapted(Resource resource, Class<T> clazz,
5245                         SyncListener<T> listener) {
5246                 asyncRequest(new PossibleAdapter<T>(resource, clazz), listener);
5247         }
5248
5249         @Override
5250         public <T> void forPossibleAdapted(Resource resource, Class<T> clazz,
5251                         Listener<T> listener) {
5252                 asyncRequest(new PossibleAdapter<T>(resource, clazz), listener);
5253         }
5254
5255         @Override
5256         final public <T> void forPossibleAdapted(final Resource resource,
5257                         final Class<T> clazz, final AsyncProcedure<T> procedure) {
5258
5259                 assert (resource != null);
5260                 assert (clazz != null);
5261                 assert (procedure != null);
5262
5263                 final AdaptionService service = getSession().peekService(AdaptionService.class);
5264                 if (service == null)
5265                         procedure.exception(this, new ServiceException("No AdaptionService available")); 
5266                 else
5267                         service.adapt(this, resource, resource, Resource.class, clazz, true, procedure);
5268         }
5269
5270         @Override
5271         public <T> void forPossibleAdapted(Resource resource, Class<T> clazz,
5272                         SyncProcedure<T> procedure) {
5273                 forPossibleAdapted(resource, clazz, new SyncToAsyncProcedure<T>(
5274                                 procedure));
5275         }
5276
5277         @Override
5278         public <T> void forPossibleAdapted(Resource resource, Class<T> clazz,
5279                         Procedure<T> procedure) {
5280                 forPossibleAdapted(resource, clazz, new NoneToAsyncProcedure<T>(
5281                                 procedure));
5282         }
5283
5284         @Override
5285         public <T> void forPossibleUniqueAdapted(Resource resource, Class<T> clazz,
5286                         AsyncListener<T> listener) {
5287                 asyncRequest(new PossibleUniqueAdapter<T>(resource, clazz), listener);
5288         }
5289
5290         @Override
5291         public <T> void forPossibleUniqueAdapted(Resource resource, Class<T> clazz,
5292                         SyncListener<T> listener) {
5293                 asyncRequest(new PossibleUniqueAdapter<T>(resource, clazz), listener);
5294         }
5295
5296         @Override
5297         public <T> void forPossibleUniqueAdapted(Resource resource, Class<T> clazz,
5298                         Listener<T> listener) {
5299                 asyncRequest(new PossibleUniqueAdapter<T>(resource, clazz), listener);
5300         }
5301
5302         @Override
5303         final public <T> void forPossibleUniqueAdapted(final Resource resource,
5304                         final Class<T> clazz, final AsyncProcedure<T> procedure) {
5305
5306                 assert (resource != null);
5307                 assert (clazz != null);
5308                 assert (procedure != null);
5309
5310                 final AdaptionService service = getSession().peekService(AdaptionService.class);
5311                 if (service == null)
5312                         procedure.exception(this, new ServiceException("No AdaptionService available")); 
5313                 else
5314                         service.adaptNew(this, resource, clazz, true, procedure);
5315
5316         }
5317
5318         @Override
5319         public <T> void forPossibleUniqueAdapted(Resource resource, Class<T> clazz,
5320                         SyncProcedure<T> procedure) {
5321                 forPossibleUniqueAdapted(resource, clazz, new SyncToAsyncProcedure<T>(
5322                                 procedure));
5323         }
5324
5325         @Override
5326         public <T> void forPossibleUniqueAdapted(Resource resource, Class<T> clazz,
5327                         Procedure<T> procedure) {
5328                 forPossibleUniqueAdapted(resource, clazz, new NoneToAsyncProcedure<T>(
5329                                 procedure));
5330         }
5331
5332         /*
5333          * Implementation of the interface AsyncRequestProcessor
5334          */
5335
5336         @Override
5337         final public Session getSession() {
5338                 return processor.getSession();
5339         }
5340
5341 //      @Override
5342 //      final public Builtins getBuiltins() {
5343 //              return processor.getSession().getBuiltins();
5344 //      }
5345
5346         @Override
5347         public <T> void asyncRequest(final Read<T> request) {
5348
5349                 asyncRequest(request, new AsyncProcedure<T>() {
5350
5351                         @Override
5352                         public void execute(AsyncReadGraph graph, T result) {
5353                         }
5354
5355                         @Override
5356                         public void exception(AsyncReadGraph graph, Throwable t) {
5357                                 Logger.defaultLogError(t);
5358                         }
5359
5360                         @Override
5361                         public String toString() {
5362                                 return "asyncRequest(Read) -> " + request;
5363                         }
5364
5365                 });
5366
5367         }
5368
5369         @Override
5370         public <T> void asyncRequest(Read<T> request, AsyncListener<T> procedure) {
5371                 asyncRequest(request, (AsyncProcedure<T>) procedure);
5372         }
5373
5374         @Override
5375         public <T> void asyncRequest(Read<T> request,
5376                         final SyncListener<T> procedure) {
5377                 asyncRequest(request, new SyncToAsyncListener<T>(procedure));
5378         }
5379
5380         @Override
5381         public <T> void asyncRequest(Read<T> request, final Listener<T> procedure) {
5382                 asyncRequest(request, new NoneToAsyncListener<T>(procedure));
5383         }
5384
5385         @Override
5386         public <T> void asyncRequest(final Read<T> request, final AsyncProcedure<T> procedure) {
5387
5388                 assert (request != null);
5389                 assert (procedure != null);
5390
5391                 final ListenerBase listener = getListenerBase(procedure);
5392
5393                 if (parent != null || listener != null) {
5394
5395                         try {
5396                                 QueryCache.runnerReadEntry(this, request, parent, listener, procedure);
5397                                 //processor.query(this, request, parent, procedure,listener);
5398                         } catch (DatabaseException e) {
5399                                 Logger.defaultLogError(e);
5400                                 // This throwable has already been transferred to procedure at this point - do nothing about it
5401                                 //
5402                         }
5403                         
5404                 } else {
5405
5406 //                      final ReadGraphImpl newGraph = newSync();
5407
5408                         try {
5409
5410                                 T result = request.perform(this);
5411                                 
5412                                 try {
5413                                         procedure.execute(this, result);
5414                                 } catch (Throwable t) {
5415                                         Logger.defaultLogError(t);
5416                                 }
5417
5418                         } catch (Throwable t) {
5419
5420                                 try {
5421                                         procedure.exception(this, t);
5422                                 } catch (Throwable t2) {
5423                                         Logger.defaultLogError(t2);
5424                                 }
5425
5426                         } finally {
5427
5428                         }
5429
5430                 }
5431
5432         }
5433
5434     public static ReadGraphImpl createAsync(QueryProcessor support) {
5435         return new ReadGraphImpl(null, support);
5436     }
5437
5438     public static ReadGraphImpl forRecompute(CacheEntry entry, QueryProcessor support) {
5439         return new ReadGraphImpl(entry, support);       
5440     }
5441
5442         @Override
5443         public <T> void asyncRequest(Read<T> request, SyncProcedure<T> procedure) {
5444                 asyncRequest(request, new SyncToAsyncProcedure<T>(procedure));
5445         }
5446
5447         @Override
5448         public <T> void asyncRequest(Read<T> request, final Procedure<T> procedure) {
5449                 asyncRequest(request, new NoneToAsyncProcedure<T>(procedure));
5450         }
5451
5452         @Override
5453         final public <T> void asyncRequest(final AsyncRead<T> request) {
5454
5455                 assert (request != null);
5456
5457                 asyncRequest(request, new AsyncProcedure<T>() {
5458
5459                         @Override
5460                         public void execute(AsyncReadGraph graph, T result) {
5461                         }
5462
5463                         @Override
5464                         public void exception(AsyncReadGraph graph, Throwable t) {
5465                         Logger.defaultLogError(t);
5466                         }
5467
5468                         @Override
5469                         public String toString() {
5470                                 return "asyncRequest(AsyncRead) -> " + request;
5471                         }
5472
5473                 });
5474
5475         }
5476
5477         @Override
5478         public <T> void asyncRequest(AsyncRead<T> request,
5479                         AsyncListener<T> procedure) {
5480                 asyncRequest(request, (AsyncProcedure<T>) procedure);
5481         }
5482
5483         @Override
5484         final public <T> void asyncRequest(AsyncRead<T> request,
5485                         final SyncListener<T> procedure) {
5486                 asyncRequest(request, new SyncToAsyncListener<T>(procedure));
5487         }
5488
5489         @Override
5490         final public <T> void asyncRequest(AsyncRead<T> request,
5491                         final Listener<T> procedure) {
5492                 asyncRequest(request, new NoneToAsyncListener<T>(procedure));
5493         }
5494
5495         @Override
5496         final public <T> void asyncRequest(final AsyncRead<T> request,
5497                         final AsyncProcedure<T> procedure) {
5498
5499                 assert (request != null);
5500                 assert (procedure != null);
5501
5502                 final ListenerBase listener = getListenerBase(procedure);
5503
5504                 if (parent != null || listener != null) {
5505
5506                         try {
5507                                 QueryCache.runnerAsyncReadEntry(this, request, parent, listener, procedure);
5508                                 //processor.query(this, request, parent, procedure, listener);
5509                         } catch (DatabaseException e) {
5510                                 Logger.defaultLogError(e);
5511                         }
5512
5513                 } else {
5514
5515                         try {
5516                                 
5517                                 request.perform(this, new CallWrappedSingleQueryProcedure4<T>(procedure, request));
5518
5519                         } catch (Throwable t) {
5520
5521                                 if (t instanceof DatabaseException)
5522                                         procedure.exception(this, t);
5523                                 else
5524                                         procedure
5525                                                         .exception(
5526                                                                         this,
5527                                                                         new DatabaseException(
5528                                                                                         "Unexpected exception in ReadGraph.asyncRequest(SingleAsyncRead, SingleProcedure)",
5529                                                                                         t));
5530
5531                         }
5532
5533                 }
5534
5535         }
5536
5537         @Override
5538         public <T> void asyncRequest(AsyncRead<T> request,
5539                         SyncProcedure<T> procedure) {
5540                 asyncRequest(request, new SyncToAsyncProcedure<T>(procedure));
5541         }
5542
5543         @Override
5544         final public <T> void asyncRequest(final AsyncRead<T> request,
5545                         final Procedure<T> procedure) {
5546                 asyncRequest(request, new NoneToAsyncProcedure<T>(procedure));
5547         }
5548
5549         @Override
5550         public <T> void asyncRequest(final MultiRead<T> request) {
5551
5552                 assert (request != null);
5553
5554                 asyncRequest(request, new AsyncMultiProcedureAdapter<T>() {
5555                         @Override
5556                         public void exception(AsyncReadGraph graph, Throwable t) {
5557                         Logger.defaultLogError(t);
5558                         }
5559
5560                         @Override
5561                         public String toString() {
5562                                 return "asyncRequest(MultiRead) -> " + request;
5563                         }
5564                 });
5565
5566         }
5567
5568         @Override
5569         public <T> void asyncRequest(MultiRead<T> request,
5570                         AsyncMultiListener<T> procedure) {
5571                 asyncRequest(request, (AsyncMultiProcedure<T>) procedure);
5572         }
5573
5574         @Override
5575         public <T> void asyncRequest(MultiRead<T> request,
5576                         SyncMultiListener<T> procedure) {
5577                 asyncRequest(request, new SyncToAsyncMultiListener<T>(procedure));
5578         }
5579
5580         @Override
5581         public <T> void asyncRequest(MultiRead<T> request,
5582                         MultiListener<T> procedure) {
5583                 asyncRequest(request, new NoneToAsyncMultiListener<T>(procedure));
5584         }
5585
5586         @Override
5587         public <T> void asyncRequest(final MultiRead<T> request,
5588                         final AsyncMultiProcedure<T> procedure) {
5589
5590                 assert (request != null);
5591                 assert (procedure != null);
5592
5593                 final ListenerBase listener = getListenerBase(procedure);
5594
5595                 if (parent != null || listener != null) {
5596
5597 //                  final ReadGraphImpl newGraph = newSync();
5598                     processor.query(this, request, parent, procedure,listener);
5599
5600                 } else {
5601
5602 //                  final ReadGraphImpl newGraph = newSync();
5603
5604                     try {
5605
5606                         request.perform(this, procedure);
5607
5608                     } catch (Throwable t) {
5609
5610                         procedure.exception(this, t);
5611
5612                     }                           
5613
5614                 }
5615
5616         }
5617
5618         @Override
5619         public <T> void asyncRequest(MultiRead<T> request,
5620                         SyncMultiProcedure<T> procedure) {
5621                 asyncRequest(request, new SyncToAsyncMultiProcedure<T>(procedure));
5622         }
5623
5624         @Override
5625         public <T> void asyncRequest(MultiRead<T> request,
5626                         MultiProcedure<T> procedure) {
5627                 asyncRequest(request, new NoneToAsyncMultiProcedure<T>(procedure));
5628         }
5629
5630         @Override
5631         final public <T> void asyncRequest(final AsyncMultiRead<T> request) {
5632
5633                 assert (request != null);
5634
5635                 asyncRequest(request, new AsyncMultiProcedureAdapter<T>() {
5636                         @Override
5637                         public void exception(AsyncReadGraph graph, Throwable t) {
5638                         Logger.defaultLogError(t);
5639                         }
5640
5641                         @Override
5642                         public String toString() {
5643                                 return "asyncRequest(AsyncMultiRead) -> " + request;
5644                         }
5645                 });
5646
5647         }
5648
5649         @Override
5650         public <T> void asyncRequest(AsyncMultiRead<T> request,
5651                         AsyncMultiListener<T> procedure) {
5652                 asyncRequest(request, (AsyncMultiProcedure<T>) procedure);
5653         }
5654
5655         @Override
5656         public <T> void asyncRequest(AsyncMultiRead<T> request,
5657                         SyncMultiListener<T> procedure) {
5658                 asyncRequest(request, new SyncToAsyncMultiListener<T>(procedure));
5659         }
5660
5661         @Override
5662         public <T> void asyncRequest(AsyncMultiRead<T> request,
5663                         MultiListener<T> procedure) {
5664                 asyncRequest(request, new NoneToAsyncMultiListener<T>(procedure));
5665         }
5666
5667         @Override
5668         final public <T> void asyncRequest(AsyncMultiRead<T> request,
5669                         final AsyncMultiProcedure<T> procedure) {
5670
5671                 assert (request != null);
5672                 assert (procedure != null);
5673
5674                 ListenerBase listener = getListenerBase(procedure);
5675
5676                 if (parent != null || listener != null) {
5677
5678                         processor.query(this, request, parent, procedure, listener);
5679
5680                 } else {
5681
5682                         try {
5683
5684                                 request.perform(this, new AsyncMultiProcedure<T>() {
5685
5686                                         @Override
5687                                         public void execute(AsyncReadGraph graph, T result) {
5688                                                 procedure.execute(graph, result);
5689                                         }
5690
5691                                         @Override
5692                                         public void finished(AsyncReadGraph graph) {
5693                                                 procedure.finished(graph);
5694                                         }
5695
5696                                         @Override
5697                                         public void exception(AsyncReadGraph graph, Throwable t) {
5698                                                 procedure.exception(graph, t);
5699                                         }
5700
5701                                         @Override
5702                                         public String toString() {
5703                                                 return "asyncRequest(AsyncMultiRead) -> " + procedure;
5704                                         }
5705
5706                                 });
5707
5708                         } catch (Throwable t) {
5709
5710                                 procedure.exception(this, new DatabaseException(t));
5711
5712                         }
5713                 }
5714
5715         }
5716
5717         @Override
5718         public <T> void asyncRequest(AsyncMultiRead<T> request,
5719                         SyncMultiProcedure<T> procedure) {
5720                 asyncRequest(request, new SyncToAsyncMultiProcedure<T>(procedure));
5721         }
5722
5723         @Override
5724         final public <T> void asyncRequest(AsyncMultiRead<T> request,
5725                         final MultiProcedure<T> procedure) {
5726                 asyncRequest(request, new NoneToAsyncMultiProcedure<T>(procedure));
5727         }
5728
5729         @Override
5730         final public <T> void asyncRequest(final ExternalRead<T> request) {
5731
5732                 assert (request != null);
5733
5734                 asyncRequest(request, new Procedure<T>() {
5735
5736                         @Override
5737                         public void execute(T result) {
5738                         }
5739
5740                         @Override
5741                         public void exception(Throwable t) {
5742                         Logger.defaultLogError(t);
5743                         }
5744
5745                         @Override
5746                         public String toString() {
5747                                 return "asyncRequest(PrimitiveRead) -> " + request;
5748                         }
5749
5750                 });
5751
5752         }
5753
5754         @Override
5755         public <T> void asyncRequest(ExternalRead<T> request,
5756                         final Listener<T> procedure) {
5757                 asyncRequest(request, (Procedure<T>) procedure);
5758         }
5759
5760         @Override
5761         final public <T> void asyncRequest(final ExternalRead<T> request,
5762                         final Procedure<T> procedure) {
5763
5764                 assert (request != null);
5765                 assert (procedure != null);
5766
5767                 ListenerBase listener = getListenerBase(procedure);
5768
5769                 if (parent != null || listener != null) {
5770
5771                         processor.query(this, request, parent, procedure, listener);
5772
5773                 } else {
5774
5775                         try {
5776
5777                                 request.register(this, new Listener<T>() {
5778
5779                                         @Override
5780                                         public void execute(T result) {
5781                                                 procedure.execute(result);
5782                                         }
5783
5784                                         @Override
5785                                         public void exception(Throwable t) {
5786                                                 procedure.exception(t);
5787                                         }
5788
5789                                         @Override
5790                                         public String toString() {
5791                                                 return "asyncRequest(PrimitiveRead) -> " + request;
5792                                         }
5793
5794                                         @Override
5795                                         public boolean isDisposed() {
5796                                                 return true;
5797                                         }
5798
5799                                 });
5800
5801                         } catch (Throwable t) {
5802
5803                                 if (t instanceof DatabaseException)
5804                                         procedure.exception(t);
5805                                 else
5806                                         procedure
5807                                                         .exception(new DatabaseException(
5808                                                                         "Unexpected exception in ReadGraph.asyncRequest(SingleAsyncRead, SingleProcedure)",
5809                                                                         t));
5810
5811                         }
5812
5813                 }
5814
5815         }
5816
5817         @Override
5818         public void asyncRequest(final Write request) {
5819
5820                 assert (request != null);
5821                 
5822                 getSession().asyncRequest(request);
5823
5824 //              processor.asyncWrite(request);
5825
5826         }
5827
5828         @Override
5829         public <T> void asyncRequest(final WriteResult<T> request, Procedure<T> procedure) {
5830                 throw new Error("Not implemented.");
5831         }
5832         
5833         @Override
5834         public void asyncRequest(Write request, Consumer<DatabaseException> callback) {
5835                 
5836                 assert (request != null);
5837                 
5838                 getSession().asyncRequest(request, callback);
5839                 
5840         }
5841
5842         @Override
5843         public void asyncRequest(final DelayedWrite request) {
5844
5845                 assert (request != null);
5846
5847                 getSession().asyncRequest(request);
5848
5849         }
5850
5851         @Override
5852         public <T> void asyncRequest(final DelayedWriteResult<T> request, Procedure<T> procedure) {
5853                 throw new Error("Not implemented.");
5854         }
5855         
5856         @Override
5857         public void asyncRequest(DelayedWrite r,
5858                         Consumer<DatabaseException> callback) {
5859                 throw new Error("Not implemented.");
5860         }
5861
5862         @Override
5863         public void asyncRequest(final WriteOnly request) {
5864
5865                 assert (request != null);
5866
5867                 getSession().asyncRequest(request);
5868
5869         }
5870
5871         @Override
5872         public <T> void asyncRequest(final WriteOnlyResult<T> request, Procedure<T> procedure) {
5873                 throw new Error("Not implemented.");
5874         }
5875         
5876         @Override
5877         public void asyncRequest(WriteOnly r, Consumer<DatabaseException> callback) {
5878                 throw new Error("Not implemented.");
5879         }
5880
5881         /*
5882          * Implementation of the interface ServiceLocator
5883          */
5884
5885         @Override
5886         public <T> T getService(Class<T> api) {
5887             if(WriteSupport.class == api) {
5888                 if(this instanceof WriteGraphImpl) {
5889                     WriteGraphImpl impl = (WriteGraphImpl)this;
5890                     return (T)impl.writeSupport;
5891                 }
5892             }
5893                 return getSession().getService(api);
5894         }
5895
5896         @Override
5897         public <T> T peekService(Class<T> api) {
5898                 return getSession().peekService(api);
5899         }
5900
5901         @Override
5902         public boolean hasService(Class<?> api) {
5903                 return getSession().hasService(api);
5904         }
5905
5906         @Override
5907         public <T> void registerService(Class<T> api, T service) {
5908                 getSession().registerService(api, service);
5909         }
5910         
5911         @Override
5912         public boolean isImmutable(Resource resource) throws DatabaseException {
5913                 ResourceImpl impl = (ResourceImpl)resource;
5914                 return processor.isImmutable(impl.id);
5915         }
5916
5917         /*
5918          * Internal routines
5919          */
5920
5921         protected static String INTERNAL_ERROR_STRING = "Transaction aborted due to internal client error. Contact application support.";
5922
5923         /*
5924          * callerThread is the currently running thread state.syncThread is blocking for
5925          * this execution state.syncParent is the blocking request
5926          */
5927
5928         final private boolean isExternal(int thread) {
5929                 return thread == Integer.MIN_VALUE;
5930         }
5931
5932 //      final private boolean isSync(int thread) {
5933 //              return thread < -1 && thread > Integer.MIN_VALUE;
5934 //      }
5935
5936         ReadGraphImpl(ReadGraphImpl graph) {
5937                 this(graph.parent, graph.processor);
5938         }
5939
5940         ReadGraphImpl(CacheEntry parent, QueryProcessor support) {
5941 //              this.state = new ReadGraphState(barrier, support);
5942                 this.parent = parent;
5943                 this.processor = support;
5944         }
5945         
5946         ReadGraphImpl(final QueryProcessor support) {
5947                 
5948 //              this.state = state;
5949                 this.processor = support;
5950                 this.parent = null;
5951                 
5952         }
5953
5954 //      public static ReadGraphImpl createSync(int syncThread, Object syncParent,
5955 //                      ReadGraphSupportImpl support) {
5956 //              return new ReadGraphImpl(syncThread, syncThread, syncParent, null,
5957 //                              support, new AsyncBarrierImpl(null));
5958 //      }
5959
5960         public static ReadGraphImpl create(QueryProcessor support) {
5961                 return new ReadGraphImpl(support);
5962         }
5963
5964 //      public ReadGraphImpl newAsync() {
5965 //              return this;
5966 ////            if(!state.synchronizedExecution) {
5967 ////                    return this;
5968 ////            } else {
5969 ////                    return new ReadGraphImpl(false, parent, state.support, state.barrier);
5970 ////            }
5971 //      }
5972
5973 //      public ReadGraphImpl newSync() {
5974 //              return new ReadGraphImpl(parent, processor);
5975 //      }
5976
5977         public ReadGraphImpl newSync(CacheEntry parentEntry) {
5978                 return new ReadGraphImpl(parentEntry, processor);
5979         }
5980
5981         public ReadGraphImpl newRestart(ReadGraphImpl impl) {
5982
5983                 WriteGraphImpl write = processor.getSession().getService(
5984                                 WriteGraphImpl.class);
5985
5986 //              if (write.callerThread != impl.callerThread)
5987 //                      return new WriteGraphImpl(impl.callerThread, parent, state.support, write.writeSupport, write.provider, write.state.barrier);
5988                 return write;
5989
5990         }
5991
5992 //      public ReadGraphImpl newSync(Object parentRequest) {
5993 //              return new ReadGraphImpl(callerThread, state.parent, state.support, new AsyncBarrierImpl(state.barrier));
5994 //      }
5995
5996 //      public ReadGraphImpl newSync(final int callerThread, Object parentRequest) {
5997 //              assert (state.syncThread == callerThread || (state.syncThread == Integer.MIN_VALUE && callerThread != Integer.MIN_VALUE));
5998 //              return new ReadGraphImpl(callerThread, callerThread, parentRequest,
5999 //                              state.parent, state.support, new AsyncBarrierImpl(state.barrier));
6000 //      }
6001 //
6002 //      public ReadGraphImpl newSyncAsync(Object parentRequest) {
6003 ////            assert (callerThread < 0);
6004 //              return new ReadGraphImpl(callerThread, state.syncThread, parentRequest,
6005 //                              state.parent, state.support, new AsyncBarrierImpl(state.barrier));
6006 //      }
6007 //
6008 //      public ReadGraphImpl newSyncAsync(final int callerThread,
6009 //                      Object parentRequest) {
6010 ////            assert (callerThread < 0);
6011 //              // assert(state.syncThread == callerThread || (state.syncThread == Integer.MIN_VALUE
6012 //              // && callerThread != Integer.MIN_VALUE) );
6013 //              return new ReadGraphImpl(callerThread, callerThread, parentRequest,
6014 //                              state.parent, state.support, new AsyncBarrierImpl(state.barrier));
6015 //      }
6016
6017         public ReadGraphImpl withAsyncParent(CacheEntry parent) {
6018                 return new ReadGraphImpl(parent, processor);
6019         }
6020
6021         public ReadGraphImpl withParent(CacheEntry parent) {
6022                 if(parent == this.parent) return this;
6023                 else return new ReadGraphImpl(parent, processor);
6024         }
6025
6026         final private ListenerBase getListenerBase(final Object procedure) {
6027                 if (procedure instanceof ListenerBase)
6028                         return (ListenerBase) procedure;
6029                 else
6030                         return null;
6031         }
6032
6033         public <T> void waitAsyncProcedure(AsyncMultiReadProcedure<T> procedure) {
6034                 
6035                 assert(procedure.done());
6036                 
6037 //              while (!procedure.done()) {
6038 //
6039 //                      boolean executed = processor.resumeTasks(callerThread, null, null);
6040 //                      if (!executed) {
6041 //                              try {
6042 //                                      Thread.sleep(1);
6043 //                                      //                                                              sema.tryAcquire(1, TimeUnit.MILLISECONDS);
6044 //                              } catch (InterruptedException e) {
6045 //                                      e.printStackTrace();
6046 //                              }
6047 //                      }
6048 //
6049 //              }
6050                 
6051         }
6052
6053         public <T> void waitAsyncProcedure(AsyncReadProcedure<T> procedure) {
6054                 
6055                 assert(procedure.done());
6056                 
6057 //              while (!procedure.done()) {
6058 //
6059 //                      boolean executed = processor.processor.resume(this);
6060 //                      if (!executed) {
6061 //                              try {
6062 //                                      Thread.sleep(1);
6063 //                                      //                                                              sema.tryAcquire(1, TimeUnit.MILLISECONDS);
6064 //                              } catch (InterruptedException e) {
6065 //                                      e.printStackTrace();
6066 //                              }
6067 //                      }
6068 //
6069 //              }
6070                 
6071         }
6072         
6073 //      public void waitAsync(Object request) {
6074 //              try {
6075 //                      state.barrier.waitBarrier(request, this);
6076 //              } catch (Throwable t) {
6077 //                      t.printStackTrace();
6078 //                      processor.scanPending();
6079 //                      processor.querySupport.checkTasks();
6080 //                      throw new RuntimeDatabaseException(t);
6081 //              }
6082 //      }
6083
6084 //      public void restart() {
6085 //              state.barrier.restart();
6086 //      }
6087
6088         public boolean resumeTasks() {
6089                 return processor.resumeTasks(this);
6090         }
6091
6092         Class<?> singleClass(Set<Resource> types) {
6093                 Class<?> result = null;
6094                 for (Resource type : types) {
6095                         Class<?> clazz = processor.getBuiltinValue(type);
6096                         if (clazz != null) {
6097                                 if (result != null)
6098                                         return null;
6099                                 else
6100                                         result = clazz;
6101                         }
6102                 }
6103                 return result;
6104         }
6105
6106         private String debugString(Resource r) {
6107                 String name = null;
6108                 try {
6109                         name = getPossibleRelatedValue(r, processor.getL0(this).HasName);
6110                 } catch (ManyObjectsForFunctionalRelationException e) {
6111                 Logger.defaultLogError(e);
6112                 } catch (ServiceException e) {
6113                 Logger.defaultLogError(e);
6114                 }
6115                 return "[" + name + " - " + r + "]";
6116         }
6117
6118         @Override
6119         public String toString() {
6120                 return "ReadGraphImpl[thread=" + Thread.currentThread() + "]";
6121         }
6122
6123         @Override
6124         final public int thread() {
6125                 return 0;
6126         }
6127         
6128     static class MultiTripleIntProcedure implements TripleIntProcedure {
6129
6130         final private AsyncMultiProcedure<Statement> procedure;
6131         final private ReadGraphImpl impl;
6132         final private QuerySupport support;
6133         
6134         public MultiTripleIntProcedure(AsyncMultiProcedure<Statement> procedure, ReadGraphImpl impl, QuerySupport support) {
6135                 this.procedure = procedure;
6136                 this.impl = impl;
6137                 this.support = support;
6138         }
6139         
6140         @Override
6141         public void execute(ReadGraphImpl graph, int s, int p, int o) {
6142                 try {
6143                         procedure.execute(graph, support.getStatement(s, p, o));
6144                 } catch (Throwable t2) {
6145                         Logger.defaultLogError(t2);
6146                 }
6147         }
6148
6149         @Override
6150         public void finished(ReadGraphImpl graph) {
6151                 try {
6152                         procedure.finished(graph);
6153 //                      impl.state.barrier.dec("ReadGraphSupportImpl.516");
6154                 } catch (Throwable t2) {
6155                         Logger.defaultLogError(t2);
6156                 }
6157         }
6158
6159         @Override
6160         public void exception(ReadGraphImpl graph, Throwable t) {
6161                 try {
6162                         procedure.exception(graph, t);
6163                 } catch (Throwable t2) {
6164                         Logger.defaultLogError(t2);
6165                 }
6166 //              impl.state.barrier.dec("ReadGraphSupportImpl.516");
6167         }
6168
6169         @Override
6170         public String toString() {
6171                 return "forEachObject with " + procedure;
6172         }
6173         
6174     }
6175
6176 //    private AsyncMultiProcedure<Resource> cacheKey = null;
6177 //    private MultiIntProcedure cacheResult = null;
6178 //    
6179 //    final IntProcedure forMultiProcedure(final AsyncMultiProcedure<Resource> procedure) {
6180 //      
6181 //      if(procedure == cacheKey) return cacheResult; 
6182 //      
6183 //      cacheResult = new MultiIntProcedure(procedure, this, processor.support);
6184 //      cacheKey = procedure;
6185 //      
6186 //      return cacheResult;
6187 //      
6188 //    }
6189 //
6190 //    private AsyncMultiProcedure<Statement> cacheKey2 = null;
6191 //    private MultiTripleIntProcedure cacheResult2 = null;
6192 //
6193 //    final synchronized TripleIntProcedure forMultiProcedure(final AsyncMultiProcedure<Statement> procedure) {
6194 //      
6195 //      if(procedure == cacheKey2) return cacheResult2; 
6196 //      
6197 //      cacheResult2 = new MultiTripleIntProcedure(procedure, this, processor.support);
6198 //      cacheKey2 = procedure;
6199 //      
6200 //      return cacheResult2;
6201 //      
6202 //    }
6203     
6204     @Override
6205     public Datatype getDataType(Resource subject) throws DatabaseException {
6206         for(Resource dataTypeResource : getObjects(subject, processor.getL0(this).HasDataType))
6207                 return getValue(dataTypeResource, Bindings.getBindingUnchecked(Datatype.class));
6208         throw new DoesNotContainValueException("The literal has no data type.");
6209     }
6210     
6211     protected <T extends Accessor> T getAccessor4File(Resource subject)
6212     throws DatabaseException {
6213         return null;
6214         /*        
6215         byte[]  bytes = processor.support.getValue(g, subject);
6216         if (null == bytes)
6217             return null;
6218         try {
6219             BinaryVariant va = (BinaryVariant) Accessors.getAccessor(bytes, Datatypes.VARIANT);
6220             Accessor ca = va.getContentAccessor();
6221             return (T)ca;
6222         } catch (AccessorConstructionException e) {
6223             throw new DatabaseException(e);
6224         }
6225         */
6226         /*
6227         if (null == bytes)
6228             return null;
6229         Binding datatype_binding = Bindings.getBindingUnchecked(DataType.class);
6230         Serializer datatype_serializer = datatype_binding.serializer();
6231         DataType datatype;
6232         try {
6233             BinaryMemory in = new BinaryMemory(ByteBuffer.wrap(bytes));
6234             datatype = (DataType)datatype_serializer.deserialize(in);
6235             Binding data_binding = Bindings.getBinding(datatype);
6236             Serializer data_serializer = data_binding.serializer(BinarySerializationFormat.INSTANCE);
6237             Object o = data_serializer.deserialize(in);
6238             try {
6239                 return (T)Accessors.getAccessor(data_binding, o);
6240             } catch(AccessorConstructionException e) {
6241                 return null;
6242             }
6243         } catch (Exception e) {
6244             throw new DatabaseException(e);
6245         }*/
6246     }
6247     @SuppressWarnings("unchecked")
6248     @Override
6249     public <T extends Accessor> T getAccessor(Resource subject) throws DatabaseException {
6250         RandomAccessBinary rab = getRandomAccessBinary(subject);
6251         try {
6252             return (T)Accessors.getAccessor(rab, getDataType(subject));
6253         } catch(AccessorConstructionException e) {
6254             throw new DatabaseException(e);
6255         }
6256     }
6257     @SuppressWarnings("unchecked")
6258     protected <T extends Accessor> T createAccessor(Resource resource, Datatype datatype, Object intialValue)
6259     throws DatabaseException {
6260         RandomAccessBinary rab = createRandomAccessBinary(resource, datatype, intialValue);
6261         try {
6262             return (T)Accessors.getAccessor(rab, datatype);
6263         } catch(AccessorConstructionException e) {
6264             throw new DatabaseException(e);
6265         }
6266     }
6267     @Override
6268     public RandomAccessBinary getRandomAccessBinary(Resource subject) throws DatabaseException {
6269         RandomAccessValueSupport ravs = getSession().getService(RandomAccessValueSupport.class);
6270         ResourceData rd = ravs.get(subject);
6271         if (null != rd)
6272             return rd;
6273         try {
6274             ExternalValueSupport evs = getService(ExternalValueSupport.class);
6275             long size = evs.getValueSize(this, subject); // Throws DatabaseException if no old external value.
6276             try {
6277                 File platform = Platform.getLocation().toFile();
6278                 File tempFiles = new File(platform, "tempFiles");
6279                 File dbDir = new File(tempFiles, "db");
6280                 dbDir.mkdirs();
6281                 File file = new File(dbDir, "ResourceFile" + subject.getResourceId());
6282                 rd = new ResourceData(new BinaryFile(file), true); // Old external value.
6283                 final int N = 1<<20;
6284                 long left = size;
6285                 long offset = 0;
6286                 while (left > 0) {
6287                     int length = N < left ? N : (int)left;
6288                     byte[] bytes = evs.readValue(this, subject, offset, length);
6289                     offset += bytes.length;
6290                     left -= bytes.length;
6291                     rd.binaryFile.write(bytes);
6292                 }
6293                 ravs.put(subject, rd);
6294                 return rd;
6295             } catch (Exception e) {
6296                 throw new DatabaseException("Resource " + subject + " have value but there was problem with accessing value data.", e);
6297             }
6298         } catch (Exception e) {
6299             if(Development.DEVELOPMENT) {
6300                 if(Development.<Boolean>getProperty(DevelopmentKeys.WRITEGRAPH_EXCEPTION_STACKTRACES, Bindings.BOOLEAN)) {
6301                     e.printStackTrace();
6302                 }
6303             }
6304         }
6305         Datatype datatype = getDataType(subject);
6306         Object value = getPossibleValue(subject, Bindings.getBinding(datatype));
6307         return createRandomAccessBinary(subject, datatype, value);
6308     }
6309     public RandomAccessBinary createRandomAccessBinary(Resource resource, Datatype datatype, Object initialValue)
6310     throws DatabaseException {
6311         RandomAccessValueSupport ravs = getSession().getService(RandomAccessValueSupport.class);
6312         try {
6313             File platform = Platform.getLocation().toFile();
6314             File tempFiles = new File(platform, "tempFiles");
6315             File dbDir = new File(tempFiles, "db");
6316             dbDir.mkdirs();
6317             File file = new File(dbDir, "ResourceFile" + resource.getResourceId());
6318             ResourceData rd = new ResourceData(new BinaryFile(file), false);
6319             Binding binding = Bindings.getBinding(datatype);
6320             if (null == initialValue) {
6321                 initialValue = binding.createDefault();
6322             }
6323             Serializer serializer = binding.serializer();
6324             byte[] bytes = serializer.serialize(initialValue);
6325             rd.binaryFile.write(bytes);
6326             ravs.put(resource, rd);
6327             return rd;
6328         } catch (Exception e) {
6329             if (e instanceof DatabaseException)
6330                 throw (DatabaseException)e;
6331             else
6332                 throw new DatabaseException(e);
6333         }
6334     }
6335
6336 //    static class ExternalValueRequest<T> extends ResourceRead<T> {
6337 //
6338 //              public ExternalValueRequest(Resource resource) {
6339 //                      super(resource);
6340 //              }
6341 //
6342 //              @SuppressWarnings("unchecked")
6343 //              @Override
6344 //              public T perform(ReadGraph graph) throws DatabaseException {
6345 //              try {
6346 //                      
6347 //                      String uri = graph.getURI(resource);
6348 //                      if(Layer0.URIs.Functions_functionApplication.equals(uri)) return (T)functionApplication;
6349 //                      
6350 //                      return (T)ReflectionUtils.getValue(uri).getValue();
6351 //                      
6352 //              } catch(ValueNotFoundException e) {
6353 //                      throw new DatabaseException("Couldn't convert to external value (r=" + resource + ")", e);
6354 //              } catch(ClassCastException e) {
6355 //                      throw new DatabaseException("Couldn't convert to external value (r=" + resource + ")", e);
6356 //              }
6357 //              }
6358 //      
6359 //    }
6360     
6361     @SuppressWarnings("unchecked")
6362     @Override
6363     public <T> T getValue2(Resource r, Object context) throws DatabaseException {
6364         Layer0 L0 = processor.getL0(this);
6365         Set<Resource> types = getTypes(r);
6366         
6367         if(types.contains(L0.Literal)) {
6368                 if(isImmutable(r)) {
6369                         return syncRequest(new ValueImplied<T>(r));
6370                 } else {
6371                         return getValue(r);
6372                 }
6373         }
6374         else if(types.contains(L0.ExternalValue)) {
6375                 return (T)syncRequest(new AdaptValue(r), TransientCacheListener.<Object>instance());
6376         }
6377         else {
6378
6379             Function3<ReadGraph,Resource,Object,T> function = requestValueFunction(r);
6380             if(function == null) throw new DoesNotContainValueException("Couldn't convert to a value function " + r);
6381             try {
6382                 return function.apply(this, r, context);
6383             } catch(RuntimeException e) {
6384                 DatabaseException dte = findPossibleRootException(e);
6385                 if(dte != null) throw dte;
6386                 else throw new DatabaseException(e);
6387             }
6388                 
6389         }
6390     }
6391
6392     @Override
6393     public Variant getVariantValue2(Resource r, Object context) throws DatabaseException {
6394         Layer0 L0 = processor.getL0(this);
6395         Set<Resource> types = getTypes(r);
6396         
6397         if(types.contains(L0.Literal)) {
6398             if(isImmutable(r)) {
6399                 return syncRequest(new VariantValueImplied(r));
6400             } else {
6401                 return getVariantValue(r);
6402             }
6403         }
6404         else if(types.contains(L0.ExternalValue)) {
6405             Object value = syncRequest(new AdaptValue(r), TransientCacheListener.<Object>instance());
6406             try {
6407                 return new Variant(Bindings.OBJECT.getContentBinding(value), value);
6408             } catch ( org.simantics.databoard.binding.error.BindingException e ) {
6409                 throw new BindingException( "No binding found for class " + value.getClass().getName(), e );
6410             }
6411         }
6412         else {
6413
6414             Function3<ReadGraph,Resource,Object,Object> function = requestValueFunction(r);
6415             if(function == null) throw new DoesNotContainValueException("Couldn't convert to a value function " + r);
6416             try {
6417                 Object value = function.apply(this, r, context);
6418                 try {
6419                     return new Variant(Bindings.OBJECT.getContentBinding(value), value);
6420                 } catch ( org.simantics.databoard.binding.error.BindingException e ) {
6421                     throw new BindingException( "No binding found for class " + value.getClass().getName(), e );
6422                 }
6423             } catch(RuntimeException e) {
6424                 DatabaseException dte = findPossibleRootException(e);
6425                 if(dte != null) throw dte;
6426                 else throw new DatabaseException(e);
6427             }
6428         }
6429     }
6430     
6431     @Override
6432     public <T> T getPossibleValue2(Resource subject, Object context) throws DatabaseException {
6433         try {
6434                 return getValue2(subject, context);
6435         } catch (DatabaseException e) {
6436                 return null;
6437         }
6438     }
6439
6440     static class PossibleConverterFunction<T> extends ResourceRead<Function3<ReadGraph,Resource,Object,T>> {
6441         
6442         public PossibleConverterFunction(Resource resource) {
6443                         super(resource);
6444                 }
6445
6446         @Override
6447         public Function3<ReadGraph,Resource,Object,T> perform(ReadGraph graph) throws DatabaseException {
6448                 return compute(graph, resource);
6449         }
6450         
6451         @SuppressWarnings("unchecked")
6452                 public static <T> Function3<ReadGraph,Resource,Object,T> compute(ReadGraph graph, Resource resource) throws DatabaseException {
6453             Layer0 L0 = Layer0.getInstance(graph);
6454             for(Resource converter : graph.getObjects(resource, L0.ConvertsToValueWith)) {
6455                 try {
6456                         if(L0.Functions_functionApplication.equals(converter)) {
6457                                 return AdaptValue.functionApplication;
6458                                 //return (Function3<ReadGraph,Resource,Object,T>)graph.syncRequest(new AdaptValue(resource));
6459                         } else {
6460                                 return graph.getValue2(converter, resource);
6461                         }
6462                 } catch(RuntimeException e) {
6463                     DatabaseException dte = findPossibleRootException(e);
6464                     if(dte != null) throw dte;
6465                     else throw new DatabaseException(e);
6466                 }
6467             }
6468             return null;
6469         }
6470         
6471     }
6472     
6473     <T> Function3<ReadGraph,Resource,Object,T> requestValueFunction(Resource r) throws DatabaseException {
6474         if(isImmutable(r))
6475                 return syncRequest(new PossibleConverterFunction<T>(r), TransientCacheAsyncListener.<Function3<ReadGraph,Resource,Object,T>>instance());
6476         else
6477                 return syncRequest(new PossibleConverterFunction<T>(r));
6478     }
6479     
6480     /**
6481      * Get a value associated with a graph {@link Resource}, using a possible context object and
6482      * a desired value binding. The following methods are tried in order to retreive the value:
6483      * <ol>
6484      *   <li>If the given resource is a {@code L0.Literal}, the value of the literal is returned, using the binding specified by {@code binding}.</li>
6485      *   <li>If the resource is a {@code L0.ExternalValue}, the value is acquired using
6486      *       {@link ReflectionUtils#getValue(String)}.</li>
6487      *   <li>If the resource is associated with a suitable value converter with relation {@code L0.ConvertsToValueWith}
6488      *       (see {@link #requestValueFunction(Resource)}), the value function is called with the graph, the resource
6489      *       and the context object.</li>
6490      * </ul>
6491      * 
6492      * @param r  A graph resource with which the value is associated
6493      * @param context  A context object that is used for acquiring the value (only applied in case 3)
6494      * @param binding  A binding for the value type (only applied in case 1)
6495      * @return  The value of the graph node.
6496      * @throws DoesNotContainValueException  No value is associated with the graph node.
6497      * @throws DatabaseException  Other errors, such as an error in casting the value to the return type or
6498      *         a runtime error in the value function.
6499      */
6500     @SuppressWarnings("unchecked")
6501         @Override
6502     public <T> T getValue2(Resource r, Object context, Binding binding) throws DatabaseException {
6503         if (binding instanceof ObjectVariantBinding)
6504                 return getValue2(r, context);
6505         
6506         Layer0 L0 = processor.getL0(this);
6507         Set<Resource> types = getTypes(r);
6508         if(types.contains(L0.Literal)) {
6509                 if(isImmutable(r)) {
6510                         return syncRequest(new Value<T>(r, binding));
6511                 } else {
6512                         return getValue(r, binding);
6513                 }
6514         } else if(types.contains(L0.ExternalValue)) {
6515                 try {
6516                         ExternalValue ev = adapt(r, ExternalValue.class);
6517                         return ev.getValue(this, r);
6518                         //return (T)ReflectionUtils.getValue(getURI(r)).getValue();
6519 //              } catch(ValueNotFoundException e) {
6520 //                      throw new DatabaseException(e);
6521                 } catch(ClassCastException e) {
6522                         throw new DatabaseException(e);
6523                 }
6524         }
6525         else {
6526             Function3<ReadGraph,Resource,Object,T> function = requestValueFunction(r);
6527             if(function == null) throw new DoesNotContainValueException("Couldn't convert to a value function.");
6528             try {
6529                 Object value = function.apply(this, r, context);
6530                 if(binding.isInstance(value)) return (T)value;
6531                 Binding srcBinding = Bindings.OBJECT.getContentBinding(value);
6532                 return (T)Bindings.adapt(value, srcBinding, binding);
6533             } catch(RuntimeException e) {
6534                 DatabaseException dte = findPossibleRootException(e);
6535                 if(dte != null) throw dte;
6536                 else throw new DatabaseException(e);
6537             } catch (AdaptException e) {
6538                 throw new DatabaseException(e);
6539                         } catch (org.simantics.databoard.binding.error.BindingException e) {
6540                 throw new DatabaseException(e);
6541                         }
6542         }
6543     }
6544     
6545     @Override
6546     public <T> T getPossibleValue2(Resource subject, Object context, Binding binding) throws DatabaseException {
6547         try {
6548                 return getValue2(subject, context, binding);
6549         } catch (DatabaseException e) {
6550                 return null;
6551         }
6552     }
6553     
6554         private static DatabaseException findPossibleRootException(Throwable t) {
6555                 if(t == null) return null;
6556                 if(t instanceof DatabaseException) return (DatabaseException)t;
6557                 if(t instanceof RuntimeException || t instanceof InvocationTargetException) {
6558                         return findPossibleRootException(t.getCause());
6559                 }
6560                 return null;
6561         }
6562     
6563     @Override
6564     public <T> T getRelatedValue2(Resource subject, Resource relation) throws DatabaseException {
6565         return getRelatedValue2(subject, relation, subject);
6566     }
6567     
6568     @Override
6569     public Variant getRelatedVariantValue2(Resource subject, Resource relation) throws DatabaseException {
6570         return getRelatedVariantValue2(subject, relation, subject);
6571     }
6572     
6573     @Override
6574     public <T> T getPossibleRelatedValue2(Resource subject, Resource relation) throws DatabaseException {
6575         try {
6576                 Resource object = getPossibleObject(subject, relation);
6577                 if(object == null) return null;
6578                 else return getValue2(object, subject);
6579         } catch (DatabaseException e) {
6580                 return null;
6581         }
6582     }
6583
6584     @Override
6585     public <T> T getRelatedValue2(Resource subject, Resource relation, Object context) throws DatabaseException {
6586                 if(Development.DEVELOPMENT) {
6587                         String error = L0Validations.checkValueType(this, subject, relation);
6588                         if(error != null) {
6589                                 Logger.defaultLogError(new ValidationException(error));
6590                                 //throw new ValidationException(error);
6591                                 new ValidationException(error).printStackTrace();
6592                         }
6593                 }
6594         return getValue2(getSingleObject(subject, relation), context);
6595     }
6596     
6597     @Override
6598     public Variant getRelatedVariantValue2(Resource subject, Resource relation, Object context) throws DatabaseException {
6599         if(Development.DEVELOPMENT) {
6600             String error = L0Validations.checkValueType(this, subject, relation);
6601             if(error != null) {
6602                 Logger.defaultLogError(new ValidationException(error));
6603                 //throw new ValidationException(error);
6604                 new ValidationException(error).printStackTrace();
6605             }
6606         }
6607         return getVariantValue2(getSingleObject(subject, relation), context);
6608     }
6609     
6610     @Override
6611     public <T> T getPossibleRelatedValue2(Resource subject, Resource relation, Object context) throws DatabaseException {
6612         try {
6613                 Resource object = getPossibleObject(subject, relation);
6614                 if(object == null) return null;
6615                 else return getValue2(object, context);
6616         } catch (DatabaseException e) {
6617                 return null;
6618         }
6619     }
6620
6621     @Override
6622     public <T> T getRelatedValue2(Resource subject, Resource relation, Binding binding) throws DatabaseException {
6623         return getRelatedValue2(subject, relation, subject, binding);
6624     }
6625     
6626     @Override
6627     public <T> T getPossibleRelatedValue2(Resource subject, Resource relation, Binding binding) throws DatabaseException {
6628         try {
6629                 Resource object = getPossibleObject(subject, relation);
6630                 if(object == null) return null;
6631                 return getValue2(object, subject, binding);
6632         } catch (DatabaseException e) {
6633                 return null;
6634         }
6635     }
6636
6637     @Override
6638     public <T> T getRelatedValue2(Resource subject, Resource relation, Object context, Binding binding) throws DatabaseException {
6639         return getValue2(getSingleObject(subject, relation), context, binding);
6640     }
6641     
6642     @Override
6643     public <T> T getPossibleRelatedValue2(Resource subject, Resource relation, Object context, Binding binding) throws DatabaseException {
6644         try {
6645                 Resource object = getPossibleObject(subject, relation);
6646                 if(object == null) return null;
6647                 else return getValue2(object, context, binding);
6648         } catch (DatabaseException e) {
6649                 return null;
6650         }
6651     }
6652     
6653     @Override
6654     public Type getRelatedValueType(Resource subject, Resource relation) throws DatabaseException {
6655         Layer0 L0 = processor.getL0(this);
6656         Resource property = getSingleObject(subject, relation);
6657         String typeText = (String)getRelatedValue(property, L0.HasValueType, Bindings.STRING);
6658         try {
6659             return org.simantics.scl.compiler.types.Types.parseType(typeText);
6660         } catch (SCLTypeParseException e) {
6661             throw new DatabaseException(e);
6662         }
6663     }
6664     
6665     @Override
6666     public boolean setSynchronous(boolean value) {
6667         boolean old = processor.synch;
6668         processor.synch = value;
6669         return old;
6670     }
6671     
6672     @Override
6673     public boolean getSynchronous() {
6674         return processor.synch;
6675     }
6676     
6677     public void ensureLoaded(int resource) {
6678         processor.querySupport.ensureLoaded(this, resource);
6679     }
6680     
6681     public void ensureLoaded(int resource, int predicate) {
6682         processor.querySupport.ensureLoaded(this, resource, predicate);
6683     }
6684
6685     public byte[] getValue(int resource) {
6686         return processor.querySupport.getValue(this, resource);
6687     }
6688     
6689     public int thread(int resource) {
6690         return (resource >>> 16) & processor.THREAD_MASK;
6691     }
6692
6693     public int thread(Resource resource) {
6694         return (((ResourceImpl)resource).id >>> 16) & processor.THREAD_MASK;
6695     }
6696     
6697     public ResourceSupport getResourceSupport() {
6698         return processor.getResourceSupport();
6699     }
6700     
6701     @Override
6702     public Object getModificationCounter() {
6703         return processor.getSession().getModificationCounter();
6704     }
6705     
6706 }