From f718360d424348784c9d2e4162bcc16973cc51b2 Mon Sep 17 00:00:00 2001 From: Troy Kruthoff Date: Fri, 27 Jun 2008 17:32:00 -0700 Subject: [PATCH] replaced @conditions array on Query with ConditionsArray < Array which inserts keyed conditions at the top of the array --- lib/dm-core/query.rb | 22 +++++++++++++++++++++- spec/unit/query_spec.rb | 14 ++++++++++++++ 2 files changed, 35 insertions(+), 1 deletions(-) diff --git a/lib/dm-core/query.rb b/lib/dm-core/query.rb index 7012eae..45f3468 100644 --- a/lib/dm-core/query.rb +++ b/lib/dm-core/query.rb @@ -164,7 +164,7 @@ module DataMapper @fields = options.fetch :fields, @properties.defaults # must be an Array of Symbol, String or DM::Property @links = options.fetch :links, [] # must be an Array of Tuples - Tuple [DM::Query,DM::Assoc::Relationship] @includes = options.fetch :includes, [] # must be an Array of DM::Query::Path - @conditions = [] # must be an Array of triplets (or pairs when passing in raw String queries) + @conditions = ConditionsArray.new # must be an Array of triplets (or pairs when passing in raw String queries) # normalize order and fields @order = normalize_order(@order) @@ -482,6 +482,26 @@ module DataMapper @conditions end + # Ensures conditions with keyed properties are placed at the beginning of the array, + # in the same order the keys are declared on the model. + # TODO: more work can be done to validate the tuples + class ConditionsArray < Array + def <<(new_condition) + operator, property = *new_condition + return super if operator == :raw or !property.key? + @keyed_properties ||= property.model.key + did_insert = false + self.each_with_index do |condition,index| + operator_this, property_this = *condition + next if (operator_this == :raw) or (property_this.key? and @keyed_properties.index(property_this) <= @keyed_properties.index(property)) + self.insert(index,new_condition) + did_insert = true + break + end + did_insert ? new_condition : super + end + end + class Direction include Assertions diff --git a/spec/unit/query_spec.rb b/spec/unit/query_spec.rb index 606eb37..7fb77ba 100644 --- a/spec/unit/query_spec.rb +++ b/spec/unit/query_spec.rb @@ -102,6 +102,13 @@ describe DataMapper::Query do value.should == acl_query end end + + # maybe this should be in a seperate test for ConditionsArray? + it "when they contain keys, should be in key order" do + query = DataMapper::Query.new(@repository, Article, :blog_id => 10, :id=>1, :author=>'Bill Clinton', :title=>'Fine Cigars') + query.conditions.first[1].name.should == :id + end + end describe ' #conditions with unknown options' do @@ -278,6 +285,13 @@ describe DataMapper::Query do end end + # maybe this should be in a seperate test for ConditionsArray? + it "#conditions should maintain key order" do + @query.update(:blog_id => 10) + @query.update(:id => 1) + @query.conditions.collect {|c| c[1].name }.should == [:id,:blog_id] + end + it "#order with other order unique values" do order = [ DataMapper::Query::Direction.new(Article.properties[:created_at], :desc), -- 1.5.4