/* * Created on Mar 17, 2005 */ package edu.mit.simile.fresnel.selection; import java.util.HashMap; import java.util.Iterator; import java.util.Vector; import org.openrdf.model.Resource; import org.openrdf.model.Statement; import org.openrdf.model.URI; import org.openrdf.model.Value; import org.openrdf.repository.Repository; import org.openrdf.repository.RepositoryConnection; import org.openrdf.repository.RepositoryException; import org.openrdf.repository.RepositoryResult; import fr.inria.jfresnel.fsl.FSLHierarchyStore; import fr.inria.jfresnel.fsl.FSLNSResolver; import fr.inria.jfresnel.fsl.FSLPath; import fr.inria.jfresnel.fsl.sesame.FSLSesameEvaluator; /** * Selector based on a Fresnel Selector Expression, composed from * the Fresnel Selector Language. canSelect(Resource) and canSelect(Value) * are indeterminate for this selector; with no Repository source, it's impossible * to tell, so false is returned by default. * * @author ryanlee */ public class FSESelector implements ISelector { /** * The original FSE. */ private String _fse; /** * The context of the FSE */ private short _use; /** * Evaluates FSE's into paths */ private FSLSesameEvaluator _eval; /** * Namespace resolver for path evaluator */ private FSLNSResolver _nsr; /** * Hierarchy store path evaluator; expected to do nothing for now. */ private FSLHierarchyStore _fhs; /** * Create an FSESelector based on its string representation. * * @param fse The <code>String</code> representation of the FSE */ public FSESelector(String fse, short use, FSLNSResolver nsr) { this._fse = fse; this._use = use; this._nsr = nsr; this._fhs = new FSLHierarchyStore(); this._eval = new FSLSesameEvaluator(this._nsr, this._fhs); } /** * This may or may not work. If the path expression is not compatible with selecting statements * based on the starting point of the selected parameter, an exception will be thrown. * * @see edu.mit.simile.fresnel.selection.ISelector#selectStatements(Repository, Resource) */ public Iterator<Statement> selectStatements(Repository in, Resource selected) throws InvalidResultSetException { this._eval.setRepository(in); HashMap<Statement, Object> start = new HashMap<Statement, Object>(); try { RepositoryConnection conn = in.getConnection(); RepositoryResult<Statement> results = conn.getStatements(selected, null, null, true); while (results.hasNext()) { start.put(results.next(), null); } conn.close(); } catch (RepositoryException e) { throw new InvalidResultSetException("Repository exception encountered generating starting points: " + this._fse); } FSLPath p = FSLPath.pathFactory(this._fse, this._nsr, this._use); Vector<Statement> statements = new Vector<Statement>(); try { Vector<Vector<Object>> paths = this._eval.evaluatePath(p, start); for (int i = 0; i < paths.size() ; i++ ) { Vector<Object> v = paths.get(i); statements.add((Statement) v.get(v.size()-1)); } } catch (ClassCastException e) { throw new InvalidResultSetException("This expression does not return statements: " + this._fse); } this._eval.unsetRepository(); return statements.iterator(); } /** * @see edu.mit.simile.fresnel.selection.ISelector#selectResources(Repository) */ public Iterator<Resource> selectResources(Repository in) throws InvalidResultSetException { this._eval.setRepository(in); FSLPath p = FSLPath.pathFactory(this._fse, this._nsr, this._use); Vector<Vector<Object>> paths = this._eval.evaluatePath(p); Vector<Resource> resources = new Vector<Resource>(); try { for (int i = 0; i < paths.size() ; i++ ) { Vector<Object> v = paths.get(i); resources.add((Resource) v.get(v.size()-1)); } } catch (ClassCastException e) { throw new InvalidResultSetException("This expression does not return resources: " + this._fse); } this._eval.unsetRepository(); return resources.iterator(); } /** * @see edu.mit.simile.fresnel.selection.ISelector#selectNodes(Repository) */ public Iterator<Value> selectNodes(Repository in) throws InvalidResultSetException { this._eval.setRepository(in); FSLPath p = FSLPath.pathFactory(this._fse, this._nsr, this._use); Vector<Vector<Object>> paths = this._eval.evaluatePath(p); Vector<Value> values = new Vector<Value>(); try { for (int i = 0; i < paths.size() ; i++ ) { Vector<Object> v = paths.get(i); values.add((Value) v.get(v.size()-1)); } } catch (ClassCastException e) { throw new InvalidResultSetException("This expression does not return values: " + this._fse); } this._eval.unsetRepository(); return values.iterator(); } /** * @see edu.mit.simile.fresnel.selection.ISelector#canSelectStatements() */ public boolean canSelectStatements() { return true; } /** * @see edu.mit.simile.fresnel.selection.ISelector#canSelectResources() */ public boolean canSelectResources() { return true; } /** * @see edu.mit.simile.fresnel.selection.ISelector#canSelectNodes() */ public boolean canSelectNodes() { return true; } /** * @see edu.mit.simile.fresnel.selection.ISelector#canSelect(Repository, Resource, URI) */ public boolean canSelect(Repository in, Resource selected, URI prop) { // if (prop.toString().equals("fsl://"+_fse)) // return true; return (prop.toString().equals("fsl://"+_fse)); // try { // Iterator<Statement> si = selectStatements(in, selected); // while (si.hasNext()) { // if (si.next().getPredicate().equals(prop)) return true; // } // } catch (InvalidResultSetException e) { // return false; // } // return false; } /** * @see edu.mit.simile.fresnel.selection.ISelector#canSelect(Repository, Resource) */ public boolean canSelect(Repository in, Resource selected) { if (_fse.equals("*")) /* will iterate all resources otherwise */ return true; try { Iterator<Resource> ri = selectResources(in); while (ri.hasNext()) { if (ri.next().equals(selected)) return true; } } catch (InvalidResultSetException e) { // TODO these exceptions should be logged. return false; } return false; } /** * This method will always return false. * * @see edu.mit.simile.fresnel.selection.ISelector#canSelect(Repository, Value) */ public boolean canSelect(Repository in, Value selected) { return false; } public String get_fse() { return _fse; } }