1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29 package org.openrdf.elmo;
30
31 import static java.util.Collections.unmodifiableList;
32 import static java.util.Collections.unmodifiableMap;
33 import static java.util.Collections.unmodifiableSet;
34
35 import java.io.IOException;
36 import java.io.InputStream;
37 import java.net.URL;
38 import java.net.URLClassLoader;
39 import java.util.ArrayList;
40 import java.util.Enumeration;
41 import java.util.HashMap;
42 import java.util.LinkedHashSet;
43 import java.util.List;
44 import java.util.Map;
45 import java.util.Set;
46 import java.util.Vector;
47
48 import javax.xml.namespace.QName;
49
50
51
52
53
54
55
56
57 public class ElmoModule {
58 public static class Association {
59 private Class<?> javaClass;
60
61 private String rdfType;
62
63 private Association(Class<?> javaClass, String rdfType) {
64 this.javaClass = javaClass;
65 this.rdfType = rdfType;
66 }
67
68 public Class<?> getJavaClass() {
69 return javaClass;
70 }
71
72 public String getRdfType() {
73 return rdfType;
74 }
75
76 public String toString() {
77 return javaClass.getName() + "=" + rdfType;
78 }
79 }
80
81 private static class CombinedClassLoader extends ClassLoader {
82 private ClassLoader alt;
83
84 public CombinedClassLoader(ClassLoader parent, ClassLoader alt) {
85 super(parent);
86 this.alt = alt;
87 }
88
89 @Override
90 public URL getResource(String name) {
91 URL resource = super.getResource(name);
92 if (resource == null)
93 return alt.getResource(name);
94 return resource;
95 }
96
97 @Override
98 public InputStream getResourceAsStream(String name) {
99 InputStream stream = super.getResourceAsStream(name);
100 if (stream == null)
101 return alt.getResourceAsStream(name);
102 return stream;
103 }
104
105 @Override
106 public Enumeration<URL> getResources(String name) throws IOException {
107 Vector<URL> list = new Vector<URL>();
108 Enumeration<URL> e = super.getResources(name);
109 while (e.hasMoreElements()) {
110 list.add(e.nextElement());
111 }
112 e = alt.getResources(name);
113 while (e.hasMoreElements()) {
114 list.add(e.nextElement());
115 }
116 return list.elements();
117 }
118
119 @Override
120 public Class<?> loadClass(String name) throws ClassNotFoundException {
121 try {
122 return super.loadClass(name);
123 } catch (ClassNotFoundException e) {
124 try {
125 return alt.loadClass(name);
126 } catch (ClassNotFoundException e2) {
127 throw e;
128 }
129 }
130 }
131
132 }
133
134 private ClassLoader cl;
135
136 private List<Association> datatypes = new ArrayList<Association>();
137
138 private List<Association> concepts = new ArrayList<Association>();
139
140 private List<Association> behaviours = new ArrayList<Association>();
141
142 private List<Association> factories = new ArrayList<Association>();
143
144 private QName graph;
145
146 private Set<QName> includedGraphs = new LinkedHashSet<QName>();
147
148 private Map<URL, String> datasets = new HashMap<URL, String>();
149
150 private List<String> resources = new ArrayList<String>();
151
152 private List<URL> jars = new ArrayList<URL>();
153
154 private ClassLoader urlClassLoader;
155
156 public ElmoModule() {
157 super();
158 cl = Thread.currentThread().getContextClassLoader();
159 if (cl == null) {
160 cl = getClass().getClassLoader();
161 }
162 }
163
164 public ElmoModule(ClassLoader cl) {
165 super();
166 this.cl = cl;
167 }
168
169 public synchronized ClassLoader getClassLoader() {
170 if (urlClassLoader == null) {
171 if (jars.isEmpty()) {
172 urlClassLoader = cl;
173 } else {
174 URL[] array = jars.toArray(new URL[jars.size()]);
175 urlClassLoader = new URLClassLoader(array, cl);
176 }
177 }
178 return urlClassLoader;
179 }
180
181 public QName getGraph() {
182 return graph;
183 }
184
185
186
187
188
189
190
191
192
193 public ElmoModule setGraph(QName graph) {
194 this.graph = graph;
195 return this;
196 }
197
198 @Deprecated
199 public ElmoModule setContext(QName graph) {
200 return setGraph(graph);
201 }
202
203
204
205
206
207
208
209
210 public ElmoModule includeModule(ElmoModule module) {
211 datatypes.addAll(module.datatypes);
212 concepts.addAll(module.concepts);
213 behaviours.addAll(module.behaviours);
214 factories.addAll(module.factories);
215 includedGraphs.add(module.graph);
216 includedGraphs.addAll(module.includedGraphs);
217 datasets.putAll(module.datasets);
218 resources.addAll(module.resources);
219 if (!module.jars.isEmpty()) {
220 cl = new CombinedClassLoader(cl, module.getClassLoader());
221 } else if (!cl.equals(module.cl)) {
222 cl = new CombinedClassLoader(cl, module.cl);
223 }
224 return this;
225 }
226
227 public Set<QName> getIncludedGraphs() {
228 return unmodifiableSet(includedGraphs);
229 }
230
231 public List<Association> getDatatypes() {
232 return unmodifiableList(datatypes);
233 }
234
235
236
237
238
239
240
241
242
243 public ElmoModule addDatatype(Class<?> type, String uri) {
244 datatypes.add(new Association(type, uri));
245 return this;
246 }
247
248 @Deprecated
249 public ElmoModule addLiteral(Class<?> type, String uri) {
250 return addDatatype(type, uri);
251 }
252
253
254
255
256
257
258
259 @Deprecated
260 public ElmoModule addRole(Class<?> role) {
261 if (role.isInterface()) {
262 addConcept(role);
263 } else {
264 addBehaviour(role);
265 }
266 return this;
267 }
268
269
270
271
272
273
274
275
276
277 @Deprecated
278 public ElmoModule addRole(Class<?> role, String type) {
279 if (role.isInterface()) {
280 addConcept(role, type);
281 } else {
282 addBehaviour(role, type);
283 }
284 return this;
285 }
286
287 public List<Association> getConcepts() {
288 return unmodifiableList(concepts);
289 }
290
291
292
293
294
295
296
297 public ElmoModule addConcept(Class<?> concept) {
298 concepts.add(new Association(concept, null));
299 return this;
300 }
301
302
303
304
305
306
307
308
309
310 public ElmoModule addConcept(Class<?> concept, String type) {
311 concepts.add(new Association(concept, type));
312 return this;
313 }
314
315 public List<Association> getBehaviours() {
316 return unmodifiableList(behaviours);
317 }
318
319
320
321
322
323
324
325 public ElmoModule addBehaviour(Class<?> behaviour) {
326 behaviours.add(new Association(behaviour, null));
327 return this;
328 }
329
330
331
332
333
334
335
336
337
338 public ElmoModule addBehaviour(Class<?> behaviour, String type) {
339 behaviours.add(new Association(behaviour, type));
340 return this;
341 }
342
343 public List<Association> getFactories() {
344 return unmodifiableList(factories);
345 }
346
347
348
349
350
351
352
353 public ElmoModule addFactory(Class<?> factory) {
354 factories.add(new Association(factory, null));
355 return this;
356 }
357
358
359
360
361
362
363
364
365
366 public ElmoModule addFactory(Class<?> factory, String type) {
367 factories.add(new Association(factory, type));
368 return this;
369 }
370
371 public Map<URL, String> getDatasets() {
372 return unmodifiableMap(datasets);
373 }
374
375
376
377
378
379
380
381
382 public ElmoModule addDataset(URL dataset) {
383 return addDataset(dataset, dataset.toExternalForm());
384 }
385
386
387
388
389
390
391
392
393
394 public ElmoModule addDataset(URL dataset, String context) {
395 datasets.put(dataset, context);
396 return this;
397 }
398
399 public List<String> getResources() {
400 return unmodifiableList(resources);
401 }
402
403
404
405
406
407
408
409
410 public ElmoModule addResources(String path) {
411 resources.add(path);
412 return this;
413 }
414
415 public List<URL> getJarFileUrls() {
416 return unmodifiableList(jars);
417 }
418
419 public ElmoModule addJarFileUrl(URL jarFile) {
420 jars.add(jarFile);
421 urlClassLoader = null;
422 return this;
423 }
424
425 @Override
426 public int hashCode() {
427 final int prime = 31;
428 int result = 1;
429 result = prime * result + ((cl == null) ? 0 : cl.hashCode());
430 result = prime * result + ((graph == null) ? 0 : graph.hashCode());
431 result = prime * result
432 + ((datasets == null) ? 0 : datasets.hashCode());
433 result = prime * result
434 + ((factories == null) ? 0 : factories.hashCode());
435 result = prime * result
436 + ((includedGraphs == null) ? 0 : includedGraphs.hashCode());
437 result = prime * result + ((jars == null) ? 0 : jars.hashCode());
438 result = prime * result
439 + ((datatypes == null) ? 0 : datatypes.hashCode());
440 result = prime * result
441 + ((resources == null) ? 0 : resources.hashCode());
442 result = prime * result
443 + ((concepts == null) ? 0 : concepts.hashCode());
444 result = prime * result
445 + ((behaviours == null) ? 0 : behaviours.hashCode());
446 result = prime * result
447 + ((urlClassLoader == null) ? 0 : urlClassLoader.hashCode());
448 return result;
449 }
450
451 @Override
452 public boolean equals(Object obj) {
453 if (this == obj)
454 return true;
455 if (obj == null)
456 return false;
457 if (getClass() != obj.getClass())
458 return false;
459 final ElmoModule other = (ElmoModule) obj;
460 if (cl == null) {
461 if (other.cl != null)
462 return false;
463 } else if (!cl.equals(other.cl))
464 return false;
465 if (graph == null) {
466 if (other.graph != null)
467 return false;
468 } else if (!graph.equals(other.graph))
469 return false;
470 if (datasets == null) {
471 if (other.datasets != null)
472 return false;
473 } else if (!datasets.equals(other.datasets))
474 return false;
475 if (factories == null) {
476 if (other.factories != null)
477 return false;
478 } else if (!factories.equals(other.factories))
479 return false;
480 if (includedGraphs == null) {
481 if (other.includedGraphs != null)
482 return false;
483 } else if (!includedGraphs.equals(other.includedGraphs))
484 return false;
485 if (jars == null) {
486 if (other.jars != null)
487 return false;
488 } else if (!jars.equals(other.jars))
489 return false;
490 if (datatypes == null) {
491 if (other.datatypes != null)
492 return false;
493 } else if (!datatypes.equals(other.datatypes))
494 return false;
495 if (resources == null) {
496 if (other.resources != null)
497 return false;
498 } else if (!resources.equals(other.resources))
499 return false;
500 if (concepts == null) {
501 if (other.concepts != null)
502 return false;
503 } else if (!concepts.equals(other.concepts))
504 return false;
505 if (behaviours == null) {
506 if (other.behaviours != null)
507 return false;
508 } else if (!behaviours.equals(other.behaviours))
509 return false;
510 if (urlClassLoader == null) {
511 if (other.urlClassLoader != null)
512 return false;
513 } else if (!urlClassLoader.equals(other.urlClassLoader))
514 return false;
515 return true;
516 }
517
518 @Override
519 public String toString() {
520 if (graph != null)
521 return graph.toString();
522 Set<Package> pkg = new LinkedHashSet<Package>();
523 for (Association concept : concepts) {
524 pkg.add(concept.getJavaClass().getPackage());
525 }
526 return pkg.toString();
527 }
528 }