View Javadoc

1   /*
2    ORDI - Ontology Repository and Data Integration
3   
4    Copyright (c) 2004-2007, OntoText Lab. / SIRMA
5   
6    This library is free software; you can redistribute it and/or modify it under
7    the terms of the GNU Lesser General Public License as published by the Free
8    Software Foundation; either version 2.1 of the License, or (at your option)
9    any later version.
10   This library is distributed in the hope that it will be useful, but WITHOUT
11   ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
12   FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
13   details.
14   You should have received a copy of the GNU Lesser General Public License along
15   with this library; if not, write to the Free Software Foundation, Inc.,
16   59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17   */
18  package com.ontotext.ordi.compatibilitytests;
19  
20  import java.io.BufferedReader;
21  import java.io.IOException;
22  import java.io.InputStream;
23  import java.io.InputStreamReader;
24  import java.util.ArrayList;
25  import java.util.Iterator;
26  import java.util.List;
27  import java.util.NoSuchElementException;
28  import java.util.regex.Matcher;
29  import java.util.regex.Pattern;
30  
31  import junit.framework.TestCase;
32  
33  import org.openrdf.model.Literal;
34  import org.openrdf.model.Resource;
35  import org.openrdf.model.Statement;
36  import org.openrdf.model.URI;
37  import org.openrdf.model.ValueFactory;
38  import org.openrdf.model.impl.ValueFactoryImpl;
39  import org.openrdf.query.Binding;
40  import org.openrdf.query.BindingSet;
41  import org.openrdf.query.impl.EmptyBindingSet;
42  import org.openrdf.query.parser.ParsedQuery;
43  import org.openrdf.query.parser.sparql.SPARQLParser;
44  
45  import com.ontotext.ordi.iterator.CloseableIterator;
46  import com.ontotext.ordi.tripleset.Listener;
47  import com.ontotext.ordi.tripleset.ORDIConst;
48  import com.ontotext.ordi.tripleset.TConnection;
49  import com.ontotext.ordi.tripleset.TSource;
50  import com.ontotext.ordi.tripleset.TStatement;
51  
52  /**
53   * This is base test for compliance with ORDI tripleset model. To test
54   * implementation please inherit this class and in the constructor of the
55   * extending class initialize your implementation and
56   * TestBaseTriplesetModel.source field.
57   * 
58   * TODO: Transaction support semantics is not yet fully determined!
59   * 
60   * @author vassil
61   */
62  public abstract class CompatibilityTests extends TestCase {
63  
64  	protected static final String SAMPLE_TRIPLE_FILE = "/test_triples.nt";
65  	protected static final String SAMPLE_SPARQL_FILE = "/test_triples.sparql";
66  	
67  	protected TSource source;
68  
69  	/*****************************************************************
70  	 * Test: Basic ORDI operations 
71  	 ****************************************************************/
72  	public void testBasicORDIOperationsAdd() throws Exception {
73  		TConnection connection = source.getConnection();
74  		ValueFactory factory = new ValueFactoryImpl();
75  		Resource subj = factory.createBNode();
76  		URI pred = factory.createURI("urn:ordi:compatibilitytest:predicate");
77  		Literal obj = factory.createLiteral("Comaptibilitytest Literal)");
78  		URI namedGraph = factory.createURI("urn:ordi:compatibilitytest:namedgraph");
79  		URI ts = factory.createURI("urn:ordi:compatibilitytest:tripleset");
80  		URI ts2 = factory.createURI("urn:ordi:compatibilitytest:tripleset2");
81  		
82  		TStatement statement = connection.addStatement(subj, pred, obj, namedGraph);
83  		assertEquals(statement.getSubject(), subj);
84  		assertEquals(statement.getPredicate(), pred);
85  		assertEquals(statement.getObject(), obj);
86  		assertEquals(statement.getContext(), namedGraph);
87  		assertEquals(statement.getTriplesetIterator().hasNext(), false);
88  		
89  		statement = connection.addStatement(subj, pred, obj, namedGraph, ts);
90  		assertEquals(statement.getSubject(), subj);
91  		assertEquals(statement.getPredicate(), pred);
92  		assertEquals(statement.getObject(), obj);
93  		assertEquals(statement.getContext(), namedGraph);
94  		assertEquals(statement.getTriplesetIterator().hasNext(), true);
95  		assertEquals(statement.getTriplesetIterator().next(), ts);
96  		
97  		assertEquals(connection.associateTripleset(subj, pred, obj, namedGraph, ts2), 1);
98  		
99  		statement = connection.addStatement(subj, pred, obj, namedGraph, ts);
100 		assertEquals(statement.getSubject(), subj);
101 		assertEquals(statement.getPredicate(), pred);
102 		assertEquals(statement.getObject(), obj);
103 		assertEquals(statement.getContext(), namedGraph);
104 		assertEquals(statement.isMemberOf(ts), true);
105 		assertEquals(statement.isMemberOf(ts2), true);
106 		
107 		assertEquals(connection.removeStatement(subj, pred, obj, namedGraph), 1);
108 		assertEquals(connection.removeStatement(null, null, null, null), 0);		
109 	}
110 	
111 	public void testBasicORDIOperationsAssociate() throws Exception {
112 		TConnection connection = source.getConnection();
113 		ValueFactory factory = new ValueFactoryImpl();
114 		Resource subj = factory.createBNode();
115 		URI pred = factory.createURI("urn:ordi:compatibilitytest:predicate");
116 		Literal obj = factory.createLiteral("Comaptibilitytest Literal");
117 		URI namedGraph = factory.createURI("urn:ordi:compatibilitytest:namedgraph");
118 		URI ts = factory.createURI("urn:ordi:compatibilitytest:tripleset");
119 		
120 		
121 		//FIXME: Uncomment the failiing tests
122 		//assertEquals(connection.associateTripleset(null, null, null, null, ts), 0);
123 		TStatement statement = connection.addStatement(subj, pred, obj, namedGraph);
124 		assertEquals(statement.getSubject(), subj);
125 		assertEquals(statement.getPredicate(), pred);
126 		assertEquals(statement.getObject(), obj);
127 		assertEquals(statement.getContext(), namedGraph);
128 		
129 		for (int i = 0; i < 1000; i++) { 
130 			assertEquals(connection.associateTripleset(subj, pred, 
131 					obj, namedGraph, factory.createURI(ts.toString()+i)), 1);
132 			statement = connection.addStatement(subj, pred, obj, namedGraph);
133 			assertEquals(statement.getSubject(), subj);
134 			assertEquals(statement.getPredicate(), pred);
135 			assertEquals(statement.getObject(), obj);
136 			assertEquals(statement.getContext(), namedGraph);
137 			assertEquals(statement.isMemberOf(factory.createURI(ts.toString()+i)), true);
138 		}
139 		
140 		statement = connection.addStatement(subj, pred, obj, namedGraph);
141 		Iterator<URI> iterator = statement.getTriplesetIterator();
142 		for (int i = 0; i < 1000; i++) {
143 			iterator.next();
144 		}
145 		assertFalse(iterator.hasNext());
146 		
147 		for (int i = 0; i < 1000; i++) {
148 			assertEquals(connection.deassociateTripleset(subj, pred, 
149 					obj, namedGraph, factory.createURI(ts.toString()+i)), 1);
150 			statement = connection.addStatement(subj, pred, obj, namedGraph);
151 			assertEquals(statement.getSubject(), subj);
152 			assertEquals(statement.getPredicate(), pred);
153 			assertEquals(statement.getObject(), obj);
154 			assertEquals(statement.getContext(), namedGraph);
155 			assertEquals(statement.isMemberOf(factory.createURI(ts.toString()+i)), false);
156 		}
157 		
158 		statement = connection.addStatement(subj, pred, obj, namedGraph);
159 		assertEquals(statement.getSubject(), subj);
160 		assertEquals(statement.getPredicate(), pred);
161 		assertEquals(statement.getObject(), obj);
162 		assertEquals(statement.getContext(), namedGraph);
163 		assertEquals(statement.getTriplesetIterator().hasNext(), false);
164 		
165 		assertEquals(connection.removeStatement(subj, pred, obj, namedGraph), 1);
166 		assertEquals(connection.removeStatement(null, null, null, null), 0);
167 	}
168 	
169 	public void testBasicORDIOperationRemove() throws Exception {
170 		TConnection connection = source.getConnection();
171 		NTParser parser = new NTParser(this.getClass().getResourceAsStream(SAMPLE_TRIPLE_FILE));
172 		ValueFactory factory = new ValueFactoryImpl();
173 		URI namedGraph = factory.createURI("urn:ordi:compatibilitytest:namedgraph");
174 		URI namedGraph2 = factory.createURI("urn:ordi:compatibilitytest:namedgraph2");
175 		URI namedGraph3 = factory.createURI("urn:ordi:compatibilitytest:namedgraph3");
176 		
177 		Statement st = null;
178 		Statement lastSt = null;
179 		int count = 0;
180 		while((st = parser.next()) != null) {			
181 			connection.addStatement(st.getSubject(), st.getPredicate(),
182 					st.getObject(), namedGraph);
183 			connection.addStatement(st.getSubject(), st.getPredicate(), 
184 					st.getObject(), namedGraph2);
185 			connection.addStatement(st.getSubject(), st.getPredicate(), 
186 					st.getObject(), namedGraph3);
187 			lastSt = st;
188 			count++;
189 		}
190 
191 		parser = new NTParser(this.getClass().getResourceAsStream(SAMPLE_TRIPLE_FILE));
192 		while((st = parser.next()) != null) {
193 			assertEquals(connection.removeStatement(st.getSubject(), st.getPredicate(),
194 					st.getObject(), namedGraph), 1);
195 		}
196 		
197 		assertEquals(connection.removeStatement(null, null, null, namedGraph2), count);
198 		
199 		int removed = 0;
200 		removed = connection.removeStatement(null, lastSt.getPredicate(), lastSt.getObject(), namedGraph3);
201 		assertTrue(removed > 0);
202 		count -= removed;
203 		removed = connection.removeStatement(lastSt.getSubject(), null,
204 				null, namedGraph3);
205 		assertTrue(removed > 0);
206 		count -= removed;
207 		removed = connection.removeStatement(null, null, null, namedGraph3);
208 		assertTrue(removed > 0);
209 		count -= removed;
210 		assertTrue(count == 0);
211 		assertEquals(connection.removeStatement(null, null, null, null), 0);
212 	}
213 	
214 	public void testBasicORDIOperationSearch() throws Exception {    
215 		TConnection connection = source.getConnection();
216 		connection.removeStatement(null, null, null, null);
217 		
218 		NTParser parser = new NTParser(this.getClass().getResourceAsStream(SAMPLE_TRIPLE_FILE));
219 		ValueFactory factory = new ValueFactoryImpl();
220 		URI namedGraph = factory.createURI("urn:ordi:compatibilitytest:namedgraph");
221 		URI namedGraph2 = factory.createURI("urn:ordi:compatibilitytest:namedgraph2");
222 		URI namedGraph3 = factory.createURI("urn:ordi:compatibilitytest:namedgraph3");
223 		URI ts = factory.createURI("urn:ordi:compatibilitytest:tripleset");
224 		URI ts2 = factory.createURI("urn:ordi:compatibilitytest:tripleset2");
225 		
226 		Statement st = null;
227 		Statement lastSt = null;
228 		while((st = parser.next()) != null) {
229 			connection.addStatement(st.getSubject(), st.getPredicate(),
230 					st.getObject(), namedGraph);
231 			connection.addStatement(st.getSubject(), st.getPredicate(),
232 					st.getObject(), namedGraph2, ts);
233 			connection.addStatement(st.getSubject(), st.getPredicate(),
234 					st.getObject(), namedGraph3, ts, ts2);
235 			
236 			assertEquals(countIteratorResults(connection.search(st.getSubject(), 
237 					st.getPredicate(), st.getObject(), namedGraph, null)), 1);
238 			assertEquals(countIteratorResults(connection.search(st.getSubject(), 
239 					st.getPredicate(), st.getObject(), namedGraph2, ts)), 1);
240 			assertEquals(countIteratorResults(connection.search(st.getSubject(), 
241 					st.getPredicate(), st.getObject(), namedGraph2, ts2)), 0);
242 			assertEquals(countIteratorResults(connection.search(st.getSubject(), 
243 					st.getPredicate(), st.getObject(), null, ts)), 2);
244 			lastSt = st;
245 		}
246 		
247 		int result = countIteratorResults(connection.search(null, lastSt.getPredicate(), 
248 				lastSt.getObject(), namedGraph, null));
249 		assertEquals(connection.removeStatement(null, lastSt.getPredicate(), 
250 				lastSt.getObject(), namedGraph), result);
251 		
252 		result = countIteratorResults(connection.search(null, lastSt.getPredicate(), 
253 				lastSt.getObject(), namedGraph2, ts2));
254 		assertEquals(0, result);
255 		
256 		result = countIteratorResults(connection.search(lastSt.getSubject(), null, 
257 				lastSt.getObject(), namedGraph2, null));
258 		assertEquals(connection.removeStatement(lastSt.getSubject(), null, 
259 				lastSt.getObject(), namedGraph2), result);
260 		
261 		result = countIteratorResults(connection.search(lastSt.getSubject(), lastSt.getPredicate(), 
262 				null, namedGraph3, null));
263 		assertEquals(connection.removeStatement(lastSt.getSubject(), lastSt.getPredicate(), 
264 				null, namedGraph3), result);
265 		
266 		connection.removeStatement(null, null, null, null);
267 	}
268 	
269 	/*****************************************************************
270 	 * Test: Listeners 
271 	 ****************************************************************/	
272 	public void testListeners() throws Exception {
273 /*		TConnection connection = source.getConnection();
274 		final List<TStatement> added = new ArrayList<TStatement>();
275 		final List<TStatement> removed = new ArrayList<TStatement>();
276 		final List<TStatement> associated = new ArrayList<TStatement>();
277 		final List<TStatement> deassociated = new ArrayList<TStatement>();
278 		final List<Listener> commited = new ArrayList<Listener>();
279 		final List<Listener> rollback = new ArrayList<Listener>();
280 		final List<Listener> closed = new ArrayList<Listener>();
281 		
282 		connection.addListener(new Listener() {
283 			public void statementAdded(TStatement statement) {
284 				added.add(statement);
285 			}
286 			
287 			public void statementInferred(TStatement statement) {
288 				added.add(statement);
289 			}
290 
291 			public void statementRemoved(TStatement statement) {
292 				removed.add(statement);
293 			}
294 
295 			public void statementAssociated(TStatement statement) {
296 				associated.add(statement);
297 			}
298 
299 			public void statementDeassociated(TStatement statement) {
300 				deassociated.add(statement);
301 			}
302 
303 			public void onCommit() {
304 				commited.add(this);
305 			}
306 
307 			public void onRollback() {
308 				rollback.add(this);
309 			}
310 
311 			public void onClose() {
312 				closed.add(this);
313 			}
314 		});
315 		assertEquals(connection.listListeners().size(), 1);
316 		
317 		ValueFactory factory = new ValueFactoryImpl();
318 		Resource subj = factory.createBNode();
319 		URI pred = factory.createURI("urn:ordi:compatibilitytest:predicate");
320 		Literal obj = factory.createLiteral("Comaptibilitytest Literal)");
321 		URI namedGraph = factory.createURI("urn:ordi:compatibilitytest:namedgraph");
322 		URI namedGraph2 = factory.createURI("urn:ordi:compatibilitytest:namedgraph2");
323 		URI ts = factory.createURI("urn:ordi:compatibilitytest:tripleset");
324 		
325 		TStatement statement = connection.addStatement(subj, pred, obj, namedGraph);
326 		assertEquals(added.size(), 1);
327 		assertEquals(statement, added.get(0));
328 		statement = connection.addStatement(subj, pred, obj, namedGraph2);
329 		assertEquals(added.size(), 2);
330 		assertEquals(statement, added.get(1));
331 		
332 		assertEquals(connection.associateTripleset(null, null, null, null, ts), 2);
333 		assertEquals(associated.size(), 2);
334 		assertEquals(connection.addStatement(subj, pred, obj, namedGraph, ts),
335 				associated.get(0));
336 		assertEquals(connection.addStatement(subj, pred, obj, namedGraph2, ts), 
337 				associated.get(1));
338 		
339 		assertEquals(connection.deassociateTripleset(null, null, null, null, ts), 2);
340 		assertEquals(deassociated.size(), 2);
341 		assertEquals(connection.addStatement(subj, pred, obj, namedGraph),
342 				deassociated.get(0));
343 		assertEquals(connection.addStatement(subj, pred, obj, namedGraph2), 
344 				deassociated.get(1));
345 		
346 		assertEquals(connection.removeStatement(null, null, null, null), 2);
347 		assertEquals(removed.size(), 2);
348 		assertEquals(connection.addStatement(subj, pred, obj, namedGraph),
349 				removed.get(0));
350 		assertEquals(connection.addStatement(subj, pred, obj, namedGraph2), 
351 				removed.get(1));
352 		assertEquals(connection.removeStatement(null, null, null, null), 2);
353 		
354 		connection.commit();
355 		assertEquals(commited.size(), 1);
356 		connection.rollback();
357 		assertEquals(rollback.size(), 1);
358 		connection.close();
359 		assertEquals(closed.size(), 1);
360 		
361 		for(Iterator<Listener> iter = connection.listListeners().iterator(); iter.hasNext();) {
362 			connection.removeListener(iter.next());
363 		}
364 		assertEquals(connection.listListeners().size(), 0);
365 */	}
366 	
367 	/*****************************************************************
368 	 * Test: SPARQL Querying
369 	 ****************************************************************/
370 	public void testSPARQLSupport() throws Exception {
371 		/*TConnection connection = source.getConnection();
372 		NTParser parser = new NTParser(this.getClass().getResourceAsStream(SAMPLE_TRIPLE_FILE));
373 		ValueFactory factory = new ValueFactoryImpl();
374 		URI defaultGraph = factory.createURI(ORDIConst.DEFAULT_GRAPH);
375 		URI namedGraph = factory.createURI("urn:ordi:compatibilitytest:namedgraph");
376 		URI namedGraph2 = factory.createURI("urn:ordi:compatibilitytest:namedgraph2");
377 		Statement st = null;
378 		
379 		while ((st = parser.next()) != null) {
380 			connection.addStatement(st.getSubject(), st.getPredicate(), 
381 					st.getObject(), defaultGraph);
382 			connection.addStatement(st.getSubject(), st.getPredicate(), 
383 					st.getObject(), namedGraph);
384 			connection.addStatement(st.getSubject(), st.getPredicate(), 
385 					st.getObject(), namedGraph2);
386 		}
387 		
388 		SPARQLQueryIterator iter = new SPARQLQueryIterator(
389 				this.getClass().getResourceAsStream(SAMPLE_SPARQL_FILE));
390 		while (iter.hasNext()) {
391 			Object[] queryData = iter.next();
392 			if (queryData[2].toString().trim().length() == 0) {
393 				throw new RuntimeException(String.format("Query [%s] has no query text assigned.", queryData[2]));
394 			}
395 			SPARQLParser sparqlParser = new SPARQLParser();
396 			ParsedQuery query = sparqlParser.parseQuery("SELECT * WHERE {?s ?p ?o. ?o ?p1 ?o2.} ", namedGraph.toString());
397 			CloseableIterator<? extends BindingSet> result = 
398 				connection.evaluate(query.getTupleExpr(), new EmptyBindingSet(), true);
399 
400 			int count = 0;
401 			while (result.hasNext()) {
402 				BindingSet solution = result.next();
403 				count++;
404 				for (Iterator<Binding> i = solution.iterator(); i.hasNext();) {
405 					Binding binding = i.next();
406 					binding.getName();
407 					binding.getValue();
408 				}
409 			}
410 			
411 			assertEquals(queryData[1], count);
412 		}*/
413 	}
414 	
415 	/*****************************************************************
416 	 * Test: Concurrent access
417 	 ****************************************************************/
418 	//TODO: Add methods to test the concurrent access
419 	
420 	
421 	/*****************************************************************
422 	 * Helper methods and classes
423 	 ****************************************************************/
424 	private int countIteratorResults(Iterator<?> iterator) {
425 		int count = 0;
426 		while (iterator.hasNext()) {
427 			iterator.next();
428 			count++;
429 		}
430 		return count;
431 	}
432 	
433 	private class SPARQLQueryIterator implements Iterator<Object> {
434 		
435 		private BufferedReader reader;
436 		private Pattern regexp;
437 		private Object[] next;
438 		private int lineNumber = 1;
439 		private String line;
440 		
441 		public SPARQLQueryIterator(InputStream stream) {
442 			reader = new BufferedReader(new InputStreamReader(stream));
443 			regexp = Pattern.compile("\\[(.+):(\\d+)\\]");
444 			try {
445 				line = reader.readLine();
446 			}
447 			catch (IOException e) {
448 				throw new RuntimeException("Could not process file!", e);
449 			}
450 		}
451 		
452 		public Object[] next() {
453 			if (hasNext()) {
454 				Object[] result = next;
455 				next = null;
456 				return result;
457 			}
458 			throw new NoSuchElementException();
459 		}
460 		
461 		public boolean hasNext() {
462 			if (next != null) {
463 				return true;
464 			}
465 			try {
466 				while (line != null) {
467 					if (line.startsWith("#") || line.trim().length() == 0) {
468 					}
469 					else if (regexp.matcher(line).matches()) {
470 						if (next != null) {
471 							return true;
472 						}
473 						next = new Object[3];
474 						Matcher match = regexp.matcher(line);
475 						match.matches();
476 						next[0] = match.group(1);
477 						next[1] = Integer.parseInt(match.group(2));
478 						next[2] = new StringBuffer();
479 					}
480 					else {
481 						if (next == null) {
482 							next = null;
483 						}
484 						((StringBuffer) next[2]).append(line);
485 						((StringBuffer) next[2]).append('\n');
486 					}
487 					line = reader.readLine();
488 					lineNumber++;
489 				}
490 				return next != null;
491 			}
492 			catch (Exception e) {
493 				throw new RuntimeException("Format problem on line " + lineNumber);
494 			}
495 		}
496 		
497 		public void remove() {
498 			throw new UnsupportedOperationException(
499 					"Remove is not allowed for this iterator!");
500 		}
501 	}
502 }