diff --git a/ruby/Gemfile b/ruby/Gemfile index a715c99a3..907ca1b79 100644 --- a/ruby/Gemfile +++ b/ruby/Gemfile @@ -24,8 +24,8 @@ gem 'aasm', '3.0.16' gem 'devise', '>= 1.1.2' gem 'postgres-copy' -gem 'geokit', :git => 'https://github.com/imajes/geokit.git' -gem 'geokit-rails3' +gem 'geokit-rails' +gem 'postgres_ext' if devenv gem 'jam_db', :path=> "../db/target/ruby_package" diff --git a/ruby/lib/jam_ruby.rb b/ruby/lib/jam_ruby.rb index baea30286..763a6ccbc 100755 --- a/ruby/lib/jam_ruby.rb +++ b/ruby/lib/jam_ruby.rb @@ -11,6 +11,9 @@ require "action_mailer" require "devise" require "sendgrid" require "postgres-copy" +require "geokit-rails" +require "postgres_ext" + require "jam_ruby/lib/module_overrides" require "jam_ruby/constants/limits" require "jam_ruby/constants/notification_types" @@ -82,4 +85,4 @@ include Jampb module JamRuby -end \ No newline at end of file +end diff --git a/ruby/lib/jam_ruby/models/max_mind_geo.rb b/ruby/lib/jam_ruby/models/max_mind_geo.rb index 0c8f2c082..47e6610a8 100644 --- a/ruby/lib/jam_ruby/models/max_mind_geo.rb +++ b/ruby/lib/jam_ruby/models/max_mind_geo.rb @@ -5,24 +5,17 @@ module JamRuby def self.import_from_max_mind(file) - # File Geo-124 + # File Geo-139 # Format: # startIpNum,endIpNum,country,region,city,postalCode,latitude,longitude,dmaCode,areaCode MaxMindGeo.transaction do MaxMindGeo.delete_all File.open(file, 'r:ISO-8859-1') do |io| - MaxMindGeo.pg_copy_from io, :map => { 'startIpNum' => 'ip_bottom', 'endIpNum' => 'ip_top', 'country' => 'country', 'region' => 'region', 'city' => 'city'}, :columns => [:startIpNum, :endIpNum, :country, :region, :city] do |row| - row[0] = ip_address_to_int(row[0]) - row[1] = ip_address_to_int(row[1]) - row.delete_at(5) - row.delete_at(5) - row.delete_at(5) - row.delete_at(5) - row.delete_at(5) - end + MaxMindGeo.pg_copy_from io, :map => { 'startIpNum' => 'ip_start', 'endIpNum' => 'ip_end', 'country' => 'country', 'region' => 'region', 'city' => 'city', 'latitude' => 'lat', 'longitude' => 'lng'}, :columns => [:startIpNum, :endIpNum, :country, :region, :city, :latitude, :longitude] end end + User.find_each { |usr| usr.update_lat_lng } end @@ -35,4 +28,4 @@ module JamRuby end -end \ No newline at end of file +end diff --git a/ruby/lib/jam_ruby/models/search.rb b/ruby/lib/jam_ruby/models/search.rb index c3c33c7e2..da3209923 100644 --- a/ruby/lib/jam_ruby/models/search.rb +++ b/ruby/lib/jam_ruby/models/search.rb @@ -5,6 +5,17 @@ module JamRuby LIMIT = 10 + ORDER_LIKED = ['Most Liked', :liked] + ORDER_FOLLOWS = ['Most Followed', :followed] + ORDER_PLAYING = ['Playing Now', :playing] + ORDERINGS = [ORDER_LIKED, ORDER_FOLLOWS, ORDER_PLAYING] + ORDERING_KEYS = ORDERINGS.collect { |oo| oo[1] } + + def self.order_param(params) + ordering = params[:orderby] + ordering.blank? ? ORDERING_KEYS[0] : ordering + end + # performs a site-white search def self.search(query, user_id = nil) diff --git a/ruby/lib/jam_ruby/models/user.rb b/ruby/lib/jam_ruby/models/user.rb index 7af848254..28b08db71 100644 --- a/ruby/lib/jam_ruby/models/user.rb +++ b/ruby/lib/jam_ruby/models/user.rb @@ -8,8 +8,12 @@ module JamRuby devise :database_authenticatable, :recoverable, :rememberable + # include Geokit::ActsAsMappable::Glue unless defined?(acts_as_mappable) + # acts_as_mappable - attr_accessible :first_name, :last_name, :email, :city, :password, :password_confirmation, :state, :country, :birth_date, :subscribe_email, :terms_of_service, :original_fpfile, :cropped_fpfile, :cropped_s3_path, :photo_url, :crop_selection + after_update :check_lat_lng + + attr_accessible :first_name, :last_name, :email, :city, :password, :password_confirmation, :state, :country, :birth_date, :subscribe_email, :terms_of_service, :original_fpfile, :cropped_fpfile, :cropped_s3_path, :photo_url, :crop_selection, :lat, :lng # updating_password corresponds to a lost_password attr_accessor :updating_password, :updating_email, :updated_email, :update_email_confirmation_url, :administratively_created, :current_password, :setting_password, :confirm_current_password, :updating_avatar, :updating_progression_field @@ -896,6 +900,39 @@ module JamRuby end end + def self.musician_search(params={}, current_user=nil) + rel = User.where(:musician => true) + unless (instrument = params[:instrument]).blank? + rel = rel.joins("INNER JOIN musicians_instruments AS minst ON minst.user_id = users.id") + .where(['minst.instrument_id = ?', instrument]) + end + + location_distance, location_city = params[:distance], params[:city] + if location_distance && location_city + citylatlng = [] # FIXME: get the lat/lng for the city + rel = rel.within(location_distance, :origin => citylatlng) + + elsif current_user + latlng = [] + if current_user.lat.nil? + # FIXME: Lookup latlng from params[:remote_ip] + else + latlng = [current_user.lat, current_user.lng] + end + distance = location_distance || 50 + rel = rel.within(distance, :origin => latlng) + end + + case ordering = Search.order_param(params) + when :liked + rel = rel.order("SELECT COUNT(*) FROM users_likers WHERE users_likers.user_id = ") + when :followed + when :playing + end + + rel.page(params[:page].to_i) + end + def self.search(query, options = { :limit => 10 }) # only issue search if at least 2 characters are specified @@ -921,6 +958,32 @@ module JamRuby .limit(options[:limit]) end + def provides_location? + !self.city.blank? && (!self.state.blank? || !self.country.blank?) + end + + def check_lat_lng + update_lat_lng if city_changed? || state_changed? || country_changed? + end + + def update_lat_lng(ip_addy=nil) + yn = false + if provides_location? # ip_addy argument ignored in this case + query = {:city => self.city} + query[:state] = self.state unless self.state.blank? + query[:country] = self.country unless self.country.blank? + geo = MaxMindGeo.where(query).limit(1).first + self.update_attributes({:lat => geo.lat, :lng => geo.lng}) + yn = true + elsif ip_addy + if geo = MaxMindGeo.where(['ip_start >= ? AND ip_end <= ?',ip_addy,ip_addy]).limit(1).first + self.update_attributes({:lat => geo.lat, :lng => geo.lng}) + yn = true + end + end + yn + end + # devise compatibility #def encrypted_password diff --git a/ruby/spec/jam_ruby/models/musician_search_spec.rb b/ruby/spec/jam_ruby/models/musician_search_spec.rb new file mode 100644 index 000000000..7d3a9a47e --- /dev/null +++ b/ruby/spec/jam_ruby/models/musician_search_spec.rb @@ -0,0 +1,44 @@ +require 'spec_helper' + +describe User do + + before(:each) do + params = { + first_name: "Example", + last_name: "User", + email: "user1@example.com", + password: "foobar", + password_confirmation: "foobar", + musician: true, + email_confirmed: true, + city: "Apex", + state: "NC", + country: "USA" + } + @user1 = FactoryGirl.create(:user, params) + params[:email] = "user2@example.com" + @user2 = FactoryGirl.create(:user, params) + end + + it "should find all musicians sorted by likes with pagination" do + pending + User.musician_search + end + + it "should find all musicians sorted by follows with pagination" do + pending + end + + it "should find all musicians sorted by now playing" do + pending + end + + it "should find musicians with an instrument" do + pending + end + + it "should find musicians within a given distance of location" do + pending + end + +end