2
votes

I want to use a spatial index in Neo4j with the spring-data-neo4j framework. Additionally I want to query the index using cypher. The database is embedded.

I'm a bit clueless as to how to get it to all wire together.

With a domain object like this,

@NodeEntity
class Junction {
    @GraphId Long id;
    @Indexed(indexType = IndexType.POINT, indexName = "junctionLocations") Point wkt;
}

SDN ought to be maintaining the index for me. It appears so, as I can do spatial queries using the repository:

interface JunctionGraph extends GraphRepository<Junction>, SpatialRepository<Junction> {}

with

junctionGraph.findWithinBoundingBox("junctionLocations", new Box(lowerBound.point, upperBound.point))

However, I understand that to query this index using cypher (via a @Query in the repository) this spatial index configuration won't work. I think that this is because each node needs to be manually added to the spatial index (or at least a proxy for the node). That means that adding this to JunctionGraph:

@Query("START n=node:junctionLocations('withinDistance:[{0}, {1}, {2}]') MATCH n-[*]->(i:Item) return i")
Collection<Item> getItemsWithin(double lat, double lon, double radius)

doesn't work.

Does anyone have a working recipe? It appears to be a bit black magic to me, and I'm unsure what the best way to proceed within SDN is.

1
Could you share where did you import the "IndexType.POINT" ?USer22999299

1 Answers

4
votes

It works, you just have to create the whole query string outside and pass it as parameter, placeholders within string constants are not substituted.

@Query("START n=node:junctionLocations({0}) MATCH n-[*]->(i:Item) return i")
Collection<Item> getItemsWithin(String query)

you have to do the replacement yourself, .e.g. using String.format

String.format("withinDistance:[%f, %f, %f]",lat,lon,radius)