Skip to content
Snippets Groups Projects
Commit 5353fea4 authored by Leonel Galán's avatar Leonel Galán Committed by Alex Reisner
Browse files

Allows radius to be a symbol representing a column in DB (#1107)

* Allows radius to be a symbol representing a column in DB

* Proposed changes by @alexreisner:

- Keeping branching condition consistent
- Not overwrite the method argument: ‘radius’
- Not assigning two variables in a single line, and
- Add code comments where needed

By “proposed” I meant, I copy/paste them from his comment. But we are
in agreement.

* Fixes broken test in PR
parent 5a37ba5b
No related branches found
No related tags found
No related merge requests found
......@@ -131,7 +131,11 @@ module Geocoder::Store
distance_column = options.fetch(:distance_column) { 'distance' }
bearing_column = options.fetch(:bearing_column) { 'bearing' }
b = Geocoder::Calculations.bounding_box([latitude, longitude], radius, options)
# If radius is a DB column name, bounding box should include
# all rows within the maximum radius appearing in that column.
# Note: performance is dependent on variability of radii.
bb_radius = radius.is_a?(Symbol) ? maximum(radius) : radius
b = Geocoder::Calculations.bounding_box([latitude, longitude], bb_radius, options)
args = b + [
full_column_name(latitude_attribute),
full_column_name(longitude_attribute)
......@@ -142,7 +146,16 @@ module Geocoder::Store
conditions = bounding_box_conditions
else
min_radius = options.fetch(:min_radius, 0).to_f
conditions = [bounding_box_conditions + " AND (#{distance}) BETWEEN ? AND ?", min_radius, radius]
# if radius is a DB column name,
# find rows between min_radius and value in column
if radius.is_a?(Symbol)
c = "BETWEEN ? AND #{radius}"
a = [min_radius]
else
c = "BETWEEN ? AND ?"
a = [min_radius, radius]
end
conditions = [bounding_box_conditions + " AND (#{distance}) " + c] + a
end
{
:select => select_clause(options[:select],
......
......@@ -15,6 +15,7 @@ class CreateTestSchema < superclass
t.column :address, :string
t.column :latitude, :decimal, :precision => 16, :scale => 6
t.column :longitude, :decimal, :precision => 16, :scale => 6
t.column :radius_column, :decimal, :precision => 16, :scale => 6
end
end
......
......@@ -75,6 +75,10 @@ else
def primary_key
:id
end
def maximum(_field)
1.0
end
end
end
end
......
......@@ -18,6 +18,13 @@ class NearTest < GeocoderTestCase
assert_match(/BETWEEN \? AND \?$/, result[:conditions][0])
end
def test_near_scope_options_includes_radius_column_max_radius
omit("Not applicable to unextended SQLite") if using_unextended_sqlite?
result = Place.send(:near_scope_options, 1.0, 2.0, :radius_column)
assert_match(/BETWEEN \? AND radius_column$/, result[:conditions][0])
end
def test_near_scope_options_includes_radius_default_min_radius
omit("Not applicable to unextended SQLite") if using_unextended_sqlite?
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment