I’ve got large number of documents with geo locations specified as polygons - lets call them boxes.
When my mobile device sends in its position via lat / long I want to pull back all documents where the Lat / Long is inside any of the specified boxes.
The only options I can see to do this in Couchbase are:
Provide a Point and a Radius and if any of the points of my boxes intersect the point + radius it returns
Provide a Polygon and if any of the points of my boxes intersect on the points, it returns.
Am I missing a trick here? this seems like a simple task that I’m trying to perform.
e.g.
I have documents which contains boxes around city centers
When my device is inside a city center I want to return the document of the city center.
If I’m on the outside of a boxed area, even if I’m near the corner of one, I don’t want it to return. so I can’t use a radius.
With Full Text Search at couchbase, we support geo distance (radius), bounding box (rectangle) and more recently geo polygon searches. So if documents were carrying a single set of geo co-ordinates, your geo query could be specified with a set of coordinates to determine if the documents were to either fall within the distance or the polygon specified by the search query.
Now your scenario seems to do the opposite - where your documents contain a set of points and the query wants to check if a given point lies within the bounding box specified by each of your documents.
Also - search only returns document IDs if your search criteria qualifies. There is a way however for you to fetch the content within these documents - by storing the fields while indexing and requesting for the fields from the query.
What you’re asking for isn’t supported directly within couchbase. However there is a way for your application to determine this -
Let’s assume the mobile device has one other attribute - a range if you will. This range needs to be sufficiently long enough to communicate with at least one of vertices of the document’s geo coordinates.
You can estimate if - at least one of the vertices of each document fall within that range, with a geo distance query
Now this isn’t good enough, because a device with a long enough range could lie well outside the polygon and still reach any or all of it’s vertices, so your application will have to do the additional math to determine if the document does actually fall within the vertices for the returned document.
I understand if this approach isn’t quite desirable, so let me loop in @sreeks to check if he can think of a better approach here for you.
As @abhinav mentioned, FTS doesn’t have a built-in solution for this.
FTS doesn’t support the geo shape indexing capability now. So even if you have a series of boundary points within a field in the source document - FTS doesn’t have a way to index/digest it now.
Still, I think your point-radius query is very close, but with a few tweaks which might also involve the additional field introduction into your original source document.
One potential idea popping to mind is that,
First you need to add/introduce an additional geo field into your source document which is the centroid/central point of the given series of boundary points. Let’s call this new central point of the region as newGeo.
ref - Centroid - Wikipedia or this becomes an approximation with irregular polygons. Perhaps find the center point of the bounding rectangle for the given region/polygon boundary. You need to investigate more there on the approach which eventually gives you better precision for the results.
You need to index this new newGeo field as a geo point type while defining the FTS index.
Then you need to index the original region boundary field (series of geo points as a polygon) of the document.
Note: Enable the store option for this boundary field so that you need to retrieve this boundary field contents later along with the search results. (You may need to change the type of this field in the source document to fit the field types we support here).
Now we are all set with the indexing part.
Your mobile device geolocation is sent as a point-radius query to the FTS backend against the newGeo point.
The radius value has to be in a reasonable limit/range to fetch the surrounding source documents.
Note: You need to request the original stored boundary field contents along with the search results. You may use the Fields in the search request for this. ref - https://docs.couchbase.com/server/current/fts/fts-response-object-schema.html
Once you have a couple of overlapping documents in the search result, the client app needs to figure out whether your mobile device location really lies within the boundary of the returned documents. (This value is already there in the Fields returned on every Hit of the search result)
You may use any standard point inclusion algorithms for polygons - http://geomalgorithms.com/a03-_inclusion.html
(This part is a light and fast logic as you would be checking this against a handful of documents)
Thank you. @abhinav and @sreeks
This is great information. I’ll have a play with these but I fear that in this instance, Couchbase is the wrong technology for my needs. I will give the above a try though and see how close it gets me to the answer I need.
Cheers!