I'm developing a rails app where Users
are having many Items
. The users are geocoded thanks to another model I called Place
that is relying on the ruby geocoder gem.
class Place < ActiveRecord::Base
attr_accessible :street_number, :street, :city, :postal_code, :country, :latitude, :longitude
belongs_to :placable, :polymorphic => true
geocoded_by :address
after_validation :geocode
def address
[street_number, street, postal_code, city, country].compact.join(', ')
end
end
In the user model, I delegated methods from the Place
model to be able to access them directly at the user level.
class User < ActiveRecord::Base
has_many :items, :dependent => :destroy
has_one :place, :as => :placable, :dependent => :destroy
accepts_nested_attributes_for :place
attr_accessible :place_attributes
geocoded_by :address
delegate :address, :to => :place, :allow_nil => true
delegate :latitude, :to => :place, :allow_nil => true
delegate :longitude, :to => :place, :allow_nil => true
#...
end
The same trick is used at the items level:
class Item < ActiveRecord::Base
belongs_to :user
# place
geocoded_by :address
delegate :place, :to => :user, :allow_nil => true
delegate :address, :to => :user, :allow_nil => true
delegate :latitude, :to => :user, :allow_nil => true
delegate :longitude, :to => :user, :allow_nil => true
# ...
end
Now I'd like to set up an index on items such that they are sorted by distance to the current user. I don't find a design to perform the task in this setup.
I tried to do the following with the delegation of the near
method from geocoder on the User
model and the Item
model but the sql query fails complaining that latitude
and longitude
are not columns of the items
table. This is actually correct but I wish to access the ones in the places
table instead.
# this added to the user model:
delegate :near :to => :place
# this added to the item model:
delegate :near :to => :user
class ItemsController < ApplicationController
def index
@items=Item.near(current_user.place, params[:distance]).paginate(:per_page => 20, :page => params[:page_name])
end
end
I would like to avoid the solution where both users and items are having attributes for geocoding (latitude, longitude, address, etc.).