From cc9320e246afb683bcbe96c7d11273f5a64936dd Mon Sep 17 00:00:00 2001 From: tidwall Date: Fri, 26 Aug 2022 16:23:28 -0700 Subject: [PATCH] Allow for WHERE for on geofence detection --- internal/collection/collection.go | 4 +++- internal/server/fence.go | 12 +++++++++++- internal/server/scanner.go | 12 +++++++++--- 3 files changed, 23 insertions(+), 5 deletions(-) diff --git a/internal/collection/collection.go b/internal/collection/collection.go index 2bce6966..63c54713 100644 --- a/internal/collection/collection.go +++ b/internal/collection/collection.go @@ -191,8 +191,10 @@ func (c *Collection) Set( oldFieldValues = c.fieldValues.get(oldItem.fieldValuesSlot) newFieldValues = oldFieldValues newItem.fieldValuesSlot = oldItem.fieldValuesSlot + if len(oldFieldValues) > 0 { + oldFieldValues = append([]float64{}, oldFieldValues...) + } } - if fields == nil { if len(values) > 0 { newFieldValues = values diff --git a/internal/server/fence.go b/internal/server/fence.go index eb0de389..94bc6de5 100644 --- a/internal/server/fence.go +++ b/internal/server/fence.go @@ -105,9 +105,18 @@ func fenceMatch( } detect = "roam" } else { + var nocross bool // not using roaming match1 := fenceMatchObject(fence, details.oldObj) + if match1 { + match1, _, _ = sw.testObject(details.id, details.oldObj, details.oldFields) + nocross = !match1 + } match2 := fenceMatchObject(fence, details.obj) + if match2 { + match2, _, _ = sw.testObject(details.id, details.obj, details.fields) + nocross = !match2 + } if match1 && match2 { detect = "inside" } else if match1 && !match2 { @@ -121,7 +130,7 @@ func fenceMatch( if details.command != "fset" { // Maybe the old object and new object create a line that crosses the fence. // Must detect for that possibility. - if details.oldObj != nil { + if !nocross && details.oldObj != nil { ls := geojson.NewLineString(geometry.NewLine( []geometry.Point{ details.oldObj.Center(), @@ -176,6 +185,7 @@ func fenceMatch( o: details.obj, fields: details.fields, noLock: true, + noTest: true, distance: distance, distOutput: fence.distance, }) diff --git a/internal/server/scanner.go b/internal/server/scanner.go index 7f73a649..839870d8 100644 --- a/internal/server/scanner.go +++ b/internal/server/scanner.go @@ -68,6 +68,7 @@ type ScanWriterParams struct { distance float64 distOutput bool // query or fence requested distance output noLock bool + noTest bool ignoreGlobMatch bool clip geojson.Object skipTesting bool @@ -373,9 +374,14 @@ func (sw *scanWriter) writeObject(opts ScanWriterParams) bool { sw.mu.Lock() defer sw.mu.Unlock() } - ok, keepGoing, _ := sw.testObject(opts.id, opts.o, opts.fields) - if !ok { - return keepGoing + + keepGoing := true + if !opts.noTest { + var ok bool + ok, keepGoing, _ = sw.testObject(opts.id, opts.o, opts.fields) + if !ok { + return keepGoing + } } sw.count++ if sw.output == outputCount {