]> gerrit.simantics Code Review - simantics/platform.git/blob - bundles/org.simantics.db.layer0/src/org/simantics/db/layer0/util/TransferableGraphRequest.java
Sync git svn branch with SVN repository r33158.
[simantics/platform.git] / bundles / org.simantics.db.layer0 / src / org / simantics / db / layer0 / util / TransferableGraphRequest.java
1 /*******************************************************************************\r
2  * Copyright (c) 2007, 2010 Association for Decentralized Information Management\r
3  * in Industry THTH ry.\r
4  * All rights reserved. This program and the accompanying materials\r
5  * are made available under the terms of the Eclipse Public License v1.0\r
6  * which accompanies this distribution, and is available at\r
7  * http://www.eclipse.org/legal/epl-v10.html\r
8  *\r
9  * Contributors:\r
10  *     VTT Technical Research Centre of Finland - initial API and implementation\r
11  *******************************************************************************/\r
12 package org.simantics.db.layer0.util;\r
13 \r
14 import gnu.trove.list.array.TIntArrayList;\r
15 \r
16 import java.io.ByteArrayInputStream;\r
17 import java.io.DataOutput;\r
18 import java.io.DataOutputStream;\r
19 import java.io.File;\r
20 import java.io.FileInputStream;\r
21 import java.io.FileNotFoundException;\r
22 import java.io.FileOutputStream;\r
23 import java.io.IOException;\r
24 import java.io.InputStream;\r
25 import java.io.ObjectInputStream;\r
26 import java.io.ObjectOutputStream;\r
27 import java.util.ArrayList;\r
28 import java.util.Collection;\r
29 import java.util.HashMap;\r
30 import java.util.HashSet;\r
31 import java.util.LinkedList;\r
32 import java.util.Map;\r
33 import java.util.Set;\r
34 import java.util.UUID;\r
35 import java.util.concurrent.ConcurrentSkipListSet;\r
36 import java.util.concurrent.atomic.AtomicInteger;\r
37 \r
38 import org.apache.commons.io.output.DeferredFileOutputStream;\r
39 import org.simantics.databoard.Bindings;\r
40 import org.simantics.databoard.Databoard;\r
41 import org.simantics.databoard.binding.mutable.Variant;\r
42 import org.simantics.databoard.serialization.Serializer;\r
43 import org.simantics.db.AsyncReadGraph;\r
44 import org.simantics.db.ReadGraph;\r
45 import org.simantics.db.Resource;\r
46 import org.simantics.db.Statement;\r
47 import org.simantics.db.common.StandardStatement;\r
48 import org.simantics.db.common.utils.NameUtils;\r
49 import org.simantics.db.exception.DatabaseException;\r
50 import org.simantics.db.exception.ValidationException;\r
51 import org.simantics.db.layer0.adapter.Instances;\r
52 import org.simantics.db.layer0.adapter.SubgraphAdvisor;\r
53 import org.simantics.db.layer0.adapter.SubgraphExtent;\r
54 import org.simantics.db.layer0.adapter.SubgraphExtent.Classifier;\r
55 import org.simantics.db.layer0.adapter.SubgraphExtent.ExtentStatus;\r
56 import org.simantics.db.procedure.AsyncProcedure;\r
57 import org.simantics.db.request.AsyncRead;\r
58 import org.simantics.db.request.Read;\r
59 import org.simantics.db.service.CollectionSupport;\r
60 import org.simantics.db.service.QueryControl;\r
61 import org.simantics.db.service.QueryControl.ControlProcedure;\r
62 import org.simantics.db.service.SerialisationSupport;\r
63 import org.simantics.graph.representation.External;\r
64 import org.simantics.graph.representation.Identity;\r
65 import org.simantics.graph.representation.Root;\r
66 import org.simantics.graph.representation.TransferableGraph1;\r
67 import org.simantics.graph.representation.Value;\r
68 import org.simantics.layer0.Layer0;\r
69 import org.simantics.operation.Layer0X;\r
70 import org.simantics.utils.datastructures.Pair;\r
71 import org.simantics.utils.datastructures.Triple;\r
72 \r
73 /**\r
74  * IsComposedOf objects are always in domain\r
75  * Ordered set elements are always in domain\r
76  * r is in domain if for all statements (s, IsRelatedTo, r) s is in domain\r
77  *\r
78  * IsWeaklyRelatedTo statements where subject is in domain are only accepted if object is in domain or has URI\r
79  * \r
80  * @deprecated in favor of {@link TransferableGraphRequest2}\r
81  */\r
82 public class TransferableGraphRequest implements Read<TransferableGraph1> {\r
83 \r
84         public static String LOG_FILE = "transferableGraph.log";\r
85         final static private boolean LOG = false;\r
86         final static private boolean DEBUG = false;\r
87         final static private boolean PROFILE = false;\r
88         \r
89 //      final private Collection<Pair<Resource, String>> roots;\r
90 //      private Collection<Resource> preExternals = Collections.emptyList();\r
91 //      private Resource model;\r
92         \r
93         private TransferableGraphConfiguration configuration;\r
94         \r
95         static DataOutput log;\r
96 \r
97         static {\r
98 \r
99                 if (LOG) {\r
100                         try {\r
101                                 FileOutputStream stream = new FileOutputStream(LOG_FILE);\r
102                                 log = new DataOutputStream(stream);\r
103                         } catch (FileNotFoundException e) {\r
104                                 e.printStackTrace();\r
105                         }\r
106                 }\r
107 \r
108         }\r
109         \r
110         private static void log(String line) {\r
111                 if (LOG) {\r
112                         try {\r
113                                 log.writeUTF(line + "\n");\r
114                         } catch (IOException e) {\r
115                                 e.printStackTrace();\r
116                         }\r
117                 }\r
118         }\r
119         \r
120         \r
121         \r
122         public TransferableGraphRequest(Collection<Pair<Resource, String>> roots, Resource model) {\r
123                 \r
124                 configuration = new TransferableGraphConfiguration();\r
125                 configuration.roots = roots;\r
126                 configuration.model = model;\r
127                 \r
128 //              this.roots = roots;\r
129 //              this.model = model;\r
130                 \r
131         }\r
132 \r
133         \r
134         public TransferableGraphRequest(Collection<Pair<Resource, String>> roots) {\r
135                 this(roots, null);\r
136         }\r
137 \r
138         public TransferableGraphRequest(TransferableGraphConfiguration conf) {\r
139                 this.configuration = conf;\r
140         }\r
141 \r
142         Layer0 l0;\r
143         \r
144         TIntArrayList inverses = new TIntArrayList();\r
145         int statements[];\r
146         int statementIndex = 0;\r
147         Map<Resource, Integer> ids;\r
148         Map<Resource, Variant> values;\r
149         TIntArrayList externalParents = new TIntArrayList();\r
150         ArrayList<String> externalNames = new ArrayList<String>(); \r
151 //      ConcurrentLinkedQueue<Pair<Resource, byte[]>> values = new ConcurrentLinkedQueue<Pair<Resource, byte[]>>();\r
152         int id = 0;\r
153         int internalCount;\r
154         \r
155         int indent = 0;\r
156 \r
157         private Serializer variantSerializer;\r
158 \r
159         private boolean validateExternal(Resource r) {\r
160                 if(configuration.disallowedExternals != null) {\r
161                         System.err.println("validateExternal agains " + configuration.disallowedExternals);\r
162                         return !configuration.disallowedExternals.contains(r);\r
163                 }\r
164                 return true;\r
165         }\r
166         \r
167         public int getId(ReadGraph graph, Resource r, Resource predicate) throws DatabaseException {\r
168 //          for(int i=0;i<indent;++i)\r
169 //              System.out.print("  ");\r
170 //          System.out.println(NameUtils.getSafeName(graph, r));\r
171                 if(ids.containsKey(r)) {\r
172                     int ret = ids.get(r);\r
173                     if(ret == -1) {\r
174                         for(int i=0;i<=indent;++i)\r
175                             System.out.print("  ");\r
176                         System.out.println("Cycle!!!"); // with " + GraphUtils.getReadableName(g, r));\r
177                     }\r
178                         return ret;\r
179                 }\r
180                 else {\r
181                     //ids.put(r, -1);\r
182                         Collection<Resource> parents = graph.getObjects(r, l0.PartOf);                  \r
183                         if(parents.size() != 1) {\r
184                             if(parents.size() == 0) {\r
185                                 Resource inv = graph.getPossibleObject(r, l0.InverseOf);\r
186                                 if(inv != null) {                       \r
187                                     ++indent;\r
188                                     if(DEBUG) System.out.println("inverse " + NameUtils.getSafeName(graph, inv));\r
189                                     int invId = getId(graph, inv, null);\r
190                                     externalParents.add(invId);\r
191                                     --indent;\r
192                                     externalNames.add("@inverse");\r
193                                     ids.put(r, id);\r
194                                     return id++;\r
195                                 }\r
196                             }\r
197 //                          for(Statement stat : graph.getStatements(r, b.IsWeaklyRelatedTo))\r
198 //                              System.out.println(NameUtils.getSafeName(graph, stat.getPredicate()) \r
199 //                                  + " -> " + NameUtils.getSafeName(graph, stat.getObject()));\r
200 //                          if(predicate != null) {\r
201 //                              if(!graph.isSubrelationOf(predicate, b.IsRelatedTo)) {\r
202 //                                      return -2;\r
203 //                              }\r
204 //                          }\r
205                                 throw new ValidationException("Reference to external resource " \r
206                                                 + NameUtils.getSafeName(graph, r, true) + " without unique uri (" + parents.size() + " parents).");\r
207                         }\r
208                         for(Resource p : parents) {\r
209 //                  System.out.println("Parent " + NameUtils.getSafeName(graph, p)); \r
210                             ++indent;\r
211                     if(!validateExternal(p)) throw new ValidationException("References to '" + graph.getURI(p) + "' are not allowed.");\r
212                                 externalParents.add(getId(graph, p, null));\r
213                                 --indent;\r
214                         }\r
215 //          System.out.println("Request named for " + GraphUtils.getReadableName(g, r)); \r
216 //                      String name = graph.getPossibleRelatedValue(r, b.HasName);\r
217             externalNames.add((String)graph.getRelatedValue(r, l0.HasName));\r
218 //                      if(name != null) externalNames.add(name);\r
219 //                      else externalNames.add("@resource");\r
220                         ids.put(r, id);\r
221                         return id++;\r
222                 }\r
223         }\r
224         \r
225         public void addId(ReadGraph graph, Resource r, Resource predicate) throws DatabaseException {\r
226                 statements[statementIndex++] = getId(graph, r, predicate); \r
227         }\r
228         \r
229         private void searchStatementPart(ReadGraph graph, final ConcurrentSkipListSet<Statement> statementSet, final ArrayList<Pair<Resource, Triple[]>> part, final Set<SubgraphExtent> extents) throws DatabaseException {\r
230 \r
231                 final SubgraphExtent.Callback callback = new SubgraphExtent.Callback() {\r
232 \r
233                         @Override\r
234                         public void statement(Statement statement, boolean accept) {\r
235                                 if(accept) {\r
236                                         statementSet.add(statement);\r
237                                 }\r
238                         }\r
239                         \r
240                 };\r
241 \r
242                 graph.syncRequest(new AsyncRead<Boolean>() {\r
243 \r
244                     @Override\r
245                     public int threadHash() {\r
246                         return hashCode();\r
247                     }\r
248                         \r
249                         @Override\r
250                         public void perform(AsyncReadGraph graph, AsyncProcedure<Boolean> procedure) {\r
251 \r
252                                 QueryControl control = graph.getService(QueryControl.class);\r
253 \r
254                                 int slice = (int)(part.size() / control.getAmountOfQueryThreads()) + 1;\r
255 \r
256                                 final Pair[] rootArray = (Pair[])part.toArray(new Pair[part.size()]);\r
257                                 for(int i=0;i<control.getAmountOfQueryThreads();i++) {\r
258 \r
259                                         final int start = i * slice;\r
260                                         final int end = Math.min(start + slice, rootArray.length);\r
261 \r
262                                         control.schedule(graph, i, new ControlProcedure() {\r
263 \r
264                                                 @Override\r
265                                                 public void execute(AsyncReadGraph graph) {\r
266 \r
267                                                         for(int index = start;index < end;index++) {\r
268 \r
269                                                                 final Pair<Resource, Triple[]> r = (Pair<Resource, Triple[]>)rootArray[index];\r
270 \r
271                                                                 final AtomicInteger position = new AtomicInteger(0);\r
272                                                                 final SubgraphExtent.Classifier[] classifiers = new SubgraphExtent.Classifier[extents.size()];\r
273 \r
274                                                                 for(SubgraphExtent extent : extents) {\r
275 \r
276                                                                         extent.accept(graph, r.first, new AsyncProcedure<Classifier>() {\r
277 \r
278                                                                                 public void execute(AsyncReadGraph graph, Classifier c) {\r
279 \r
280                                                                                         int current = position.incrementAndGet();\r
281                                                                                         classifiers[current-1] = c;\r
282 \r
283                                                                                         if(current == extents.size()) {\r
284 \r
285                                                                                                 for(Triple statement : r.second) {\r
286                                                                                                         if(!r.first.isPersistent()) continue;\r
287                                                                                                         for(Classifier classifier : classifiers) {\r
288                                                                                                                 classifier.classify(graph, new StandardStatement(r.first, (Resource)statement.first, (Resource)statement.second), (ExtentStatus)statement.third, callback);\r
289                                                                                                         }\r
290                                                                                                 }\r
291                                                                                                 \r
292 //                                                                                              graph.forEachDirectStatement(r, new AsyncMultiProcedure<Statement>() {\r
293 //\r
294 //                                                                                                      @Override\r
295 //                                                                                                      public void exception(AsyncReadGraph graph, Throwable throwable) {\r
296 //                                                                                                              throwable.printStackTrace();\r
297 //                                                                                                      }\r
298 //\r
299 //                                                                                                      @Override\r
300 //                                                                                                      public void execute(AsyncReadGraph graph, Statement statement) {\r
301 //                                                                                                      }\r
302 //\r
303 //                                                                                                      @Override\r
304 //                                                                                                      public void finished(AsyncReadGraph graph) {\r
305 //                                                                                                      }\r
306 //\r
307 //                                                                                              });\r
308 \r
309                                                                                         }\r
310 \r
311                                                                                 }\r
312 \r
313                                                                                 public void exception(AsyncReadGraph graph, Throwable throwable) {\r
314                                                                                         throwable.printStackTrace();\r
315                                                                                 }\r
316 \r
317                                                                         }, callback);\r
318 \r
319                                                                 }\r
320 \r
321                                                         }\r
322 \r
323                                                 }\r
324 \r
325                                         });\r
326 \r
327                                 }\r
328 \r
329                                 procedure.execute(graph, false);\r
330 \r
331                         }\r
332 \r
333                         @Override\r
334                         public int getFlags() {\r
335                                 return 0;\r
336                         }\r
337 \r
338                 });\r
339 \r
340         }\r
341 \r
342         class StatementSetBuilder {\r
343 \r
344                 private int SLICE = 100000;\r
345                 \r
346                 final private CollectionSupport cs;\r
347                 final private LinkedList<Collection<Statement>> sets = new LinkedList<Collection<Statement>>();\r
348 \r
349                 private Collection<Statement> current;\r
350                 \r
351                 StatementSetBuilder(CollectionSupport cs) {\r
352                         this.cs = cs;\r
353                         current = cs.createStatementList();\r
354                 }\r
355                 \r
356                 LinkedList<Collection<Statement>> get() {\r
357                         sets.add(current);\r
358                         return sets;\r
359                 }\r
360                 \r
361                 void add(Statement stm) {\r
362                         current.add(stm);\r
363                         if(current.size() == SLICE) {\r
364                                 sets.add(current);\r
365                                 current = cs.createStatementList();\r
366                         }\r
367                 }\r
368 \r
369                 int size() {\r
370                         int result = 0;\r
371                         for(Collection<Statement> c : sets) result += c.size();\r
372                         return result;\r
373                 }\r
374                 \r
375                 \r
376                 void addAll(Collection<Statement> ss) {\r
377                         for(Statement s : ss) add(s);\r
378                 }\r
379                 \r
380         }\r
381         \r
382         private void searchStatements(ReadGraph graph, ObjectInputStream composedInput, ObjectInputStream statementInput, ObjectInputStream valueInput, final Set<SubgraphExtent> extents) throws DatabaseException, IOException {\r
383 \r
384                 CollectionSupport cs = graph.getService(CollectionSupport.class);\r
385                 \r
386                 ConcurrentSkipListSet<Statement> statementSet = new ConcurrentSkipListSet<Statement>();\r
387 \r
388                 StatementSetBuilder builder = new StatementSetBuilder(cs);\r
389 \r
390                 SerialisationSupport support = graph.getService(SerialisationSupport.class);\r
391 \r
392                 while(composedInput.available() > 0) {\r
393 \r
394                         int s = composedInput.readInt();\r
395                         Resource subject = support.getResource(s);\r
396 \r
397                         int size = composedInput.readInt();\r
398                         for(int i=0;i<size;i++) {\r
399                                 int p = composedInput.readInt();\r
400                                 int o = composedInput.readInt();\r
401                                 StandardStatement stm = new StandardStatement(subject, support.getResource(p), support.getResource(o));\r
402 //                              if(DEBUG) System.out.println("composed " + NameUtils.toString(graph, stm));\r
403                                 builder.add(stm);\r
404                         }\r
405                         \r
406                 }\r
407 \r
408                 while(statementInput.available() > 0) {\r
409 \r
410                         ArrayList<Pair<Resource, Triple[]>> stms = new ArrayList<Pair<Resource, Triple[]>>(); \r
411 \r
412                         int counter = 0;\r
413                         \r
414                         while(statementInput.available() > 0 && counter++ < 1000) {\r
415                         \r
416                                 int s = statementInput.readInt();\r
417                                 Resource subject = support.getResource(s);\r
418                                 int size = statementInput.readInt();\r
419                                 Triple[] list = new Triple[size];\r
420                                 stms.add(Pair.make(subject, list));\r
421                                 for(int i=0;i<size;i++) {\r
422                                         int p = statementInput.readInt();\r
423                                         int o = statementInput.readInt();\r
424                                         if(DEBUG) {\r
425                                                 System.out.println("otherInput " + NameUtils.toString(graph, new StandardStatement(support.getResource(s), support.getResource(p), support.getResource(o))));\r
426                                         }\r
427                                         list[i] = new Triple<Resource, Resource, ExtentStatus>(support.getResource(p), support.getResource(o), ExtentStatus.EXTERNAL);\r
428                                 }\r
429                         }\r
430                         \r
431                         searchStatementPart(graph, statementSet, stms, extents);\r
432                         \r
433                 }\r
434 \r
435                 if(DEBUG) {\r
436                         for(Statement stm : statementSet)\r
437                                 System.out.println("other " + NameUtils.toString(graph, stm));\r
438                 }\r
439                 \r
440                 builder.addAll(statementSet);\r
441                 \r
442                 if(DEBUG) System.out.println("total " + statementSet.size() + " statements found.");\r
443 \r
444                 statementSet = null;\r
445                 \r
446                 LinkedList<Collection<Statement>> statementSets = builder.get();\r
447                 \r
448                 Map<Resource, Resource> inverses = cs.createMap(Resource.class);\r
449                 Set<Resource> predicateSet = cs.createSet();\r
450                 for(Collection<Statement> set : statementSets)\r
451                         for(Statement s : set) {\r
452                                 Resource predicate = s.getPredicate();\r
453                                 if(predicateSet.add(predicate)) {\r
454                                         Resource inverse = graph.getPossibleInverse(predicate);\r
455                                         inverses.put(predicate, inverse);\r
456                                 }\r
457                         }\r
458 \r
459                 predicateSet = null;\r
460                 \r
461                 statements = new int[4 * builder.size()];\r
462                 \r
463         while(!statementSets.isEmpty()) {\r
464                 Collection<Statement> set = statementSets.pop();\r
465                         for(Statement s : set) {\r
466                                 Resource subject = s.getSubject();\r
467                                 Resource predicate = s.getPredicate();\r
468                                 Resource object = s.getObject();\r
469                                 int subjectId = ids.get(subject);\r
470                                 int objectId = getId(graph, object, predicate);\r
471                                 // The statement can be denied still\r
472                                 if(objectId != -2) {\r
473                                         statements[statementIndex++] = subjectId;\r
474                                         addId(graph, predicate, null);\r
475                                         Resource inverse = inverses.get(predicate);\r
476                                         if(inverse != null) {\r
477                                                 if(LOG) log("[STM] " + subject.getResourceId() + ", " + predicate.getResourceId() + ", " + inverse.getResourceId() + ", " + object.getResourceId());\r
478                                                 addId(graph, inverse, null);\r
479                                         } else {\r
480                                                 if(LOG) log("[STM] " + subject.getResourceId() + ", " + predicate.getResourceId() + ", -1, " + object.getResourceId());\r
481                                                 statements[statementIndex++] = -1;\r
482                                         }\r
483                                         statements[statementIndex++] = objectId;\r
484                                         \r
485                                         \r
486                                         \r
487                                 } else {\r
488                                         System.out.println("denied");\r
489                                 }\r
490                         }\r
491                 }\r
492                 \r
493                 inverses = null;\r
494                 \r
495                 while(valueInput.available() > 0) {\r
496 \r
497                         int s = valueInput.readInt();\r
498                         Resource subject = support.getResource(s);\r
499                         int valueSize = valueInput.readInt();\r
500                         byte[] value = new byte[valueSize];\r
501                         valueInput.readFully(value);\r
502                         Variant variant = (Variant) variantSerializer.deserialize(value);\r
503                         values.put(subject, variant);\r
504                         \r
505                 }\r
506                 \r
507         }\r
508         \r
509         public void setExternals(Collection<Resource> rs) {\r
510                 configuration.externals = rs;\r
511         }\r
512         \r
513         @Override\r
514         public TransferableGraph1 perform(ReadGraph graph) throws DatabaseException {\r
515 \r
516                 this.variantSerializer = graph.getService(Databoard.class).getSerializerUnchecked(Bindings.VARIANT);\r
517 \r
518                 this.l0 = Layer0.getInstance(graph);\r
519                 Layer0X L0X = Layer0X.getInstance(graph);\r
520                 \r
521                 long total = System.nanoTime();\r
522 \r
523         long startupTime = System.nanoTime();\r
524 \r
525         CollectionSupport cs = graph.getService(CollectionSupport.class);\r
526         \r
527         ids = cs.createMap(Integer.class);\r
528         values = cs.createMap(byte[].class);\r
529         \r
530                 ArrayList<Resource> rootResources = new ArrayList<Resource>();\r
531                 for(Pair<Resource, String> p : configuration.roots) rootResources.add(p.first);\r
532 \r
533 //              if(model == null) {\r
534 //                      SimulationResource SIMU = SimulationResource.getInstance(graph);\r
535 //                      for(Resource root : rootResources) {\r
536 //                              if(graph.isInstanceOf(root, SIMU.Model)) {\r
537 //                                      model = root;\r
538 //                                      break;\r
539 //                              }\r
540 //                              model = graph.syncRequest(new TypedParent(root, SIMU.Model));\r
541 //                              if(model != null) break;\r
542 //                      }\r
543 //              }\r
544 \r
545                 Map<Resource, ExtentStatus> preStatus = new HashMap<Resource, ExtentStatus>();\r
546                 \r
547                 for(Resource root : rootResources) {\r
548                         Resource name = graph.getPossibleObject(root, l0.HasName);\r
549                         if(name != null) {\r
550                                 preStatus.put(name, ExtentStatus.EXCLUDED);\r
551                         }\r
552                 }\r
553                 \r
554                 for(Resource r : configuration.externals) preStatus.put(r, ExtentStatus.EXTERNAL); \r
555 \r
556                 Set<SubgraphExtent> extents = configuration.extents;\r
557                 if(extents == null) {\r
558                         \r
559                         Instances extentInstances = graph.adapt(L0X.SubgraphExtent, Instances.class);\r
560                         Collection<Resource> extentResources = extentInstances.find(graph, configuration.model);\r
561                         extents = new HashSet<SubgraphExtent>();\r
562                         for(Resource r : extentResources) {\r
563                                 extents.add(graph.getPossibleAdapter(r, SubgraphExtent.class));\r
564                         }\r
565 \r
566                         if(DEBUG) {\r
567                                 System.out.println("Extents " + extents.size());\r
568                                 for(Resource extent : extentResources) System.out.println("-" + NameUtils.getSafeName(graph, extent));\r
569                         }\r
570                         \r
571                 }\r
572                 \r
573                 Set<SubgraphAdvisor> advisors = configuration.advisors;\r
574                 if(advisors == null) {\r
575 \r
576                         Instances advisorInstances = graph.adapt(L0X.SubgraphAdvisor, Instances.class);\r
577                         Collection<Resource> advisorResources = advisorInstances.find(graph, configuration.model);\r
578                         advisors = new HashSet<SubgraphAdvisor>();\r
579                         for(Resource r : advisorResources) {\r
580                                 advisors.add(graph.getPossibleAdapter(r, SubgraphAdvisor.class));\r
581                         }\r
582 \r
583                         if(DEBUG) {\r
584                                 System.out.println("Advisors " + advisors.size());\r
585                                 for(Resource advisor : advisorResources) System.out.println("-" + NameUtils.getSafeName(graph, advisor));\r
586                         }\r
587                         \r
588                 }\r
589 \r
590         long startupTimeEnd = System.nanoTime();\r
591 \r
592                 long domainTime = System.nanoTime();\r
593                 \r
594                 String composedStatements = "composed" + UUID.randomUUID().toString();\r
595                 String otherStatements = "other" + UUID.randomUUID().toString();\r
596                 String valueFileName = "value" + UUID.randomUUID().toString();\r
597                 \r
598         File composedStatementsFile = new File(composedStatements);\r
599         File otherStatementsFile = new File(otherStatements);\r
600         File valueFile = new File(valueFileName);\r
601         \r
602         if(DEBUG)\r
603                 System.out.println("getDomain writes " + composedStatementsFile.getAbsolutePath());\r
604 \r
605         try {\r
606         \r
607                 DeferredFileOutputStream composedStatementsStream = new DeferredFileOutputStream(5 * 1024*1024, composedStatementsFile);\r
608                 DeferredFileOutputStream otherStatementsStream = new DeferredFileOutputStream(1024*1024, otherStatementsFile);\r
609                 DeferredFileOutputStream valueStream = new DeferredFileOutputStream(1024*1024, valueFile);\r
610                 \r
611                 ObjectOutputStream composedStatementsOutput = new ObjectOutputStream(composedStatementsStream);\r
612                 ObjectOutputStream otherStatementsOutput = new ObjectOutputStream(otherStatementsStream);\r
613                 ObjectOutputStream valueOutput = new ObjectOutputStream(valueStream);\r
614 \r
615                 Subgraphs.getDomain(graph, ids, rootResources, preStatus, advisors, composedStatementsOutput, otherStatementsOutput, valueOutput);\r
616                 id = ids.size();\r
617 \r
618                 composedStatementsOutput.flush();\r
619                 otherStatementsOutput.flush();\r
620                 valueOutput.flush();\r
621                 composedStatementsStream.close();\r
622                 otherStatementsStream.close();\r
623                 valueStream.close();\r
624                 \r
625                 long domainTimeEnd = System.nanoTime();\r
626 \r
627                 long fileTime = System.nanoTime();\r
628 \r
629                 internalCount = id;\r
630 \r
631                 ids.put(graph.getRootLibrary(), id++);\r
632                 externalNames.add("http:/");\r
633                 externalParents.add(-1);\r
634 \r
635 //              if(model == null) return null;\r
636 \r
637                 InputStream composedStatementsInputStream = null;\r
638                 InputStream otherStatementsInputStream = null;\r
639                 InputStream valueInputStream = null;\r
640                 \r
641                 if(composedStatementsStream.isInMemory()) {\r
642                         composedStatementsInputStream = new ByteArrayInputStream(composedStatementsStream.getData());\r
643                 } else {\r
644                         composedStatementsInputStream = new FileInputStream(composedStatementsFile);\r
645                 }\r
646                 \r
647                 if(otherStatementsStream.isInMemory()) {\r
648                         otherStatementsInputStream = new ByteArrayInputStream(otherStatementsStream.getData());\r
649                 } else {\r
650                         otherStatementsInputStream = new FileInputStream(otherStatementsFile);\r
651                 }\r
652 \r
653                 if(valueStream.isInMemory()) {\r
654                         valueInputStream = new ByteArrayInputStream(valueStream.getData());\r
655                 } else {\r
656                         valueInputStream = new FileInputStream(valueFile);\r
657                 }\r
658 \r
659                 composedStatementsStream = null;\r
660                 otherStatementsStream = null;\r
661                 valueStream = null;\r
662                 \r
663                 ObjectInputStream composedStatementsInput = new ObjectInputStream(composedStatementsInputStream);\r
664                 ObjectInputStream otherStatementsInput = new ObjectInputStream(otherStatementsInputStream);\r
665                 ObjectInputStream valueInput = new ObjectInputStream(valueInputStream);\r
666 \r
667                 long fileTimeEnd = System.nanoTime();\r
668 \r
669                 long statementTime = System.nanoTime();\r
670                 searchStatements(graph, composedStatementsInput, otherStatementsInput, valueInput, extents);\r
671                 long statementTimeEnd = System.nanoTime();\r
672 \r
673                 //              domainParts = null;\r
674 \r
675                 long buildTime = System.nanoTime();\r
676 \r
677                 int resourceCount = ids.size();\r
678 \r
679                 Identity[] identityArray;\r
680                 { // Identities\r
681                         ArrayList<Identity> identities = new ArrayList<Identity>();\r
682 \r
683                         for(Pair<Resource, String> r : configuration.roots) {\r
684                                 Resource type = graph.getPossibleType(r.first, l0.Entity);\r
685                                 if(type == null) type = l0.Entity;\r
686                                 identities.add(new Identity(\r
687                                                 ids.get(r.first),\r
688                                                 new Root(r.second, graph.getURI(type))\r
689                                 ));\r
690                         }\r
691 \r
692                         int internalsPlusExternals = ids.size();                \r
693                         for(int i = internalCount; i < internalsPlusExternals ; i++) {\r
694                                 int parent = externalParents.get(i - internalCount);\r
695                                 String name = externalNames.get(i - internalCount);\r
696                                 identities.add(new Identity(\r
697                                                 i, \r
698                                                 new External(parent, name)\r
699                                 ));\r
700                         }\r
701                         identityArray = identities.toArray(new Identity[identities.size()]);\r
702                 }            \r
703 \r
704                 Value[] valueArray = new Value[values.size()];\r
705                 { // Values\r
706                         int index = 0;\r
707                         for(Map.Entry<Resource, Variant> entry : values.entrySet()) {\r
708                                 if(LOG) log("[VALUE] " + entry.getKey().getResourceId());\r
709                                 int r = getId(graph, entry.getKey(), null);\r
710                                 valueArray[index++] = new Value(r, entry.getValue());\r
711                         }\r
712                 }\r
713                 ids = null;\r
714                 values = null;\r
715 \r
716                 long buildTimeEnd = System.nanoTime();\r
717 \r
718                 TransferableGraph1 result = \r
719                     new TransferableGraph1(resourceCount, \r
720                             identityArray, \r
721                             statements, \r
722                             valueArray);\r
723 \r
724                 if(DEBUG) {\r
725                         System.out.println("transferable graph content: " + result);\r
726                 }\r
727 \r
728                 long totalEnd = System.nanoTime();\r
729 \r
730                 if(PROFILE) {   \r
731                         System.out.println("startup in " + 1e-9*(startupTimeEnd - startupTime) + "s.");\r
732                         System.out.println("domain was found in " + 1e-9*(domainTimeEnd - domainTime) + "s.");\r
733                         System.out.println("files were written in " + 1e-9*(fileTimeEnd - fileTime) + "s.");\r
734                         System.out.println("statements were found in " + 1e-9*(statementTimeEnd - statementTime) + "s.");\r
735                         System.out.println("tg was built in " + 1e-9*(buildTimeEnd - buildTime) + "s.");\r
736                         System.out.println("total time for building subgraph was " + 1e-9*(totalEnd-total) + "s.");\r
737                 }               \r
738 \r
739                 return result;\r
740         } catch (IOException e) {\r
741                 e.printStackTrace();\r
742         }\r
743                 \r
744         return null;\r
745                 \r
746         }\r
747         \r
748 }\r