jena-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From jpz6311...@apache.org
Subject svn commit: r1519358 [2/5] - in /jena/trunk/jena-spatial: ./ src/ src/main/ src/main/java/ src/main/java/examples/ src/main/java/jena/ src/main/java/org/ src/main/java/org/apache/ src/main/java/org/apache/jena/ src/main/java/org/apache/jena/query/ src/...
Date Mon, 02 Sep 2013 06:46:21 GMT
Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialIndexException.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialIndexException.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialIndexException.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialIndexException.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,31 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial;
+
+import com.hp.hpl.jena.query.QueryExecException;
+
+public class SpatialIndexException extends QueryExecException 
+{
+    public SpatialIndexException() { super() ; }
+    public SpatialIndexException(Throwable cause) { super(cause) ; }
+    public SpatialIndexException(String msg) { super(msg) ; }
+    public SpatialIndexException(String msg, Throwable cause) { super(msg, cause) ; }
+
+}
+

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialIndexException.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialIndexLucene.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialIndexLucene.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialIndexLucene.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialIndexLucene.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,258 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial;
+
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.List;
+
+import org.apache.lucene.analysis.Analyzer;
+import org.apache.lucene.analysis.standard.StandardAnalyzer;
+import org.apache.lucene.document.Document;
+import org.apache.lucene.document.Field;
+import org.apache.lucene.document.FieldType;
+import org.apache.lucene.index.DirectoryReader;
+import org.apache.lucene.index.IndexReader;
+import org.apache.lucene.index.IndexWriter;
+import org.apache.lucene.index.IndexWriterConfig;
+import org.apache.lucene.index.IndexableField;
+import org.apache.lucene.queries.function.ValueSource;
+import org.apache.lucene.queryparser.classic.ParseException;
+import org.apache.lucene.search.Filter;
+import org.apache.lucene.search.IndexSearcher;
+import org.apache.lucene.search.MatchAllDocsQuery;
+import org.apache.lucene.search.ScoreDoc;
+import org.apache.lucene.search.Sort;
+import org.apache.lucene.search.TopDocs;
+import org.apache.lucene.spatial.SpatialStrategy;
+import org.apache.lucene.spatial.prefix.RecursivePrefixTreeStrategy;
+import org.apache.lucene.spatial.prefix.tree.GeohashPrefixTree;
+import org.apache.lucene.spatial.prefix.tree.SpatialPrefixTree;
+import org.apache.lucene.spatial.query.SpatialArgs;
+import org.apache.lucene.spatial.query.SpatialOperation;
+import org.apache.lucene.store.Directory;
+import org.apache.lucene.util.Version;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import com.hp.hpl.jena.graph.Node;
+import com.hp.hpl.jena.graph.NodeFactory;
+import com.hp.hpl.jena.sparql.util.NodeFactoryExtra;
+import com.spatial4j.core.shape.Point;
+import com.spatial4j.core.shape.Shape;
+
+public class SpatialIndexLucene implements SpatialIndex {
+	private static Logger log = LoggerFactory
+			.getLogger(SpatialIndexLucene.class);
+
+	private static int MAX_N = 10000;
+	public static final Version VER = Version.LUCENE_43;
+
+	public static final FieldType ftIRI;
+	static {
+		ftIRI = new FieldType();
+		ftIRI.setTokenized(false);
+		ftIRI.setStored(true);
+		ftIRI.setIndexed(true);
+		ftIRI.freeze();
+	}
+	// public static final FieldType ftText = TextField.TYPE_NOT_STORED ;
+	// Bigger index, easier to debug!
+	// public static final FieldType ftText = TextField.TYPE_STORED ;
+
+	private final EntityDefinition docDef;
+	private final Directory directory;
+	private IndexWriter indexWriter;
+	private Analyzer analyzer = new StandardAnalyzer(VER);
+
+	/**
+	 * The Lucene spatial {@link SpatialStrategy} encapsulates an approach to
+	 * indexing and searching shapes, and providing distance values for them.
+	 * It's a simple API to unify different approaches. You might use more than
+	 * one strategy for a shape as each strategy has its strengths and
+	 * weaknesses.
+	 * <p />
+	 * Note that these are initialized with a field name.
+	 */
+	private SpatialStrategy strategy;
+
+	public SpatialIndexLucene(Directory directory, EntityDefinition def) {
+		this.directory = directory;
+		this.docDef = def;
+
+		int maxLevels = 11;// results in sub-meter precision for geohash
+		// This can also be constructed from SpatialPrefixTreeFactory
+		SpatialPrefixTree grid = new GeohashPrefixTree(SpatialQuery.ctx, maxLevels);
+
+		this.strategy = new RecursivePrefixTreeStrategy(grid, def.getGeoField());
+
+		//this.strategy = new PointVectorStrategy(ctx, def.getGeoField());
+		
+		// force creation of the index if it don't exist
+		// otherwise if we get a search before data is written we get an
+		// exception
+		startIndexing();
+		finishIndexing();
+	}
+
+	public Directory getDirectory() {
+		return directory;
+	}
+
+	public Analyzer getAnalyzer() {
+		return analyzer;
+	}
+
+	@Override
+	public void startIndexing() {
+		try {
+			IndexWriterConfig wConfig = new IndexWriterConfig(VER, analyzer);
+			indexWriter = new IndexWriter(directory, wConfig);
+		} catch (IOException e) {
+			exception(e);
+		}
+	}
+
+	@Override
+	public void finishIndexing() {
+		try {
+			indexWriter.commit();
+			indexWriter.close();
+			indexWriter = null;
+		} catch (IOException e) {
+			exception(e);
+		}
+	}
+
+	@Override
+	public void abortIndexing() {
+		try {
+			indexWriter.rollback();
+		} catch (IOException ex) {
+			exception(ex);
+		}
+	}
+
+	@Override
+	public void close() {
+		if (indexWriter != null)
+			try {
+				indexWriter.close();
+			} catch (IOException ex) {
+				exception(ex);
+			}
+	}
+
+	@Override
+	public void add(String entityURI, Shape... shapes) {
+		try {
+			boolean autoBatch = (indexWriter == null);
+
+			Document doc = doc(entityURI, shapes);
+			if (autoBatch)
+				startIndexing();
+			indexWriter.addDocument(doc);
+			if (autoBatch)
+				finishIndexing();
+		} catch (IOException e) {
+			exception(e);
+		}
+	}
+
+	private Document doc(String entityURI, Shape... shapes) {
+		Document doc = new Document();
+		Field entField = new Field(docDef.getEntityField(), entityURI, ftIRI);
+		doc.add(entField);
+		for (Shape shape : shapes) {
+			for (IndexableField f : strategy.createIndexableFields(shape)) {
+				doc.add(f);
+			}
+		}
+
+		return doc;
+	}
+	
+	@Override
+	public List<Node> query(Shape shape, int limit, SpatialOperation operation) {
+		try {
+			// Upgrade at Java7 ...
+			IndexReader indexReader = DirectoryReader.open(directory);
+			try {
+				return query$(indexReader, shape, limit, operation);
+			} finally {
+				indexReader.close();
+			}
+		} catch (Exception ex) {
+			exception(ex);
+			return null;
+		}
+	}
+	
+	private List<Node> query$(IndexReader indexReader, Shape shape, int limit, SpatialOperation operation) throws ParseException,
+			IOException {
+		if (limit <= 0)
+			limit = MAX_N;
+
+		IndexSearcher indexSearcher = new IndexSearcher(indexReader);
+		Point pt = shape.getCenter();
+		ValueSource valueSource = strategy.makeDistanceValueSource(pt);// the
+																		// distance
+																		// (in
+																		// degrees)
+		Sort distSort = new Sort(valueSource.getSortField(false))
+				.rewrite(indexSearcher);
+		SpatialArgs args = new SpatialArgs(operation, shape);
+		args.setDistErr(0.0);
+		Filter filter = strategy.makeFilter(args);
+		TopDocs docs = indexSearcher.search(new MatchAllDocsQuery(), filter,
+				limit, distSort);
+
+		List<Node> results = new ArrayList<Node>();
+
+		// Align and DRY with Solr.
+		for (ScoreDoc sd : docs.scoreDocs) {
+			Document doc = indexSearcher.doc(sd.doc);
+			String[] values = doc.getValues(docDef.getEntityField());
+			for (String v : values) {
+				Node n = NodeFactory.createURI(v);
+				results.add(n);
+			}
+		}
+		return results;
+	}
+
+	@Override
+	public EntityDefinition getDocDef() {
+		return docDef;
+	}
+
+	private Node entryToNode(String v) {
+		// TEMP
+		return NodeFactoryExtra.createLiteralNode(v, null, null);
+	}
+
+	private static void exception(Exception ex) {
+		throw new SpatialIndexException(ex);
+	}
+
+
+
+
+
+}

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialIndexLucene.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialIndexSolr.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialIndexSolr.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialIndexSolr.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialIndexSolr.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,177 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.apache.lucene.spatial.SpatialStrategy;
+import org.apache.lucene.spatial.prefix.RecursivePrefixTreeStrategy;
+import org.apache.lucene.spatial.prefix.tree.GeohashPrefixTree;
+import org.apache.lucene.spatial.prefix.tree.SpatialPrefixTree;
+import org.apache.lucene.spatial.query.SpatialOperation;
+import org.apache.solr.client.solrj.SolrQuery;
+import org.apache.solr.client.solrj.SolrServer;
+import org.apache.solr.client.solrj.SolrServerException;
+import org.apache.solr.client.solrj.response.QueryResponse;
+import org.apache.solr.common.SolrDocument;
+import org.apache.solr.common.SolrDocumentList;
+import org.apache.solr.common.SolrInputDocument;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import com.hp.hpl.jena.graph.Node;
+import com.hp.hpl.jena.graph.NodeFactory;
+import com.hp.hpl.jena.sparql.util.NodeFactoryExtra;
+import com.spatial4j.core.shape.Shape;
+
+public class SpatialIndexSolr implements SpatialIndex {
+	private static Logger log = LoggerFactory.getLogger(SpatialIndexSolr.class);
+	private final SolrServer solrServer;
+	private EntityDefinition docDef;
+	private SpatialPrefixTree grid;
+
+	/**
+	 * The Lucene spatial {@link SpatialStrategy} encapsulates an approach to
+	 * indexing and searching shapes, and providing distance values for them.
+	 * It's a simple API to unify different approaches. You might use more than
+	 * one strategy for a shape as each strategy has its strengths and
+	 * weaknesses.
+	 * <p />
+	 * Note that these are initialized with a field name.
+	 */
+	private SpatialStrategy strategy;
+
+	public SpatialIndexSolr(SolrServer server, EntityDefinition def) {
+		this.solrServer = server;
+		this.docDef = def;
+
+		int maxLevels = 11;// results in sub-meter precision for geohash
+		// This can also be constructed from SpatialPrefixTreeFactory
+		grid = new GeohashPrefixTree(SpatialQuery.ctx, maxLevels);
+
+		this.strategy = new RecursivePrefixTreeStrategy(grid, def.getGeoField());
+	}
+
+	@Override
+	public void startIndexing() {
+	}
+
+	@Override
+	public void finishIndexing() {
+		try {
+			solrServer.commit();
+		} catch (Exception ex) {
+			exception(ex);
+		}
+	}
+
+	@Override
+	public void abortIndexing() {
+		try {
+			solrServer.rollback();
+		} catch (Exception ex) {
+			exception(ex);
+		}
+	}
+
+	@Override
+	public void close() {
+		if (solrServer != null)
+			solrServer.shutdown();
+	}
+
+	@Override
+	public void add(String entityURI, Shape... shapes) {
+
+		// log.info("Add entity: "+entityURI) ;
+		try {
+			SolrInputDocument doc = solrDoc(entityURI, shapes);
+			solrServer.add(doc);
+		} catch (Exception e) {
+			exception(e);
+		}
+	}
+
+	private SolrInputDocument solrDoc(String entityURI, Shape... shapes) {
+		SolrInputDocument doc = new SolrInputDocument();
+		doc.addField(docDef.getEntityField(), entityURI);
+		if (shapes.length != 1) {
+			throw new SpatialIndexException(
+					"Solr spatial only supports indexing one shape a time, but provided: "
+							+ shapes.length + " shapes.");
+		}
+		doc.addField(docDef.getGeoField(), SpatialQuery.ctx.toString(shapes[0]));
+
+		return doc;
+	}
+
+	@Override
+	public List<Node> query(Shape shape, int limit, SpatialOperation operation) {
+
+		SolrDocumentList solrResults = solrQuery(shape, limit, operation);
+		List<Node> results = new ArrayList<Node>();
+
+		for (SolrDocument sd : solrResults) {
+			String uriStr = (String) sd.getFieldValue(docDef.getEntityField());
+			// log.info("Entity: "+uriStr) ;
+			results.add(NodeFactory.createURI(uriStr));
+		}
+
+		if (limit > 0 && results.size() > limit)
+			results = results.subList(0, limit);
+
+		return results;
+	}
+
+	private SolrDocumentList solrQuery(Shape shape, int limit,
+			SpatialOperation operation) {
+		SolrQuery sq = new SolrQuery();
+		sq.setQuery("*:*");
+		sq.setFilterQueries(docDef.getGeoField() + ":\"" + operation.toString()
+				+ "(" + SpatialQuery.ctx.toString(shape) + ") distErrPct=0\"");
+		//System.out.println("SolrQuery: " +sq.toString());
+		try {
+			QueryResponse rsp = solrServer.query(sq);
+			SolrDocumentList docs = rsp.getResults();
+			return docs;
+		} catch (SolrServerException e) {
+			exception(e);
+			return null;
+		}
+	}
+
+	@Override
+	public EntityDefinition getDocDef() {
+		return docDef;
+	}
+
+	private Node entryToNode(String v) {
+		// TEMP
+		return NodeFactoryExtra.createLiteralNode(v, null, null);
+	}
+
+	public SolrServer getServer() {
+		return solrServer;
+	}
+
+	private static Void exception(Exception ex) {
+		throw new SpatialIndexException(ex);
+	}
+}

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialIndexSolr.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialPredicatePair.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialPredicatePair.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialPredicatePair.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialPredicatePair.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,74 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial;
+
+import com.hp.hpl.jena.graph.Node;
+
+public class SpatialPredicatePair {
+
+	private Node latitudePredicate;
+	private Node longitudePredicate;
+
+	public SpatialPredicatePair(Node latitudePredicate, Node longitudePredicate) {
+		super();
+		this.latitudePredicate = latitudePredicate;
+		this.longitudePredicate = longitudePredicate;
+	}
+
+	public Node getLatitudePredicate() {
+		return latitudePredicate;
+	}
+
+	public Node getLongitudePredicate() {
+		return longitudePredicate;
+	}
+
+	@Override
+	public int hashCode() {
+		return latitudePredicate.hashCode() * 7 + longitudePredicate.hashCode()
+				* 13;
+	}
+
+	@Override
+	public boolean equals(Object otherObject) {
+		// a quick test to see if the objects are identical
+		if (this == otherObject)
+			return true;
+
+		// must return false if the explicit parameter is null
+		if (otherObject == null)
+			return false;
+
+		// if the classes don't match, they can't be equal
+		if (getClass() != otherObject.getClass())
+			return false;
+
+		// now we know otherObject is a non-null Employee
+		SpatialPredicatePair other = (SpatialPredicatePair) otherObject;
+
+		// test whether the fields have identical values
+		return latitudePredicate.equals(other.latitudePredicate)
+				&& longitudePredicate == other.longitudePredicate;
+	}
+	
+	@Override
+	public String toString(){
+		return "[ " + latitudePredicate.toString() + ", " + longitudePredicate.toString() + " ]";
+	}
+}

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialPredicatePair.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialPredicatePairValue.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialPredicatePairValue.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialPredicatePairValue.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialPredicatePairValue.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,110 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial;
+
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import com.hp.hpl.jena.graph.Node;
+
+public class SpatialPredicatePairValue {
+
+	private static Logger log = LoggerFactory
+			.getLogger(SpatialPredicatePairValue.class);
+
+	public SpatialPredicatePairValue(SpatialPredicatePair pair) {
+		this.pair = pair;
+	}
+
+	private SpatialPredicatePair pair;
+	private Double latitudeValue;
+	private Double longitudeValue;
+
+	public Double getLatitudeValue() {
+		return latitudeValue;
+	}
+
+	public Double getLongitudeValue() {
+		return longitudeValue;
+	}
+
+	public SpatialPredicatePair getPair() {
+		return pair;
+	}
+
+	public void setValue(Node predicate, Double value) {
+		if (predicate.equals(pair.getLatitudePredicate())) {
+			this.latitudeValue = value;
+		} else if (predicate.equals(pair.getLongitudePredicate())) {
+			this.longitudeValue = value;
+		} else {
+			log.warn("Try to set value to a SpatialPredicatePairValue with no such predicate: "
+					+ predicate + " :: " + value);
+		}
+
+	}
+
+	public Double getTheOtherValue(Node predicate) {
+		if (pair.getLatitudePredicate().equals(predicate)) {
+			return this.getLongitudeValue();
+		} else if (predicate.equals(pair.getLongitudePredicate())) {
+			return this.getLatitudeValue();
+		} else {
+			log.warn("Try to get value to a SpatialPredicatePairValue with no such predicate: "
+					+ predicate);
+			return null;
+		}
+	}
+
+	@Override
+	public int hashCode() {
+		int latitudeHashCode = latitudeValue == null ? 0 : latitudeValue
+				.hashCode() * 17;
+		int longitudeHashCode = longitudeValue == null ? 0 : longitudeValue
+				.hashCode() * 19;
+		return pair.hashCode() * 11 + latitudeHashCode + longitudeHashCode;
+	}
+
+	@Override
+	public boolean equals(Object otherObject) {
+		// a quick test to see if the objects are identical
+		if (this == otherObject)
+			return true;
+
+		// must return false if the explicit parameter is null
+		if (otherObject == null)
+			return false;
+
+		// if the classes don't match, they can't be equal
+		if (getClass() != otherObject.getClass())
+			return false;
+
+		// now we know otherObject is a non-null Employee
+		SpatialPredicatePairValue other = (SpatialPredicatePairValue) otherObject;
+
+		boolean latitudeValueEquals = this.latitudeValue == null ? other.latitudeValue == null
+				: this.latitudeValue.equals(other.latitudeValue);
+		boolean longitudeValueEquals = this.longitudeValue == null ? other.longitudeValue == null
+				: this.longitudeValue.equals(other.longitudeValue);
+
+		// test whether the fields have identical values
+		return pair.equals(other.pair) && latitudeValueEquals
+				&& longitudeValueEquals;
+	}
+}

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialPredicatePairValue.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialQuery.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialQuery.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialQuery.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialQuery.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,135 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial;
+
+import org.apache.jena.query.spatial.assembler.SpatialAssembler;
+import org.apache.jena.query.spatial.pfunction.library.EastPF;
+import org.apache.jena.query.spatial.pfunction.library.IntersectsBoxPF;
+import org.apache.jena.query.spatial.pfunction.library.IsNearByPF;
+import org.apache.jena.query.spatial.pfunction.library.IsWithinBoxPF;
+import org.apache.jena.query.spatial.pfunction.library.IsWithinCirclePF;
+import org.apache.jena.query.spatial.pfunction.library.NorthPF;
+import org.apache.jena.query.spatial.pfunction.library.SouthPF;
+import org.apache.jena.query.spatial.pfunction.library.WestPF;
+
+import com.hp.hpl.jena.sparql.SystemARQ;
+import com.hp.hpl.jena.sparql.lib.Metadata;
+import com.hp.hpl.jena.sparql.mgt.ARQMgt;
+import com.hp.hpl.jena.sparql.mgt.SystemInfo;
+import com.hp.hpl.jena.sparql.pfunction.PropertyFunction;
+import com.hp.hpl.jena.sparql.pfunction.PropertyFunctionFactory;
+import com.hp.hpl.jena.sparql.pfunction.PropertyFunctionRegistry;
+import com.hp.hpl.jena.sparql.util.Symbol;
+import com.hp.hpl.jena.tdb.TDB;
+import com.spatial4j.core.context.SpatialContext;
+import com.spatial4j.core.context.jts.JtsSpatialContext;
+
+public class SpatialQuery
+{
+    private static boolean initialized = false ;
+    private static Object lock = new Object() ;
+    public static String NS = "http://jena.apache.org/spatial#" ;
+    public static String IRI = "http://jena.apache.org/#spatial" ;
+    public static final Symbol spatialIndex = Symbol.create(NS+"index") ;
+    public static final String PATH         = "org.apache.jena.query.spatial";
+    
+    static private String metadataLocation  = "org/apache/jena/query/spatial/properties.xml" ;
+    static private Metadata metadata        = new Metadata(metadataLocation) ;
+    public static final String NAME         = "ARQ Spatial Query";
+   
+    public static final String VERSION      = metadata.get(PATH+".version", "unknown") ;
+    public static final String BUILD_DATE   = metadata.get(PATH+".build.datetime", "unset") ;
+    
+    public static final SpatialContext ctx = JtsSpatialContext.GEO;
+    
+    static { init() ; }
+    
+    public static void init() 
+    {
+        if ( initialized ) return ;
+        synchronized(lock)
+        {
+            if ( initialized ) return ;
+            initialized = true ;
+            TDB.init() ;
+            SpatialAssembler.init() ;
+            
+            SystemInfo sysInfo = new SystemInfo(IRI, VERSION, BUILD_DATE) ;
+            ARQMgt.register(PATH+".system:type=SystemInfo", sysInfo) ;
+            SystemARQ.registerSubSystem(sysInfo) ;
+            
+            PropertyFunctionRegistry.get().put("http://jena.apache.org/spatial#withinCircle", new PropertyFunctionFactory() {
+                @Override
+                public PropertyFunction create(String uri) {
+                    return new IsWithinCirclePF() ;
+                }
+            });
+            PropertyFunctionRegistry.get().put("http://jena.apache.org/spatial#nearby", new PropertyFunctionFactory() {
+                @Override
+                public PropertyFunction create(String uri) {
+                    return new IsNearByPF() ;
+                }
+            });
+            
+            PropertyFunctionRegistry.get().put("http://jena.apache.org/spatial#withinBox", new PropertyFunctionFactory() {
+                @Override
+                public PropertyFunction create(String uri) {
+                    return new IsWithinBoxPF() ;
+                }
+            });
+            
+            
+            PropertyFunctionRegistry.get().put("http://jena.apache.org/spatial#intersectBox", new PropertyFunctionFactory() {
+                @Override
+                public PropertyFunction create(String uri) {
+                    return new IntersectsBoxPF() ;
+                }
+            });
+            
+            PropertyFunctionRegistry.get().put("http://jena.apache.org/spatial#north", new PropertyFunctionFactory() {
+                @Override
+                public PropertyFunction create(String uri) {
+                    return new NorthPF() ;
+                }
+            });
+            
+            PropertyFunctionRegistry.get().put("http://jena.apache.org/spatial#south", new PropertyFunctionFactory() {
+                @Override
+                public PropertyFunction create(String uri) {
+                    return new SouthPF() ;
+                }
+            });
+            
+            PropertyFunctionRegistry.get().put("http://jena.apache.org/spatial#east", new PropertyFunctionFactory() {
+                @Override
+                public PropertyFunction create(String uri) {
+                    return new EastPF() ;
+                }
+            });
+            
+            PropertyFunctionRegistry.get().put("http://jena.apache.org/spatial#west", new PropertyFunctionFactory() {
+                @Override
+                public PropertyFunction create(String uri) {
+                    return new WestPF() ;
+                }
+            });
+        }
+    }
+}
+

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialQuery.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialValueUtil.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialValueUtil.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialValueUtil.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialValueUtil.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,54 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial;
+
+import com.hp.hpl.jena.datatypes.RDFDatatype;
+import com.hp.hpl.jena.datatypes.xsd.XSDDatatype;
+import com.hp.hpl.jena.graph.impl.LiteralLabel;
+
+public class SpatialValueUtil {
+
+	public static boolean isDecimal(LiteralLabel literal) {
+		RDFDatatype dtype = literal.getDatatype();
+		if (dtype == null) {
+			try {
+				Double.parseDouble(literal.getLexicalForm());
+				return true;
+			} catch (NumberFormatException e) {
+				return false;
+			}
+		}
+		if ((dtype.equals(XSDDatatype.XSDfloat))
+				|| (dtype.equals(XSDDatatype.XSDdecimal))
+				|| (dtype.equals(XSDDatatype.XSDdouble) || (dtype
+						.equals(XSDDatatype.XSDinteger))))
+			return true;
+		return false;
+	}
+
+	public static boolean isWKTLiteral(LiteralLabel literal) {
+		RDFDatatype dtype = literal.getDatatype();
+		if (dtype == null)
+			return false;
+		if (dtype.getURI().equals(
+				EntityDefinition.geosparql_wktLiteral.getURI()))
+			return true;
+		return false;
+	}
+}

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/SpatialValueUtil.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/EntityDefinitionAssembler.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/EntityDefinitionAssembler.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/EntityDefinitionAssembler.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/EntityDefinitionAssembler.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,120 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial.assembler;
+
+import static org.apache.jena.query.spatial.assembler.SpatialVocab.NS;
+
+import java.util.List;
+
+import org.apache.jena.atlas.lib.StrUtils;
+import org.apache.jena.atlas.logging.Log;
+import org.apache.jena.query.spatial.EntityDefinition;
+import org.apache.jena.query.spatial.SpatialIndexException;
+
+import com.hp.hpl.jena.assembler.Assembler;
+import com.hp.hpl.jena.assembler.Mode;
+import com.hp.hpl.jena.assembler.assemblers.AssemblerBase;
+import com.hp.hpl.jena.query.ParameterizedSparqlString;
+import com.hp.hpl.jena.query.Query;
+import com.hp.hpl.jena.query.QueryExecution;
+import com.hp.hpl.jena.query.QueryExecutionFactory;
+import com.hp.hpl.jena.query.QueryFactory;
+import com.hp.hpl.jena.query.QuerySolution;
+import com.hp.hpl.jena.query.ResultSet;
+import com.hp.hpl.jena.query.ResultSetFormatter;
+import com.hp.hpl.jena.rdf.model.Model;
+import com.hp.hpl.jena.rdf.model.Resource;
+
+public class EntityDefinitionAssembler extends AssemblerBase implements Assembler
+{
+    
+    // V1
+    
+    /*
+<#definition> a spatial:EntityDefinition ;
+    spatial:entityField      "uri" ;
+    spatial:geoField         "geo" ;
+    spatial:hasSpatialPredicatePairs (
+         [ spatial:latitude <#latitude_1> ; spatial:longitude <#longitude_1> ]
+         [ spatial:latitude <#latitude_2> ; spatial:longitude <#longitude_2> ]
+    ) ;
+    spatial:hasWKTPredicates (<#wkt_1> <#wkt_2>) .
+      */
+    
+    @Override
+    public EntityDefinition open(Assembler a, Resource root, Mode mode)
+    {
+        String prologue = "PREFIX : <"+NS+">   PREFIX list: <http://jena.hpl.hp.com/ARQ/list#> " ;
+        Model model = root.getModel() ;
+
+        String qs1 = StrUtils.strjoinNL(prologue,
+                                        "SELECT * {" ,
+                                        "  ?definition  :entityField  ?entityField ;" ,
+                                        "               :geoField ?geoField" , 
+                                        "}") ;
+        ParameterizedSparqlString pss = new ParameterizedSparqlString(qs1) ;
+        pss.setIri("definition", root.getURI()) ;
+        
+        Query query1 = QueryFactory.create(pss.toString()) ;
+        QueryExecution qexec1 = QueryExecutionFactory.create(query1, model) ;
+        ResultSet rs1 = qexec1.execSelect() ;
+        List<QuerySolution> results = ResultSetFormatter.toList(rs1) ;
+        if ( results.size() == 0 ) {
+            //Log.warn(this, "Failed to find a valid EntityDefinition for : "+root) ;
+            throw new SpatialIndexException("Failed to find a valid EntityDefinition for : "+root) ;
+        }
+        
+        if ( results.size() !=1 )  {
+            Log.warn(this, "Multiple matches for EntityMap for : "+root) ;
+            throw new SpatialIndexException("Multiple matches for EntityDefinition for : "+root) ;
+        }
+        
+        QuerySolution qsol1 = results.get(0) ;
+        String entityField = qsol1.getLiteral("entityField").getLexicalForm() ;
+        String geoField = qsol1.getLiteral("geoField").getLexicalForm() ;
+        
+        EntityDefinition docDef = new EntityDefinition(entityField, geoField) ;
+        
+        String qs2 = StrUtils.strjoinNL("SELECT * { ?definition :hasSpatialPredicatePairs [ list:member [ :latitude ?latitude ; :longitude ?longitude ] ]}") ;
+        Query query2 = QueryFactory.create(prologue+" "+qs2) ;
+        QueryExecution qexec2 = QueryExecutionFactory.create(query2, model, qsol1) ;
+        ResultSet rs2 = qexec2.execSelect() ;
+        List<QuerySolution> mapEntries = ResultSetFormatter.toList(rs2) ;
+        
+        for ( QuerySolution qsol : mapEntries ) {
+        	Resource latitude = qsol.getResource("latitude") ;
+            Resource longitude = qsol.getResource("longitude") ;
+            docDef.addSpatialPredicatePair(latitude, longitude);
+        }
+               
+        String qs3 = StrUtils.strjoinNL("SELECT * { ?definition :hasWKTPredicates [ list:member ?wkt ] }") ;
+        Query query3 = QueryFactory.create(prologue+" "+qs3) ;
+        QueryExecution qexec3 = QueryExecutionFactory.create(query3, model, qsol1) ;
+        ResultSet rs3 = qexec3.execSelect() ;
+        mapEntries = ResultSetFormatter.toList(rs3) ;
+        
+        for ( QuerySolution qsol : mapEntries ) {
+        	Resource wkt = qsol.getResource("wkt") ;
+            docDef.addWKTPredicate(wkt);
+        }
+        
+        return docDef ;
+    }
+}
+

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/EntityDefinitionAssembler.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialAssembler.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialAssembler.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialAssembler.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialAssembler.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,35 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial.assembler;
+
+import com.hp.hpl.jena.assembler.Assembler;
+import com.hp.hpl.jena.sparql.core.assembler.AssemblerUtils;
+
+public class SpatialAssembler
+{
+    public static void init()
+    {
+        AssemblerUtils.init() ;
+        Assembler.general.implementWith(SpatialVocab.spatialDataset,      new SpatialDatasetAssembler()) ;
+        Assembler.general.implementWith(SpatialVocab.definition,        new EntityDefinitionAssembler()) ;
+        Assembler.general.implementWith(SpatialVocab.spatialIndexSolr,    new SpatialIndexSolrAssembler()) ; 
+        Assembler.general.implementWith(SpatialVocab.spatialIndexLucene,  new SpatialIndexLuceneAssembler()) ;
+    }
+}
+

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialAssembler.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialDatasetAssembler.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialDatasetAssembler.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialDatasetAssembler.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialDatasetAssembler.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,62 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial.assembler;
+
+import static org.apache.jena.query.spatial.assembler.SpatialVocab.pDataset;
+import static org.apache.jena.query.spatial.assembler.SpatialVocab.pIndex;
+
+import org.apache.jena.query.spatial.SpatialDatasetFactory;
+import org.apache.jena.query.spatial.SpatialIndex;
+
+import com.hp.hpl.jena.assembler.Assembler;
+import com.hp.hpl.jena.assembler.Mode;
+import com.hp.hpl.jena.assembler.assemblers.AssemblerBase;
+import com.hp.hpl.jena.query.Dataset;
+import com.hp.hpl.jena.rdf.model.Resource;
+import com.hp.hpl.jena.sparql.util.graph.GraphUtils;
+
+public class SpatialDatasetAssembler extends AssemblerBase implements Assembler
+{
+//    private DatasetAssembler datasetAssembler = new DatasetAssembler() ;
+//    
+//    public static Resource getType() { return textDataset ; }
+        
+    /*
+<#spatial_dataset> rdf:type     spatial:SpatialDataset ;
+    spatial:dataset <#dataset> ;
+    spatial:index   <#index> ;
+    .
+
+    */
+    
+    @Override
+    public Dataset open(Assembler a, Resource root, Mode mode)
+    {
+        Resource dataset = GraphUtils.getResourceValue(root, pDataset) ;
+        Resource index   = GraphUtils.getResourceValue(root, pIndex) ;
+        
+        Dataset ds = (Dataset)a.open(dataset) ;
+        SpatialIndex textIndex = (SpatialIndex)a.open(index) ;
+        
+        Dataset dst = SpatialDatasetFactory.create(ds, textIndex) ;
+        return dst ;
+        
+    }
+}
+

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialDatasetAssembler.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialIndexLuceneAssembler.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialIndexLuceneAssembler.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialIndexLuceneAssembler.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialIndexLuceneAssembler.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,87 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial.assembler;
+
+import static org.apache.jena.query.spatial.assembler.SpatialVocab.pDefinition;
+import static org.apache.jena.query.spatial.assembler.SpatialVocab.pDirectory;
+
+import java.io.File;
+import java.io.IOException;
+
+import org.apache.jena.atlas.io.IO;
+import org.apache.jena.query.spatial.EntityDefinition;
+import org.apache.jena.query.spatial.SpatialDatasetFactory;
+import org.apache.jena.query.spatial.SpatialIndex;
+import org.apache.jena.query.spatial.SpatialIndexException;
+import org.apache.jena.riot.system.IRILib;
+import org.apache.lucene.store.Directory;
+import org.apache.lucene.store.FSDirectory;
+import org.apache.lucene.store.RAMDirectory;
+
+import com.hp.hpl.jena.assembler.Assembler;
+import com.hp.hpl.jena.assembler.Mode;
+import com.hp.hpl.jena.assembler.assemblers.AssemblerBase;
+import com.hp.hpl.jena.rdf.model.RDFNode;
+import com.hp.hpl.jena.rdf.model.Resource;
+import com.hp.hpl.jena.sparql.util.graph.GraphUtils;
+
+public class SpatialIndexLuceneAssembler extends AssemblerBase
+{
+    /*
+    <#index> a :SpatialIndexLucene ;
+        #spatial:directory "mem" ;
+        spatial:directory <file:DIR> ;
+        spatial:definition <#definition> ;
+        .
+    */
+
+    @SuppressWarnings("resource")
+    @Override
+    public SpatialIndex open(Assembler a, Resource root, Mode mode)
+    {
+        try
+        {
+            if ( ! GraphUtils.exactlyOneProperty(root, pDirectory) )
+                throw new SpatialIndexException("No 'spatial:directory' property on "+root) ;
+            
+            Directory directory ;
+            RDFNode n = root.getProperty(pDirectory).getObject() ;
+            if ( n.isLiteral() )
+            {
+                if ( ! "mem".equals(n.asLiteral().getLexicalForm()) )
+                    throw new SpatialIndexException("No 'spatial:directory' property on "+root+ " is a literal and not \"mem\"") ;
+                 directory = new RAMDirectory() ;
+            }
+            else
+            { 
+                Resource x = n.asResource() ;
+                String path = IRILib.IRIToFilename(x.getURI()) ; 
+                File dir = new File(path) ; 
+                directory = FSDirectory.open(dir) ;
+            }
+        
+            Resource r = GraphUtils.getResourceValue(root, pDefinition) ;
+            EntityDefinition docDef = (EntityDefinition)a.open(r) ; 
+            
+            return SpatialDatasetFactory.createLuceneIndex(directory, docDef) ;
+        } catch (IOException e) { IO.exception(e) ; return null ;}
+    }
+
+}
+

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialIndexLuceneAssembler.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialIndexSolrAssembler.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialIndexSolrAssembler.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialIndexSolrAssembler.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialIndexSolrAssembler.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,89 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial.assembler;
+
+import static org.apache.jena.query.spatial.assembler.SpatialVocab.pDefinition;
+import static org.apache.jena.query.spatial.assembler.SpatialVocab.pServer;
+import static org.apache.jena.query.spatial.assembler.SpatialVocab.pSolrHome;
+
+import java.io.FileNotFoundException;
+
+import org.apache.jena.query.spatial.EntityDefinition;
+import org.apache.jena.query.spatial.SpatialDatasetFactory;
+import org.apache.jena.query.spatial.SpatialIndex;
+import org.apache.jena.query.spatial.SpatialIndexException;
+import org.apache.jena.riot.system.IRILib;
+import org.apache.solr.client.solrj.SolrServer;
+import org.apache.solr.client.solrj.embedded.EmbeddedSolrServer;
+import org.apache.solr.client.solrj.impl.HttpSolrServer;
+import org.apache.solr.core.CoreContainer;
+
+import com.hp.hpl.jena.assembler.Assembler;
+import com.hp.hpl.jena.assembler.Mode;
+import com.hp.hpl.jena.assembler.assemblers.AssemblerBase;
+import com.hp.hpl.jena.rdf.model.RDFNode;
+import com.hp.hpl.jena.rdf.model.Resource;
+import com.hp.hpl.jena.sparql.util.graph.GraphUtils;
+
+public class SpatialIndexSolrAssembler extends AssemblerBase {
+	/*
+	 * <#index> a :TextIndexSolr ; text:server
+	 * <http://localhost:8983/solr/COLLECTION> ; #text:server <embedded:SolrARQ>
+	 * ; text:entityMap <#endMap> ; .
+	 */
+
+	@Override
+	public SpatialIndex open(Assembler a, Resource root, Mode mode) {
+		String uri = GraphUtils.getResourceValue(root, pServer).getURI();
+		SolrServer server;
+		if (uri.startsWith("embedded:")) {
+			try {
+	            if ( ! GraphUtils.exactlyOneProperty(root, pSolrHome) )
+	                throw new SpatialIndexException("No 'spatial:solrHome' property on EmbeddedSolrServer "+root) ;
+	            
+	            RDFNode n = root.getProperty(pSolrHome).getObject() ;
+	            
+	            if (n.isLiteral()){
+	            	throw new SpatialIndexException ("No 'spatial:solrHome' property on EmbeddedSolrServer "+root+ " is a literal and not a Resource/URI");
+	            }
+                Resource x = n.asResource() ;
+                String path = IRILib.IRIToFilename(x.getURI()) ;
+				
+				System.setProperty("solr.solr.home", path);
+				String coreName = uri.substring("embedded:".length());
+				CoreContainer.Initializer initializer = new CoreContainer.Initializer();
+				CoreContainer coreContainer = initializer.initialize();
+				server = new EmbeddedSolrServer(coreContainer, coreName);
+			} catch (FileNotFoundException e) {
+				throw new SpatialIndexException(e);
+				// throw new
+				// SpatialIndexException("Embedded Solr server not supported (change code and dependencies to enable)")
+				// ;
+			}
+		} else if (uri.startsWith("http://")) {
+			server = new HttpSolrServer(uri);
+		} else
+			throw new SpatialIndexException(
+					"URI for the server must begin 'http://'");
+
+		Resource r = GraphUtils.getResourceValue(root, pDefinition);
+		EntityDefinition docDef = (EntityDefinition) a.open(r);
+		return SpatialDatasetFactory.createSolrIndex(server, docDef);
+	}
+}

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialIndexSolrAssembler.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialVocab.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialVocab.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialVocab.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialVocab.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,52 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial.assembler;
+
+import com.hp.hpl.jena.rdf.model.Property ;
+import com.hp.hpl.jena.rdf.model.Resource ;
+import com.hp.hpl.jena.tdb.assembler.Vocab ;
+
+public class SpatialVocab
+{
+    public static final String NS                   =  "http://jena.apache.org/spatial#" ;
+
+    public static final Resource spatialDataset     = Vocab.resource(NS, "SpatialDataset") ;
+    public static final Property pDataset           = Vocab.property(NS, "dataset") ;
+    public static final Property pIndex             = Vocab.property(NS, "index") ;
+    
+    public static final Resource spatialIndex       = Vocab.resource(NS, "SpatialIndex") ;
+    public static final Resource spatialIndexSolr   = Vocab.resource(NS, "SpatialIndexSolr") ;
+    public static final Resource spatialIndexLucene = Vocab.resource(NS, "SpatialIndexLucene") ;
+    public static final Property pServer            = Vocab.property(NS, "server") ;            // Solr
+    public static final Property pSolrHome          = Vocab.property(NS, "solrHome") ;          // EmbeddedSolrServer 
+    public static final Property pDirectory         = Vocab.property(NS, "directory") ;         // Lucene
+    public static final Property pDefinition        = Vocab.property(NS, "definition") ;
+    
+    // Entity definition
+    public static final Resource definition         = Vocab.resource(NS, "EntityDefinition") ;
+    public static final Property pEntityField       = Vocab.property(NS, "entityField") ;
+    public static final Property pGeoField          = Vocab.property(NS, "geoField") ;
+    public static final Property pHasSpatialPredicatePairs = Vocab.property(NS, "hasSpatialPredicatePairs") ;
+    public static final Property pHasWKTPredicates  = Vocab.property(NS, "hasWKTPredicates") ;
+    public static final Property pLatitude             = Vocab.property(NS, "latitude") ;
+    public static final Property pLongitude         = Vocab.property(NS, "longitude") ;
+    // public static final Property pOptional          = Vocab.property(NS, "optional") ;
+
+}
+

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/assembler/SpatialVocab.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/DirectionWithPointPFBase.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/DirectionWithPointPFBase.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/DirectionWithPointPFBase.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/DirectionWithPointPFBase.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,146 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial.pfunction;
+
+import java.util.List;
+
+import org.apache.jena.query.spatial.SpatialIndexException;
+import org.apache.jena.query.spatial.SpatialValueUtil;
+import org.apache.lucene.spatial.query.SpatialOperation;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import com.hp.hpl.jena.datatypes.xsd.XSDDatatype;
+import com.hp.hpl.jena.graph.Node;
+import com.hp.hpl.jena.graph.impl.LiteralLabel;
+import com.hp.hpl.jena.query.QueryBuildException;
+import com.hp.hpl.jena.sparql.engine.ExecutionContext;
+import com.hp.hpl.jena.sparql.pfunction.PropFuncArg;
+import com.hp.hpl.jena.sparql.util.NodeFactoryExtra;
+
+public abstract class DirectionWithPointPFBase extends SpatialOperationPFBase {
+	
+	private static Logger log = LoggerFactory.getLogger(DirectionWithPointPFBase.class);
+
+	public DirectionWithPointPFBase() {
+		
+	}
+
+	@Override
+	public void build(PropFuncArg argSubject, Node predicate,
+			PropFuncArg argObject, ExecutionContext execCxt) {
+		super.build(argSubject, predicate, argObject, execCxt);
+		
+		if (!argSubject.isNode())
+			throw new QueryBuildException("Subject is not a single node: "
+					+ argSubject);
+
+		if (argObject.isList()) {
+			List<Node> list = argObject.getArgList();
+			if (list.size() < 2)
+				throw new QueryBuildException("Not enough arguments in list");
+
+			if (list.size() > 3)
+				throw new QueryBuildException("Too many arguments in list : "
+						+ list);
+		}
+	}
+	
+
+	/** Deconstruct the node or list object argument and make a SpatialMatch */
+	protected SpatialMatch objectToStruct(PropFuncArg argObject) {
+		if (argObject.isNode()) {
+			log.warn("Object not a List: " + argObject);
+			return null;
+		}
+
+		List<Node> list = argObject.getArgList();
+
+		if (list.size() < 2 || list.size() > 3)
+			throw new SpatialIndexException("Change in object list size");
+
+		int idx = 0;
+
+		Node x = list.get(idx);
+		if (!x.isLiteral()) {
+			log.warn("Latitude is not a literal " + list);
+			return null;
+		}
+		if (!SpatialValueUtil.isDecimal(x.getLiteral())) {
+			log.warn("Latitude is not a decimal " + list);
+			return null;
+		}
+		Double latitude = Double.parseDouble(x.getLiteralLexicalForm());
+
+		idx++;
+
+		x = list.get(idx);
+		if (!x.isLiteral()) {
+			log.warn("Longitude is not a literal " + list);
+			return null;
+		}
+		if (!SpatialValueUtil.isDecimal(x.getLiteral())) {
+			log.warn("Longitude is not a decimal " + list);
+			return null;
+		}
+		Double longitude = Double.parseDouble(x.getLiteralLexicalForm());
+
+		idx++;
+
+		int limit =-1;
+		
+		if (idx < list.size()) {
+			x = list.get(idx);
+
+			if (!x.isLiteral()) {
+				log.warn("Limit is not a literal " + list);
+				return null;
+			}
+
+			LiteralLabel lit = x.getLiteral();
+
+			if (!XSDDatatype.XSDinteger.isValidLiteral(lit)) {
+				log.warn("Limit is not an integer " + list);
+				return null;
+			}
+
+			int v = NodeFactoryExtra.nodeToInt(x);
+			limit = (v < 0) ? -1 : v;
+
+			idx++;
+			if (idx < list.size()) {
+				log.warn("Limit is not the last parameter " + list);
+				return null;
+			}
+		}
+		
+		SpatialMatch match = this.getSpatialMatch(latitude, longitude, limit);
+		if (log.isDebugEnabled())
+			log.debug("Trying SpatialMatch: " + match.toString());
+		return match;
+	}
+	
+	protected abstract SpatialMatch getSpatialMatch(Double latitude, Double longitude, int limit);
+
+	@Override
+	protected SpatialOperation getSpatialOperation() {
+		return SpatialOperation.IsWithin;
+	}
+
+}

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/DirectionWithPointPFBase.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialMatch.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialMatch.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialMatch.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialMatch.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,66 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial.pfunction;
+
+import org.apache.jena.query.spatial.DistanceUnitsUtils;
+import org.apache.jena.query.spatial.SpatialQuery;
+import org.apache.lucene.spatial.query.SpatialOperation;
+
+import com.spatial4j.core.shape.Shape;
+
+public class SpatialMatch {
+
+	private final Shape shape;
+	private final int limit;
+	private final SpatialOperation operation;
+
+	public SpatialMatch(Double latitude, Double longitude, Double radius,
+			String units, int limit, SpatialOperation operation) {
+
+		double degrees = DistanceUnitsUtils.dist2Degrees(radius, units);
+		this.shape = SpatialQuery.ctx.makeCircle(longitude, latitude, degrees);
+		//System.out.println( SpatialQuery.ctx.toString(shape) );
+		this.limit = limit;
+		this.operation = operation;
+	}
+
+	public SpatialMatch(Double latitude1, Double longitude1, Double latitude2,
+			Double longitude2, int limit, SpatialOperation operation) {
+		this.shape = SpatialQuery.ctx.makeRectangle(longitude1, longitude2, latitude1, latitude2);
+		this.limit = limit;
+		this.operation = operation;
+	}
+
+	public Shape getShape() {
+		return shape;
+	}
+
+	public int getLimit() {
+		return limit;
+	}
+
+	public SpatialOperation getSpatialOperation() {
+		return operation;
+	}
+
+	public String toString() {
+		return "(" + shape + " " + limit + " " + operation + ")";
+	}
+
+}

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialMatch.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialOperationPFBase.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialOperationPFBase.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialOperationPFBase.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialOperationPFBase.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,161 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial.pfunction;
+
+import java.util.List;
+
+import org.apache.jena.atlas.iterator.Iter;
+import org.apache.jena.atlas.lib.InternalErrorException;
+import org.apache.jena.atlas.logging.Log;
+import org.apache.jena.query.spatial.DatasetGraphSpatial;
+import org.apache.jena.query.spatial.SpatialIndex;
+import org.apache.jena.query.spatial.SpatialQuery;
+import org.apache.lucene.spatial.query.SpatialOperation;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import com.hp.hpl.jena.graph.Node;
+import com.hp.hpl.jena.sparql.core.DatasetGraph;
+import com.hp.hpl.jena.sparql.core.Var;
+import com.hp.hpl.jena.sparql.engine.ExecutionContext;
+import com.hp.hpl.jena.sparql.engine.QueryIterator;
+import com.hp.hpl.jena.sparql.engine.binding.Binding;
+import com.hp.hpl.jena.sparql.engine.iterator.QueryIterExtendByVar;
+import com.hp.hpl.jena.sparql.engine.iterator.QueryIterSlice;
+import com.hp.hpl.jena.sparql.pfunction.PropFuncArg;
+import com.hp.hpl.jena.sparql.pfunction.PropertyFunctionBase;
+import com.hp.hpl.jena.sparql.util.IterLib;
+
+public abstract class SpatialOperationPFBase extends PropertyFunctionBase {
+
+	private static Logger log = LoggerFactory.getLogger(SpatialOperationPFBase.class);
+
+	protected SpatialIndex server = null;
+	private boolean warningIssued = false;
+
+	public SpatialOperationPFBase() {
+	}
+	
+	@Override
+	public void build(PropFuncArg argSubject, Node predicate,
+			PropFuncArg argObject, ExecutionContext execCxt) {
+		super.build(argSubject, predicate, argObject, execCxt);
+		DatasetGraph dsg = execCxt.getDataset();
+		server = chooseTextIndex(dsg);
+	}
+
+	protected SpatialIndex chooseTextIndex(DatasetGraph dsg) {
+		Object obj = dsg.getContext().get(SpatialQuery.spatialIndex);
+
+		if (obj != null) {
+			try {
+				return (SpatialIndex) obj;
+			} catch (ClassCastException ex) {
+				Log.warn(SpatialOperationWithCircleBase.class, "Context setting '"
+						+ SpatialQuery.spatialIndex + "'is not a SpatialIndex");
+			}
+		}
+
+		if (dsg instanceof DatasetGraphSpatial) {
+			DatasetGraphSpatial x = (DatasetGraphSpatial) dsg;
+			return x.getSpatialIndex();
+		}
+		Log.warn(
+				SpatialOperationWithCircleBase.class,
+				"Failed to find the spatial index : tried context and as a spatial-enabled dataset");
+		return null;
+	}
+
+	@Override
+	public QueryIterator exec(Binding binding, PropFuncArg argSubject,
+			Node predicate, PropFuncArg argObject, ExecutionContext execCxt) {
+		if (server == null) {
+			if (!warningIssued) {
+				Log.warn(getClass(), "No text index - no text search performed");
+				warningIssued = true;
+			}
+			// Not a text dataset - no-op
+			return IterLib.result(binding, execCxt);
+		}
+
+		DatasetGraph dsg = execCxt.getDataset();
+
+		if (!argSubject.isNode())
+			throw new InternalErrorException(
+					"Subject is not a node (it was earlier!)");
+
+		Node s = argSubject.getArg();
+
+		if (s.isLiteral())
+			// Does not match
+			return IterLib.noResults(execCxt);
+
+		SpatialMatch match = objectToStruct(argObject);
+
+		if (match == null) {
+			// can't match
+			return IterLib.noResults(execCxt);
+		}
+
+		// ----
+
+		QueryIterator qIter = (Var.isVar(s)) ? variableSubject(binding, s,
+				match, execCxt) : concreteSubject(binding, s, match, execCxt);
+		if (match.getLimit() >= 0)
+			qIter = new QueryIterSlice(qIter, 0, match.getLimit(), execCxt);
+		return qIter;
+	}
+
+	private QueryIterator variableSubject(Binding binding, Node s,
+			SpatialMatch match, ExecutionContext execCxt) {
+
+		Var v = Var.alloc(s);
+		List<Node> r = query(match);
+		// Make distinct. Note interaction with limit is imperfect
+		r = Iter.iter(r).distinct().toList();
+		QueryIterator qIter = new QueryIterExtendByVar(binding, v,
+				r.iterator(), execCxt);
+		return qIter;
+	}
+
+	private QueryIterator concreteSubject(Binding binding, Node s,
+			SpatialMatch match, ExecutionContext execCxt) {
+		if (!s.isURI()) {
+			log.warn("Subject not a URI: " + s);
+			return IterLib.noResults(execCxt);
+		}
+
+		List<Node> x = query(match);
+		if (x == null || !x.contains(s))
+			return IterLib.noResults(execCxt);
+		else
+			return IterLib.result(binding, execCxt);
+	}
+
+	private List<Node> query(SpatialMatch match) {
+
+		return server.query(match.getShape(), match.getLimit(),
+				match.getSpatialOperation());
+	}
+
+	/** Deconstruct the node or list object argument and make a SpatialMatch */
+	protected abstract SpatialMatch objectToStruct(PropFuncArg argObject);
+	
+	protected abstract SpatialOperation getSpatialOperation();
+}

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialOperationPFBase.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialOperationWithBoxPFBase.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialOperationWithBoxPFBase.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialOperationWithBoxPFBase.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialOperationWithBoxPFBase.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,164 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial.pfunction;
+
+import java.util.List;
+
+import org.apache.jena.query.spatial.SpatialIndexException;
+import org.apache.jena.query.spatial.SpatialValueUtil;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import com.hp.hpl.jena.datatypes.xsd.XSDDatatype;
+import com.hp.hpl.jena.graph.Node;
+import com.hp.hpl.jena.graph.impl.LiteralLabel;
+import com.hp.hpl.jena.query.QueryBuildException;
+import com.hp.hpl.jena.sparql.engine.ExecutionContext;
+import com.hp.hpl.jena.sparql.pfunction.PropFuncArg;
+import com.hp.hpl.jena.sparql.util.NodeFactoryExtra;
+
+public abstract class SpatialOperationWithBoxPFBase extends SpatialOperationPFBase {
+	private static Logger log = LoggerFactory.getLogger(SpatialOperationWithCircleBase.class);
+
+	public SpatialOperationWithBoxPFBase() {
+	}
+
+	@Override
+	public void build(PropFuncArg argSubject, Node predicate,
+			PropFuncArg argObject, ExecutionContext execCxt) {
+		super.build(argSubject, predicate, argObject, execCxt);
+		
+		if (!argSubject.isNode())
+			throw new QueryBuildException("Subject is not a single node: "
+					+ argSubject);
+
+		if (argObject.isList()) {
+			List<Node> list = argObject.getArgList();
+			if (list.size() < 4)
+				throw new QueryBuildException("Not enough arguments in list");
+
+			if (list.size() > 5)
+				throw new QueryBuildException("Too many arguments in list : "
+						+ list);
+		}
+	}
+
+	/** Deconstruct the node or list object argument and make a SpatialMatch */
+	protected SpatialMatch objectToStruct(PropFuncArg argObject) {
+		
+		if (argObject.isNode()) {
+			log.warn("Object not a List: " + argObject);
+			return null;
+		}
+
+		List<Node> list = argObject.getArgList();
+
+		if (list.size() < 4 || list.size() > 5)
+			throw new SpatialIndexException("Change in object list size");
+
+		int idx = 0;
+
+		Node x = list.get(idx);
+		if (!x.isLiteral()) {
+			log.warn("Latitude 1 is not a literal " + list);
+			return null;
+		}
+		if (!SpatialValueUtil.isDecimal(x.getLiteral())) {
+			log.warn("Latitude 1 is not a decimal " + list);
+			return null;
+		}
+		Double latitude1 = Double.parseDouble(x.getLiteralLexicalForm());
+
+		idx++;
+
+		x = list.get(idx);
+		if (!x.isLiteral()) {
+			log.warn("Longitude 1 is not a literal " + list);
+			return null;
+		}
+		if (!SpatialValueUtil.isDecimal(x.getLiteral())) {
+			log.warn("Longitude 1 is not a decimal " + list);
+			return null;
+		}
+		Double longtitude1 = Double.parseDouble(x.getLiteralLexicalForm());
+
+		idx++;
+
+		x = list.get(idx);
+		if (!x.isLiteral()) {
+			log.warn("Latitude 2 is not a literal " + list);
+			return null;
+		}
+		if (!SpatialValueUtil.isDecimal(x.getLiteral())) {
+			log.warn("Latitude 2 is not a decimal " + list);
+			return null;
+		}
+		Double latitude2 = Double.parseDouble(x.getLiteralLexicalForm());
+
+		idx++;
+
+		x = list.get(idx);
+		if (!x.isLiteral()) {
+			log.warn("Longitude 2 is not a literal " + list);
+			return null;
+		}
+		if (!SpatialValueUtil.isDecimal(x.getLiteral())) {
+			log.warn("Longitude 2 is not a decimal " + list);
+			return null;
+		}
+		Double longtitude2 = Double.parseDouble(x.getLiteralLexicalForm());
+
+		idx++;
+		int limit =-1;
+		
+		if (idx < list.size()) {
+			x = list.get(idx);
+
+			if (!x.isLiteral()) {
+				log.warn("Limit is not a literal " + list);
+				return null;
+			}
+
+			LiteralLabel lit = x.getLiteral();
+
+			if (!XSDDatatype.XSDinteger.isValidLiteral(lit)) {
+				log.warn("Limit is not an integer " + list);
+				return null;
+			}
+
+			int v = NodeFactoryExtra.nodeToInt(x);
+			limit = (v < 0) ? -1 : v;
+
+			idx++;
+			if (idx < list.size()) {
+				log.warn("Limit is not the last parameter " + list);
+				return null;
+			}
+		}
+		
+		SpatialMatch match = new SpatialMatch(latitude1, longtitude1,
+				latitude2, longtitude2, limit, getSpatialOperation());
+
+		if (log.isDebugEnabled())
+			log.debug("Trying SpatialMatch: " + match.toString());
+		return match;
+	}
+
+
+}

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialOperationWithBoxPFBase.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialOperationWithCircleBase.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialOperationWithCircleBase.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialOperationWithCircleBase.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialOperationWithCircleBase.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,181 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial.pfunction;
+
+import java.util.List;
+
+import org.apache.jena.query.spatial.DistanceUnitsUtils;
+import org.apache.jena.query.spatial.SpatialIndexException;
+import org.apache.jena.query.spatial.SpatialValueUtil;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import com.hp.hpl.jena.datatypes.xsd.XSDDatatype;
+import com.hp.hpl.jena.graph.Node;
+import com.hp.hpl.jena.graph.impl.LiteralLabel;
+import com.hp.hpl.jena.query.QueryBuildException;
+import com.hp.hpl.jena.sparql.engine.ExecutionContext;
+import com.hp.hpl.jena.sparql.pfunction.PropFuncArg;
+import com.hp.hpl.jena.sparql.util.NodeFactoryExtra;
+
+/** property function that accesses a spatial server */
+public abstract class SpatialOperationWithCircleBase extends SpatialOperationPFBase {
+	
+	private static Logger log = LoggerFactory.getLogger(SpatialOperationWithCircleBase.class);
+
+	public SpatialOperationWithCircleBase() {
+	}
+
+	@Override
+	public void build(PropFuncArg argSubject, Node predicate,
+			PropFuncArg argObject, ExecutionContext execCxt) {
+		super.build(argSubject, predicate, argObject, execCxt);
+
+		if (!argSubject.isNode())
+			throw new QueryBuildException("Subject is not a single node: "
+					+ argSubject);
+
+		if (argObject.isList()) {
+			List<Node> list = argObject.getArgList();
+			if (list.size() < 3)
+				throw new QueryBuildException("Not enough arguments in list");
+
+			if (list.size() > 5)
+				throw new QueryBuildException("Too many arguments in list : "
+						+ list);
+		}
+	}
+	/** Deconstruct the node or list object argument and make a NearbyMatch */
+	protected SpatialMatch objectToStruct(PropFuncArg argObject) {
+
+		// EntityDefinition docDef = server.getDocDef();
+		if (argObject.isNode()) {
+			log.warn("Object not a List: " + argObject);
+			return null;
+		}
+
+		List<Node> list = argObject.getArgList();
+
+		if (list.size() < 3 || list.size() > 5)
+			throw new SpatialIndexException("Change in object list size");
+
+		int idx = 0;
+
+		Node x = list.get(idx);
+		if (!x.isLiteral()) {
+			log.warn("Latitude is not a literal " + list);
+			return null;
+		}
+		if (!SpatialValueUtil.isDecimal(x.getLiteral())) {
+			log.warn("Latitude is not a decimal " + list);
+			return null;
+		}
+		Double latitude = Double.parseDouble(x.getLiteralLexicalForm());
+
+		idx++;
+
+		x = list.get(idx);
+		if (!x.isLiteral()) {
+			log.warn("Longitude is not a literal " + list);
+			return null;
+		}
+		if (!SpatialValueUtil.isDecimal(x.getLiteral())) {
+			log.warn("Longitude is not a decimal " + list);
+			return null;
+		}
+		Double longtitude = Double.parseDouble(x.getLiteralLexicalForm());
+
+		idx++;
+
+		x = list.get(idx);
+
+		if (!x.isLiteral()) {
+			log.warn("Radius is not a literal " + list);
+			return null;
+		}
+		if (!SpatialValueUtil.isDecimal(x.getLiteral())) {
+			log.warn("Radius is not a decimal " + list);
+			return null;
+		}
+		Double radius = Double.parseDouble(x.getLiteralLexicalForm());
+
+		if (radius <= 0) {
+			log.warn("Radius is not a correct decimal " + list);
+			return null;
+		}
+
+		String units = "miles";
+		int limit = -1;
+
+		idx++;
+
+		if (idx < list.size()) {
+			x = list.get(idx);
+
+			if (!x.isLiteral()) {
+				log.warn("Units or limit is not a literal " + list);
+				return null;
+			}
+			if (x.getLiteralDatatype() == null
+					|| x.getLiteralDatatype().equals(XSDDatatype.XSDstring)) {
+				String u = x.getLiteralLexicalForm();
+				if (DistanceUnitsUtils.isSupportedUnits(u)) {
+					idx++;
+					units = u;
+				} else {
+					log.warn("Units are not a supported " + list);
+					return null;
+				}
+			}
+		}
+
+		if (idx < list.size()) {
+			x = list.get(idx);
+
+			if (!x.isLiteral()) {
+				log.warn("Limit is not a literal " + list);
+				return null;
+			}
+
+			LiteralLabel lit = x.getLiteral();
+
+			if (!XSDDatatype.XSDinteger.isValidLiteral(lit)) {
+				log.warn("Limit is not an integer " + list);
+				return null;
+			}
+
+			int v = NodeFactoryExtra.nodeToInt(x);
+			limit = (v < 0) ? -1 : v;
+
+			idx++;
+			if (idx < list.size()) {
+				log.warn("Limit is not the last parameter " + list);
+				return null;
+			}
+		}
+
+		SpatialMatch match = new SpatialMatch(latitude, longtitude, radius,
+				units, limit, this.getSpatialOperation());
+
+		if (log.isDebugEnabled())
+			log.debug("Trying SpatialMatch: " + match.toString());
+		return match;
+	}
+
+}

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/SpatialOperationWithCircleBase.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/library/EastPF.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/library/EastPF.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/library/EastPF.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/library/EastPF.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,44 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial.pfunction.library;
+
+import org.apache.jena.query.spatial.SpatialQuery;
+import org.apache.jena.query.spatial.pfunction.DirectionWithPointPFBase;
+import org.apache.jena.query.spatial.pfunction.SpatialMatch;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class EastPF extends DirectionWithPointPFBase {
+
+	private static Logger log = LoggerFactory.getLogger(EastPF.class);
+
+	public EastPF() {
+		// TODO Auto-generated constructor stub
+	}
+
+	/** Deconstruct the node or list object argument and make a SpatialMatch */
+	protected SpatialMatch getSpatialMatch(Double latitude, Double longitude,
+			int limit) {
+		SpatialMatch match = new SpatialMatch(SpatialQuery.ctx.getWorldBounds().getMinY(),
+				longitude, SpatialQuery.ctx.getWorldBounds().getMaxY(), SpatialQuery.ctx.getWorldBounds()
+						.getMaxX(), limit, getSpatialOperation());
+		return match;
+	}
+
+}

Propchange: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/library/EastPF.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/library/IntersectsBoxPF.java
URL: http://svn.apache.org/viewvc/jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/library/IntersectsBoxPF.java?rev=1519358&view=auto
==============================================================================
--- jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/library/IntersectsBoxPF.java (added)
+++ jena/trunk/jena-spatial/src/main/java/org/apache/jena/query/spatial/pfunction/library/IntersectsBoxPF.java Mon Sep  2 06:46:19 2013
@@ -0,0 +1,35 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.jena.query.spatial.pfunction.library;
+
+import org.apache.jena.query.spatial.pfunction.SpatialOperationWithBoxPFBase;
+import org.apache.lucene.spatial.query.SpatialOperation;
+
+public class IntersectsBoxPF extends SpatialOperationWithBoxPFBase {
+
+	public IntersectsBoxPF() {
+	}
+
+	
+	@Override
+	protected SpatialOperation getSpatialOperation() {
+		return SpatialOperation.Intersects;
+	}
+
+}



Mime
View raw message