Railsify relation selection (aka ripping out the f***in SQL).

This commit is contained in:
Tom Hughes 2008-06-24 23:42:39 +00:00
parent cfc14f1ddc
commit def60c1935
6 changed files with 14 additions and 36 deletions

View file

@ -123,7 +123,9 @@ class AmfController < ApplicationController
points = nodes_not_used_in_area.collect { |n| [n.id, n.lon_potlatch(baselong,masterscale), n.lat_potlatch(basey,masterscale), n.tags_as_hash] }
# find the relations used by those nodes and ways
relation_ids = (Relation.find_for_nodes_and_ways(nodes_in_area.collect {|n| n.id}, way_ids)).collect {|n| n.id}.uniq
relations = nodes_in_area.collect { |node| node.containing_relations.visible }.flatten +
way_ids.collect { |id| Way.find(id).containing_relations.visible }.flatten
relation_ids = relations.collect { |relation| relation.id }.uniq
[way_ids,points,relation_ids]
end

View file

@ -124,8 +124,6 @@ class ApiController < ApplicationController
return
end
relations = Array.new
doc = OSM::API.new.get_xml_doc
# get ways
@ -170,19 +168,15 @@ class ApiController < ApplicationController
end
end
relations = Relation.find_for_nodes_and_ways(visible_nodes.keys, way_ids)
relations = visible_nodes.values.collect { |node| node.containing_relations.visible }.flatten +
way_ids.collect { |id| Way.find(id).containing_relations.visible }.flatten
# we do not normally return the "other" partners referenced by an relation,
# e.g. if we return a way A that is referenced by relation X, and there's
# another way B also referenced, that is not returned. But we do make
# an exception for cases where an relation references another *relation*;
# in that case we return that as well (but we don't go recursive here)
relation_ids = relations.collect { |relation| relation.id }
if relation_ids.length > 0
relations += Relation.find_by_sql("select e.* from current_relations e,current_relation_members em where " +
"e.visible=1 and " +
"em.id = e.id and em.member_type='relation' and em.member_id in (#{relation_ids.join(',')})")
end
relations += relations.collect { |relation| relation.containing_relations.visible }.flatten
# this "uniq" may be slightly inefficient; it may be better to first collect and output
# all node-related relations, then find the *not yet covered* way-related ones etc.

View file

@ -18,7 +18,7 @@ class Node < ActiveRecord::Base
has_many :ways, :through => :way_nodes
has_many :containing_relation_members, :class_name => "RelationMember", :as => :member
has_many :containing_relations, :class_name => "Relation", :through => :containing_relation_members, :source => :relation
has_many :containing_relations, :class_name => "Relation", :through => :containing_relation_members, :source => :relation, :extend => ObjectFinder
# Sanity check the latitude and longitude and add an error if it's broken
def validate_position

View file

@ -11,7 +11,7 @@ class Relation < ActiveRecord::Base
has_many :relation_tags, :foreign_key => 'id'
has_many :containing_relation_members, :class_name => "RelationMember", :as => :member
has_many :containing_relations, :class_name => "Relation", :through => :containing_relation_members, :source => :relation
has_many :containing_relations, :class_name => "Relation", :through => :containing_relation_members, :source => :relation, :extend => ObjectFinder
def self.from_xml(xml, create=false)
begin
@ -105,29 +105,6 @@ class Relation < ActiveRecord::Base
return el1
end
# collect relationships. currently done in one big block at the end;
# may need to move this upwards if people want automatic completion of
# relationships, i.e. deliver referenced objects like we do with ways...
# FIXME: rip out the fucking SQL
def self.find_for_nodes_and_ways(node_ids, way_ids)
relations = []
if node_ids.length > 0
relations += Relation.find_by_sql("select e.* from current_relations e,current_relation_members em where " +
"e.visible=1 and " +
"em.id = e.id and em.member_type='node' and em.member_id in (#{node_ids.join(',')})")
end
if way_ids.length > 0
relations += Relation.find_by_sql("select e.* from current_relations e,current_relation_members em where " +
"e.visible=1 and " +
"em.id = e.id and em.member_type='way' and em.member_id in (#{way_ids.join(',')})")
end
relations # if you don't do this then it returns nil and not []
end
# FIXME is this really needed?
def members
unless @members

View file

@ -13,7 +13,7 @@ class Way < ActiveRecord::Base
has_many :way_tags, :foreign_key => 'id'
has_many :containing_relation_members, :class_name => "RelationMember", :as => :member
has_many :containing_relations, :class_name => "Relation", :through => :containing_relation_members, :source => :relation
has_many :containing_relations, :class_name => "Relation", :through => :containing_relation_members, :source => :relation, :extend => ObjectFinder
def self.from_xml(xml, create=false)
begin

5
lib/object_finder.rb Normal file
View file

@ -0,0 +1,5 @@
module ObjectFinder
def visible
find :all, :conditions => "#{proxy_reflection.table_name}.visible = 1"
end
end