sequel 2.6.0 → 2.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/CHANGELOG +64 -0
 - data/Rakefile +1 -1
 - data/lib/sequel_core/adapters/jdbc.rb +6 -2
 - data/lib/sequel_core/adapters/jdbc/oracle.rb +23 -0
 - data/lib/sequel_core/adapters/oracle.rb +4 -77
 - data/lib/sequel_core/adapters/postgres.rb +39 -26
 - data/lib/sequel_core/adapters/shared/mssql.rb +0 -1
 - data/lib/sequel_core/adapters/shared/mysql.rb +1 -1
 - data/lib/sequel_core/adapters/shared/oracle.rb +82 -0
 - data/lib/sequel_core/adapters/shared/postgres.rb +65 -46
 - data/lib/sequel_core/core_ext.rb +10 -0
 - data/lib/sequel_core/core_sql.rb +7 -0
 - data/lib/sequel_core/database.rb +22 -0
 - data/lib/sequel_core/database/schema.rb +1 -1
 - data/lib/sequel_core/dataset.rb +29 -11
 - data/lib/sequel_core/dataset/sql.rb +27 -7
 - data/lib/sequel_core/migration.rb +20 -2
 - data/lib/sequel_core/object_graph.rb +24 -10
 - data/lib/sequel_core/schema/generator.rb +22 -9
 - data/lib/sequel_core/schema/sql.rb +13 -9
 - data/lib/sequel_core/sql.rb +27 -2
 - data/lib/sequel_model/association_reflection.rb +251 -141
 - data/lib/sequel_model/associations.rb +114 -61
 - data/lib/sequel_model/base.rb +25 -21
 - data/lib/sequel_model/eager_loading.rb +17 -40
 - data/lib/sequel_model/hooks.rb +25 -24
 - data/lib/sequel_model/record.rb +29 -51
 - data/lib/sequel_model/schema.rb +1 -1
 - data/lib/sequel_model/validations.rb +13 -3
 - data/spec/adapters/postgres_spec.rb +104 -18
 - data/spec/adapters/spec_helper.rb +4 -1
 - data/spec/integration/eager_loader_test.rb +5 -4
 - data/spec/integration/spec_helper.rb +4 -1
 - data/spec/sequel_core/connection_pool_spec.rb +24 -24
 - data/spec/sequel_core/core_sql_spec.rb +12 -0
 - data/spec/sequel_core/dataset_spec.rb +77 -2
 - data/spec/sequel_core/expression_filters_spec.rb +6 -0
 - data/spec/sequel_core/object_graph_spec.rb +40 -2
 - data/spec/sequel_core/schema_spec.rb +13 -0
 - data/spec/sequel_model/association_reflection_spec.rb +8 -8
 - data/spec/sequel_model/associations_spec.rb +164 -3
 - data/spec/sequel_model/caching_spec.rb +2 -1
 - data/spec/sequel_model/eager_loading_spec.rb +107 -3
 - data/spec/sequel_model/hooks_spec.rb +38 -22
 - data/spec/sequel_model/model_spec.rb +11 -35
 - data/spec/sequel_model/plugins_spec.rb +4 -2
 - data/spec/sequel_model/record_spec.rb +8 -5
 - data/spec/sequel_model/validations_spec.rb +25 -0
 - data/spec/spec_config.rb +4 -3
 - metadata +21 -19
 
| 
         @@ -18,21 +18,21 @@ describe Sequel::Model::Associations::AssociationReflection, "#associated_class" 
     | 
|
| 
       18 
18 
     | 
    
         
             
              end
         
     | 
| 
       19 
19 
     | 
    
         
             
            end
         
     | 
| 
       20 
20 
     | 
    
         | 
| 
       21 
     | 
    
         
            -
            describe Sequel::Model::Associations::AssociationReflection, "# 
     | 
| 
      
 21 
     | 
    
         
            +
            describe Sequel::Model::Associations::AssociationReflection, "#primary_key" do
         
     | 
| 
       22 
22 
     | 
    
         
             
              before do
         
     | 
| 
       23 
23 
     | 
    
         
             
                @c = Class.new(Sequel::Model)
         
     | 
| 
       24 
24 
     | 
    
         
             
                class ::ParParent < Sequel::Model; end
         
     | 
| 
       25 
25 
     | 
    
         
             
              end
         
     | 
| 
       26 
26 
     | 
    
         | 
| 
       27 
     | 
    
         
            -
              it "should use the : 
     | 
| 
       28 
     | 
    
         
            -
                @c.many_to_one :c, :class=>ParParent, : 
     | 
| 
       29 
     | 
    
         
            -
                @c.association_reflection(:c).should include(: 
     | 
| 
       30 
     | 
    
         
            -
                @c.association_reflection(:c). 
     | 
| 
      
 27 
     | 
    
         
            +
              it "should use the :primary_key value if present" do
         
     | 
| 
      
 28 
     | 
    
         
            +
                @c.many_to_one :c, :class=>ParParent, :primary_key=>:blah__blah
         
     | 
| 
      
 29 
     | 
    
         
            +
                @c.association_reflection(:c).should include(:primary_key)
         
     | 
| 
      
 30 
     | 
    
         
            +
                @c.association_reflection(:c).primary_key.should == :blah__blah
         
     | 
| 
       31 
31 
     | 
    
         
             
              end
         
     | 
| 
       32 
     | 
    
         
            -
              it "should use the associated table's primary key if : 
     | 
| 
      
 32 
     | 
    
         
            +
              it "should use the associated table's primary key if :primary_key is not present" do
         
     | 
| 
       33 
33 
     | 
    
         
             
                @c.many_to_one :c, :class=>'ParParent'
         
     | 
| 
       34 
     | 
    
         
            -
                @c.association_reflection(:c).should_not include(: 
     | 
| 
       35 
     | 
    
         
            -
                @c.association_reflection(:c). 
     | 
| 
      
 34 
     | 
    
         
            +
                @c.association_reflection(:c).should_not include(:primary_key)
         
     | 
| 
      
 35 
     | 
    
         
            +
                @c.association_reflection(:c).primary_key.should == :id
         
     | 
| 
       36 
36 
     | 
    
         
             
              end
         
     | 
| 
       37 
37 
     | 
    
         
             
            end
         
     | 
| 
       38 
38 
     | 
    
         | 
| 
         @@ -46,7 +46,7 @@ end 
     | 
|
| 
       46 
46 
     | 
    
         
             
            describe Sequel::Model, "many_to_one" do
         
     | 
| 
       47 
47 
     | 
    
         
             
              before do
         
     | 
| 
       48 
48 
     | 
    
         
             
                MODEL_DB.reset
         
     | 
| 
       49 
     | 
    
         
            -
             
     | 
| 
      
 49 
     | 
    
         
            +
                
         
     | 
| 
       50 
50 
     | 
    
         
             
                @c2 = Class.new(Sequel::Model(:nodes)) do
         
     | 
| 
       51 
51 
     | 
    
         
             
                  unrestrict_primary_key
         
     | 
| 
       52 
52 
     | 
    
         
             
                  columns :id, :parent_id, :par_parent_id, :blah
         
     | 
| 
         @@ -105,6 +105,12 @@ describe Sequel::Model, "many_to_one" do 
     | 
|
| 
       105 
105 
     | 
    
         
             
                MODEL_DB.sqls.should == ["SELECT * FROM nodes WHERE (nodes.id = 567) LIMIT 1"]
         
     | 
| 
       106 
106 
     | 
    
         
             
              end
         
     | 
| 
       107 
107 
     | 
    
         | 
| 
      
 108 
     | 
    
         
            +
              it "should use :primary_key option if given" do
         
     | 
| 
      
 109 
     | 
    
         
            +
                @c2.many_to_one :parent, :class => @c2, :key => :blah, :primary_key => :pk
         
     | 
| 
      
 110 
     | 
    
         
            +
                @c2.new(:id => 1, :blah => 567).parent
         
     | 
| 
      
 111 
     | 
    
         
            +
                MODEL_DB.sqls.should == ["SELECT * FROM nodes WHERE (nodes.pk = 567) LIMIT 1"]
         
     | 
| 
      
 112 
     | 
    
         
            +
              end
         
     | 
| 
      
 113 
     | 
    
         
            +
             
     | 
| 
       108 
114 
     | 
    
         
             
              it "should use :select option if given" do
         
     | 
| 
       109 
115 
     | 
    
         
             
                @c2.many_to_one :parent, :class => @c2, :key => :blah, :select=>[:id, :name]
         
     | 
| 
       110 
116 
     | 
    
         
             
                @c2.new(:id => 1, :blah => 567).parent
         
     | 
| 
         @@ -157,6 +163,21 @@ describe Sequel::Model, "many_to_one" do 
     | 
|
| 
       157 
163 
     | 
    
         
             
                d.values.should == {:id => 1, :parent_id => 6677}
         
     | 
| 
       158 
164 
     | 
    
         
             
              end
         
     | 
| 
       159 
165 
     | 
    
         | 
| 
      
 166 
     | 
    
         
            +
              it "should have the setter method respect the :primary_key option" do
         
     | 
| 
      
 167 
     | 
    
         
            +
                @c2.many_to_one :parent, :class => @c2, :primary_key=>:blah
         
     | 
| 
      
 168 
     | 
    
         
            +
             
     | 
| 
      
 169 
     | 
    
         
            +
                d = @c2.new(:id => 1)
         
     | 
| 
      
 170 
     | 
    
         
            +
                d.parent = @c2.new(:id => 4321, :blah=>444)
         
     | 
| 
      
 171 
     | 
    
         
            +
                d.values.should == {:id => 1, :parent_id => 444}
         
     | 
| 
      
 172 
     | 
    
         
            +
             
     | 
| 
      
 173 
     | 
    
         
            +
                d.parent = nil
         
     | 
| 
      
 174 
     | 
    
         
            +
                d.values.should == {:id => 1, :parent_id => nil}
         
     | 
| 
      
 175 
     | 
    
         
            +
             
     | 
| 
      
 176 
     | 
    
         
            +
                e = @c2.new(:id => 6677, :blah=>8)
         
     | 
| 
      
 177 
     | 
    
         
            +
                d.parent = e
         
     | 
| 
      
 178 
     | 
    
         
            +
                d.values.should == {:id => 1, :parent_id => 8}
         
     | 
| 
      
 179 
     | 
    
         
            +
              end
         
     | 
| 
      
 180 
     | 
    
         
            +
              
         
     | 
| 
       160 
181 
     | 
    
         
             
              it "should not persist changes until saved" do
         
     | 
| 
       161 
182 
     | 
    
         
             
                @c2.many_to_one :parent, :class => @c2
         
     | 
| 
       162 
183 
     | 
    
         | 
| 
         @@ -289,6 +310,14 @@ describe Sequel::Model, "many_to_one" do 
     | 
|
| 
       289 
310 
     | 
    
         
             
                @c2.instance_methods.collect{|x| x.to_s}.should_not(include('parent='))
         
     | 
| 
       290 
311 
     | 
    
         
             
              end
         
     | 
| 
       291 
312 
     | 
    
         | 
| 
      
 313 
     | 
    
         
            +
              it "should not add associations methods directly to class" do
         
     | 
| 
      
 314 
     | 
    
         
            +
                @c2.many_to_one :parent, :class => @c2
         
     | 
| 
      
 315 
     | 
    
         
            +
                @c2.instance_methods.collect{|x| x.to_s}.should(include('parent'))
         
     | 
| 
      
 316 
     | 
    
         
            +
                @c2.instance_methods.collect{|x| x.to_s}.should(include('parent='))
         
     | 
| 
      
 317 
     | 
    
         
            +
                @c2.instance_methods(false).collect{|x| x.to_s}.should_not(include('parent'))
         
     | 
| 
      
 318 
     | 
    
         
            +
                @c2.instance_methods(false).collect{|x| x.to_s}.should_not(include('parent='))
         
     | 
| 
      
 319 
     | 
    
         
            +
              end
         
     | 
| 
      
 320 
     | 
    
         
            +
             
     | 
| 
       292 
321 
     | 
    
         
             
              it "should raise an error if trying to set a model object that doesn't have a valid primary key" do
         
     | 
| 
       293 
322 
     | 
    
         
             
                @c2.many_to_one :parent, :class => @c2
         
     | 
| 
       294 
323 
     | 
    
         
             
                p = @c2.new
         
     | 
| 
         @@ -520,6 +549,18 @@ describe Sequel::Model, "one_to_many" do 
     | 
|
| 
       520 
549 
     | 
    
         
             
                MODEL_DB.sqls.should == ['UPDATE attributes SET node_id = NULL WHERE (id = 2345)']
         
     | 
| 
       521 
550 
     | 
    
         
             
              end
         
     | 
| 
       522 
551 
     | 
    
         | 
| 
      
 552 
     | 
    
         
            +
              it "should have add_ method respect the :primary_key option" do
         
     | 
| 
      
 553 
     | 
    
         
            +
                @c2.one_to_many :attributes, :class => @c1, :primary_key=>:xxx
         
     | 
| 
      
 554 
     | 
    
         
            +
                
         
     | 
| 
      
 555 
     | 
    
         
            +
                n = @c2.new(:id => 1234, :xxx=>5)
         
     | 
| 
      
 556 
     | 
    
         
            +
                a = @c1.new(:id => 2345)
         
     | 
| 
      
 557 
     | 
    
         
            +
                a.save!
         
     | 
| 
      
 558 
     | 
    
         
            +
                MODEL_DB.reset
         
     | 
| 
      
 559 
     | 
    
         
            +
                a.should == n.add_attribute(a)
         
     | 
| 
      
 560 
     | 
    
         
            +
                MODEL_DB.sqls.should == ['UPDATE attributes SET node_id = 5 WHERE (id = 2345)']
         
     | 
| 
      
 561 
     | 
    
         
            +
              end
         
     | 
| 
      
 562 
     | 
    
         
            +
             
     | 
| 
      
 563 
     | 
    
         
            +
              
         
     | 
| 
       523 
564 
     | 
    
         
             
              it "should raise an error in add_ and remove_ if the passed object returns false to save (is not valid)" do
         
     | 
| 
       524 
565 
     | 
    
         
             
                @c2.one_to_many :attributes, :class => @c1
         
     | 
| 
       525 
566 
     | 
    
         
             
                n = @c2.new(:id => 1234)
         
     | 
| 
         @@ -540,6 +581,12 @@ describe Sequel::Model, "one_to_many" do 
     | 
|
| 
       540 
581 
     | 
    
         
             
                proc{a.remove_all_attributes}.should raise_error(Sequel::Error)
         
     | 
| 
       541 
582 
     | 
    
         
             
              end
         
     | 
| 
       542 
583 
     | 
    
         | 
| 
      
 584 
     | 
    
         
            +
              it "should use :primary_key option if given" do
         
     | 
| 
      
 585 
     | 
    
         
            +
                @c1.one_to_many :nodes, :class => @c2, :primary_key => :node_id, :key=>:id
         
     | 
| 
      
 586 
     | 
    
         
            +
                n = @c1.load(:id => 1234, :node_id=>4321)
         
     | 
| 
      
 587 
     | 
    
         
            +
                n.nodes_dataset.sql.should == "SELECT * FROM nodes WHERE (nodes.id = 4321)"
         
     | 
| 
      
 588 
     | 
    
         
            +
              end
         
     | 
| 
      
 589 
     | 
    
         
            +
             
     | 
| 
       543 
590 
     | 
    
         
             
              it "should support a select option" do
         
     | 
| 
       544 
591 
     | 
    
         
             
                @c2.one_to_many :attributes, :class => @c1, :select => [:id, :name]
         
     | 
| 
       545 
592 
     | 
    
         | 
| 
         @@ -727,6 +774,22 @@ describe Sequel::Model, "one_to_many" do 
     | 
|
| 
       727 
774 
     | 
    
         
             
                im.should_not(include('remove_all_attributes'))
         
     | 
| 
       728 
775 
     | 
    
         
             
              end
         
     | 
| 
       729 
776 
     | 
    
         | 
| 
      
 777 
     | 
    
         
            +
              it "should not add associations methods directly to class" do
         
     | 
| 
      
 778 
     | 
    
         
            +
                @c2.one_to_many :attributes, :class => @c1
         
     | 
| 
      
 779 
     | 
    
         
            +
                im = @c2.instance_methods.collect{|x| x.to_s}
         
     | 
| 
      
 780 
     | 
    
         
            +
                im.should(include('attributes'))
         
     | 
| 
      
 781 
     | 
    
         
            +
                im.should(include('attributes_dataset'))
         
     | 
| 
      
 782 
     | 
    
         
            +
                im.should(include('add_attribute'))
         
     | 
| 
      
 783 
     | 
    
         
            +
                im.should(include('remove_attribute'))
         
     | 
| 
      
 784 
     | 
    
         
            +
                im.should(include('remove_all_attributes'))
         
     | 
| 
      
 785 
     | 
    
         
            +
                im2 = @c2.instance_methods(false).collect{|x| x.to_s}
         
     | 
| 
      
 786 
     | 
    
         
            +
                im2.should_not(include('attributes'))
         
     | 
| 
      
 787 
     | 
    
         
            +
                im2.should_not(include('attributes_dataset'))
         
     | 
| 
      
 788 
     | 
    
         
            +
                im2.should_not(include('add_attribute'))
         
     | 
| 
      
 789 
     | 
    
         
            +
                im2.should_not(include('remove_attribute'))
         
     | 
| 
      
 790 
     | 
    
         
            +
                im2.should_not(include('remove_all_attributes'))
         
     | 
| 
      
 791 
     | 
    
         
            +
              end
         
     | 
| 
      
 792 
     | 
    
         
            +
             
     | 
| 
       730 
793 
     | 
    
         
             
              it "should have has_many alias" do
         
     | 
| 
       731 
794 
     | 
    
         
             
                @c2.has_many :attributes, :class => @c1
         
     | 
| 
       732 
795 
     | 
    
         | 
| 
         @@ -777,6 +840,12 @@ describe Sequel::Model, "one_to_many" do 
     | 
|
| 
       777 
840 
     | 
    
         
             
                MODEL_DB.sqls.first.should == 'UPDATE attributes SET node_id = NULL WHERE (node_id = 1234)'
         
     | 
| 
       778 
841 
     | 
    
         
             
              end
         
     | 
| 
       779 
842 
     | 
    
         | 
| 
      
 843 
     | 
    
         
            +
              it "should have the remove_all_ method respect the :primary_key option" do
         
     | 
| 
      
 844 
     | 
    
         
            +
                @c2.one_to_many :attributes, :class => @c1, :primary_key=>:xxx
         
     | 
| 
      
 845 
     | 
    
         
            +
                @c2.new(:id => 1234, :xxx=>5).remove_all_attributes
         
     | 
| 
      
 846 
     | 
    
         
            +
                MODEL_DB.sqls.first.should == 'UPDATE attributes SET node_id = NULL WHERE (node_id = 5)'
         
     | 
| 
      
 847 
     | 
    
         
            +
              end
         
     | 
| 
      
 848 
     | 
    
         
            +
             
     | 
| 
       780 
849 
     | 
    
         
             
              it "remove_all should set the cached instance variable to []" do
         
     | 
| 
       781 
850 
     | 
    
         
             
                @c2.one_to_many :attributes, :class => @c1
         
     | 
| 
       782 
851 
     | 
    
         
             
                node = @c2.new(:id => 1234)
         
     | 
| 
         @@ -828,7 +897,7 @@ describe Sequel::Model, "one_to_many" do 
     | 
|
| 
       828 
897 
     | 
    
         
             
                att.values.should == {}
         
     | 
| 
       829 
898 
     | 
    
         
             
              end
         
     | 
| 
       830 
899 
     | 
    
         | 
| 
       831 
     | 
    
         
            -
              it "should not add a  
     | 
| 
      
 900 
     | 
    
         
            +
              it "should not add a setter method if the :one_to_one option is true and :read_only option is true" do
         
     | 
| 
       832 
901 
     | 
    
         
             
                @c2.one_to_many :attributes, :class => @c1, :one_to_one=>true, :read_only=>true
         
     | 
| 
       833 
902 
     | 
    
         
             
                im = @c2.instance_methods.collect{|x| x.to_s}
         
     | 
| 
       834 
903 
     | 
    
         
             
                im.should(include('attribute'))
         
     | 
| 
         @@ -861,6 +930,25 @@ describe Sequel::Model, "one_to_many" do 
     | 
|
| 
       861 
930 
     | 
    
         
             
                MODEL_DB.sqls.last.should == 'UPDATE attributes SET node_id = NULL WHERE ((node_id = 1234) AND (id != 3))'
         
     | 
| 
       862 
931 
     | 
    
         
             
              end
         
     | 
| 
       863 
932 
     | 
    
         | 
| 
      
 933 
     | 
    
         
            +
              it "should have the setter method for the :one_to_one option respect the :primary_key option" do
         
     | 
| 
      
 934 
     | 
    
         
            +
                @c2.one_to_many :attributes, :class => @c1, :one_to_one=>true, :primary_key=>:xxx
         
     | 
| 
      
 935 
     | 
    
         
            +
                attrib = @c1.new(:id=>3)
         
     | 
| 
      
 936 
     | 
    
         
            +
                d = @c1.dataset
         
     | 
| 
      
 937 
     | 
    
         
            +
                def d.fetch_rows(s); yield({:id=>3}) end
         
     | 
| 
      
 938 
     | 
    
         
            +
                @c2.new(:id => 1234, :xxx=>5).attribute = attrib
         
     | 
| 
      
 939 
     | 
    
         
            +
                ['INSERT INTO attributes (node_id, id) VALUES (5, 3)',
         
     | 
| 
      
 940 
     | 
    
         
            +
                  'INSERT INTO attributes (id, node_id) VALUES (3, 5)'].should(include(MODEL_DB.sqls.first))
         
     | 
| 
      
 941 
     | 
    
         
            +
                MODEL_DB.sqls.last.should == 'UPDATE attributes SET node_id = NULL WHERE ((node_id = 5) AND (id != 3))'
         
     | 
| 
      
 942 
     | 
    
         
            +
                MODEL_DB.sqls.length.should == 2
         
     | 
| 
      
 943 
     | 
    
         
            +
                @c2.new(:id => 321, :xxx=>5).attribute.should == attrib
         
     | 
| 
      
 944 
     | 
    
         
            +
                MODEL_DB.sqls.clear
         
     | 
| 
      
 945 
     | 
    
         
            +
                attrib = @c1.load(:id=>3)
         
     | 
| 
      
 946 
     | 
    
         
            +
                @c2.new(:id => 621, :xxx=>5).attribute = attrib
         
     | 
| 
      
 947 
     | 
    
         
            +
                MODEL_DB.sqls.length.should == 2
         
     | 
| 
      
 948 
     | 
    
         
            +
                MODEL_DB.sqls.first.should =~ /UPDATE attributes SET (node_id = 5, id = 3|id = 3, node_id = 5) WHERE \(id = 3\)/
         
     | 
| 
      
 949 
     | 
    
         
            +
                MODEL_DB.sqls.last.should == 'UPDATE attributes SET node_id = NULL WHERE ((node_id = 5) AND (id != 3))'
         
     | 
| 
      
 950 
     | 
    
         
            +
              end
         
     | 
| 
      
 951 
     | 
    
         
            +
             
     | 
| 
       864 
952 
     | 
    
         
             
              it "should raise an error if the one_to_one getter would be the same as the association name" do
         
     | 
| 
       865 
953 
     | 
    
         
             
                proc{@c2.one_to_many :song, :class => @c1, :one_to_one=>true}.should raise_error(Sequel::Error)
         
     | 
| 
       866 
954 
     | 
    
         
             
              end
         
     | 
| 
         @@ -873,7 +961,7 @@ describe Sequel::Model, "one_to_many" do 
     | 
|
| 
       873 
961 
     | 
    
         | 
| 
       874 
962 
     | 
    
         
             
              it "should make non getter and setter methods private if :one_to_one option is used" do 
         
     | 
| 
       875 
963 
     | 
    
         
             
                @c2.one_to_many :attributes, :class => @c1, :one_to_one=>true do |ds| end
         
     | 
| 
       876 
     | 
    
         
            -
                meths = @c2.private_instance_methods 
     | 
| 
      
 964 
     | 
    
         
            +
                meths = @c2.private_instance_methods.collect{|x| x.to_s}
         
     | 
| 
       877 
965 
     | 
    
         
             
                meths.should(include("attributes"))
         
     | 
| 
       878 
966 
     | 
    
         
             
                meths.should(include("add_attribute"))
         
     | 
| 
       879 
967 
     | 
    
         
             
                meths.should(include("attributes_dataset"))
         
     | 
| 
         @@ -994,6 +1082,7 @@ describe Sequel::Model, "many_to_many" do 
     | 
|
| 
       994 
1082 
     | 
    
         | 
| 
       995 
1083 
     | 
    
         
             
                @c1 = Class.new(Sequel::Model(:attributes)) do
         
     | 
| 
       996 
1084 
     | 
    
         
             
                  unrestrict_primary_key
         
     | 
| 
      
 1085 
     | 
    
         
            +
                  attr_accessor :yyy
         
     | 
| 
       997 
1086 
     | 
    
         
             
                  def self.name; 'Attribute'; end
         
     | 
| 
       998 
1087 
     | 
    
         
             
                  def self.to_s; 'Attribute'; end
         
     | 
| 
       999 
1088 
     | 
    
         
             
                  columns :id
         
     | 
| 
         @@ -1081,6 +1170,11 @@ describe Sequel::Model, "many_to_many" do 
     | 
|
| 
       1081 
1170 
     | 
    
         
             
                a.sql.should == 'SELECT attributes.* FROM attributes INNER JOIN attributes_nodes ON ((attributes_nodes.attribute_id = attributes.id) AND (attributes_nodes.node_id = 1234)) ORDER BY blah1, blah2'
         
     | 
| 
       1082 
1171 
     | 
    
         
             
              end
         
     | 
| 
       1083 
1172 
     | 
    
         | 
| 
      
 1173 
     | 
    
         
            +
              it "should support :left_primary_key and :right_primary_key options" do
         
     | 
| 
      
 1174 
     | 
    
         
            +
                @c2.many_to_many :attributes, :class => @c1, :left_primary_key=>:xxx, :right_primary_key=>:yyy
         
     | 
| 
      
 1175 
     | 
    
         
            +
                @c2.new(:id => 1234, :xxx=>5).attributes_dataset.sql.should == 'SELECT attributes.* FROM attributes INNER JOIN attributes_nodes ON ((attributes_nodes.attribute_id = attributes.yyy) AND (attributes_nodes.node_id = 5))'
         
     | 
| 
      
 1176 
     | 
    
         
            +
              end
         
     | 
| 
      
 1177 
     | 
    
         
            +
              
         
     | 
| 
       1084 
1178 
     | 
    
         
             
              it "should support a select option" do
         
     | 
| 
       1085 
1179 
     | 
    
         
             
                @c2.many_to_many :attributes, :class => @c1, :select => :blah
         
     | 
| 
       1086 
1180 
     | 
    
         | 
| 
         @@ -1182,6 +1276,26 @@ describe Sequel::Model, "many_to_many" do 
     | 
|
| 
       1182 
1276 
     | 
    
         
             
                MODEL_DB.sqls.first.should == 'DELETE FROM attributes_nodes WHERE ((node_id = 1234) AND (attribute_id = 2345))'
         
     | 
| 
       1183 
1277 
     | 
    
         
             
              end
         
     | 
| 
       1184 
1278 
     | 
    
         | 
| 
      
 1279 
     | 
    
         
            +
              it "should have the add_ method respect the :left_primary_key and :right_primary_key options" do
         
     | 
| 
      
 1280 
     | 
    
         
            +
                @c2.many_to_many :attributes, :class => @c1, :left_primary_key=>:xxx, :right_primary_key=>:yyy
         
     | 
| 
      
 1281 
     | 
    
         
            +
                
         
     | 
| 
      
 1282 
     | 
    
         
            +
                n = @c2.new(:id => 1234, :xxx=>5)
         
     | 
| 
      
 1283 
     | 
    
         
            +
                a = @c1.new(:id => 2345, :yyy=>8)
         
     | 
| 
      
 1284 
     | 
    
         
            +
                a.should == n.add_attribute(a)
         
     | 
| 
      
 1285 
     | 
    
         
            +
                ['INSERT INTO attributes_nodes (node_id, attribute_id) VALUES (5, 8)',
         
     | 
| 
      
 1286 
     | 
    
         
            +
                 'INSERT INTO attributes_nodes (attribute_id, node_id) VALUES (8, 5)'
         
     | 
| 
      
 1287 
     | 
    
         
            +
                ].should(include(MODEL_DB.sqls.first))
         
     | 
| 
      
 1288 
     | 
    
         
            +
              end
         
     | 
| 
      
 1289 
     | 
    
         
            +
             
     | 
| 
      
 1290 
     | 
    
         
            +
              it "should have the remove_ method respect the :left_primary_key and :right_primary_key options" do
         
     | 
| 
      
 1291 
     | 
    
         
            +
                @c2.many_to_many :attributes, :class => @c1, :left_primary_key=>:xxx, :right_primary_key=>:yyy
         
     | 
| 
      
 1292 
     | 
    
         
            +
                
         
     | 
| 
      
 1293 
     | 
    
         
            +
                n = @c2.new(:id => 1234, :xxx=>5)
         
     | 
| 
      
 1294 
     | 
    
         
            +
                a = @c1.new(:id => 2345, :yyy=>8)
         
     | 
| 
      
 1295 
     | 
    
         
            +
                a.should == n.remove_attribute(a)
         
     | 
| 
      
 1296 
     | 
    
         
            +
                MODEL_DB.sqls.first.should == 'DELETE FROM attributes_nodes WHERE ((node_id = 5) AND (attribute_id = 8))'
         
     | 
| 
      
 1297 
     | 
    
         
            +
              end
         
     | 
| 
      
 1298 
     | 
    
         
            +
             
     | 
| 
       1185 
1299 
     | 
    
         
             
              it "should raise an error if the model object doesn't have a valid primary key" do
         
     | 
| 
       1186 
1300 
     | 
    
         
             
                @c2.many_to_many :attributes, :class => @c1 
         
     | 
| 
       1187 
1301 
     | 
    
         
             
                a = @c2.new
         
     | 
| 
         @@ -1300,6 +1414,22 @@ describe Sequel::Model, "many_to_many" do 
     | 
|
| 
       1300 
1414 
     | 
    
         
             
                im.should_not(include('remove_all_attributes'))
         
     | 
| 
       1301 
1415 
     | 
    
         
             
              end
         
     | 
| 
       1302 
1416 
     | 
    
         | 
| 
      
 1417 
     | 
    
         
            +
              it "should not add associations methods directly to class" do
         
     | 
| 
      
 1418 
     | 
    
         
            +
                @c2.many_to_many :attributes, :class => @c1
         
     | 
| 
      
 1419 
     | 
    
         
            +
                im = @c2.instance_methods.collect{|x| x.to_s}
         
     | 
| 
      
 1420 
     | 
    
         
            +
                im.should(include('attributes'))
         
     | 
| 
      
 1421 
     | 
    
         
            +
                im.should(include('attributes_dataset'))
         
     | 
| 
      
 1422 
     | 
    
         
            +
                im.should(include('add_attribute'))
         
     | 
| 
      
 1423 
     | 
    
         
            +
                im.should(include('remove_attribute'))
         
     | 
| 
      
 1424 
     | 
    
         
            +
                im.should(include('remove_all_attributes'))
         
     | 
| 
      
 1425 
     | 
    
         
            +
                im2 = @c2.instance_methods(false).collect{|x| x.to_s}
         
     | 
| 
      
 1426 
     | 
    
         
            +
                im2.should_not(include('attributes'))
         
     | 
| 
      
 1427 
     | 
    
         
            +
                im2.should_not(include('attributes_dataset'))
         
     | 
| 
      
 1428 
     | 
    
         
            +
                im2.should_not(include('add_attribute'))
         
     | 
| 
      
 1429 
     | 
    
         
            +
                im2.should_not(include('remove_attribute'))
         
     | 
| 
      
 1430 
     | 
    
         
            +
                im2.should_not(include('remove_all_attributes'))
         
     | 
| 
      
 1431 
     | 
    
         
            +
              end
         
     | 
| 
      
 1432 
     | 
    
         
            +
             
     | 
| 
       1303 
1433 
     | 
    
         
             
              it "should have has_and_belongs_to_many alias" do
         
     | 
| 
       1304 
1434 
     | 
    
         
             
                @c2.has_and_belongs_to_many :attributes, :class => @c1 
         
     | 
| 
       1305 
1435 
     | 
    
         | 
| 
         @@ -1315,6 +1445,12 @@ describe Sequel::Model, "many_to_many" do 
     | 
|
| 
       1315 
1445 
     | 
    
         
             
                MODEL_DB.sqls.first.should == 'DELETE FROM attributes_nodes WHERE (node_id = 1234)'
         
     | 
| 
       1316 
1446 
     | 
    
         
             
              end
         
     | 
| 
       1317 
1447 
     | 
    
         | 
| 
      
 1448 
     | 
    
         
            +
              it "should have the remove_all_ method respect the :left_primary_key option" do
         
     | 
| 
      
 1449 
     | 
    
         
            +
                @c2.many_to_many :attributes, :class => @c1, :left_primary_key=>:xxx
         
     | 
| 
      
 1450 
     | 
    
         
            +
                @c2.new(:id => 1234, :xxx=>5).remove_all_attributes
         
     | 
| 
      
 1451 
     | 
    
         
            +
                MODEL_DB.sqls.first.should == 'DELETE FROM attributes_nodes WHERE (node_id = 5)'
         
     | 
| 
      
 1452 
     | 
    
         
            +
              end
         
     | 
| 
      
 1453 
     | 
    
         
            +
             
     | 
| 
       1318 
1454 
     | 
    
         
             
              it "remove_all should set the cached instance variable to []" do
         
     | 
| 
       1319 
1455 
     | 
    
         
             
                @c2.many_to_many :attributes, :class => @c1
         
     | 
| 
       1320 
1456 
     | 
    
         
             
                node = @c2.new(:id => 1234)
         
     | 
| 
         @@ -1463,6 +1599,20 @@ describe Sequel::Model, "many_to_many" do 
     | 
|
| 
       1463 
1599 
     | 
    
         
             
                p.remove_attribute(c).should == nil
         
     | 
| 
       1464 
1600 
     | 
    
         
             
                p.attributes.should == [c]
         
     | 
| 
       1465 
1601 
     | 
    
         
             
              end
         
     | 
| 
      
 1602 
     | 
    
         
            +
             
     | 
| 
      
 1603 
     | 
    
         
            +
              it "should support a :uniq option that removes duplicates from the association" do
         
     | 
| 
      
 1604 
     | 
    
         
            +
                h = []
         
     | 
| 
      
 1605 
     | 
    
         
            +
                @c2.many_to_many :attributes, :class => @c1, :uniq=>true
         
     | 
| 
      
 1606 
     | 
    
         
            +
                @c1.class_eval do
         
     | 
| 
      
 1607 
     | 
    
         
            +
                  def @dataset.fetch_rows(sql)
         
     | 
| 
      
 1608 
     | 
    
         
            +
                    yield({:id=>20})
         
     | 
| 
      
 1609 
     | 
    
         
            +
                    yield({:id=>30})
         
     | 
| 
      
 1610 
     | 
    
         
            +
                    yield({:id=>20})
         
     | 
| 
      
 1611 
     | 
    
         
            +
                    yield({:id=>30})
         
     | 
| 
      
 1612 
     | 
    
         
            +
                  end
         
     | 
| 
      
 1613 
     | 
    
         
            +
                end
         
     | 
| 
      
 1614 
     | 
    
         
            +
                @c2.load(:id=>10, :parent_id=>20).attributes.should == [@c1.load(:id=>20), @c1.load(:id=>30)]
         
     | 
| 
      
 1615 
     | 
    
         
            +
              end
         
     | 
| 
       1466 
1616 
     | 
    
         
             
            end
         
     | 
| 
       1467 
1617 
     | 
    
         | 
| 
       1468 
1618 
     | 
    
         
             
            describe Sequel::Model, " association reflection methods" do
         
     | 
| 
         @@ -1514,4 +1664,15 @@ describe Sequel::Model, " association reflection methods" do 
     | 
|
| 
       1514 
1664 
     | 
    
         
             
                @c1.associate :one_to_many, :children, :class => @c1
         
     | 
| 
       1515 
1665 
     | 
    
         
             
                @c1.associations.sort_by{|x|x.to_s}.should == [:children, :parent]
         
     | 
| 
       1516 
1666 
     | 
    
         
             
              end
         
     | 
| 
      
 1667 
     | 
    
         
            +
             
     | 
| 
      
 1668 
     | 
    
         
            +
              it "association reflections should be copied upon subclasing" do
         
     | 
| 
      
 1669 
     | 
    
         
            +
                @c1.associate :many_to_one, :parent, :class => @c1
         
     | 
| 
      
 1670 
     | 
    
         
            +
                c = Class.new(@c1)
         
     | 
| 
      
 1671 
     | 
    
         
            +
                @c1.associations.should == [:parent]
         
     | 
| 
      
 1672 
     | 
    
         
            +
                c.associations.should == [:parent]
         
     | 
| 
      
 1673 
     | 
    
         
            +
                c.associate :many_to_one, :parent2, :class => @c1
         
     | 
| 
      
 1674 
     | 
    
         
            +
                @c1.associations.should == [:parent]
         
     | 
| 
      
 1675 
     | 
    
         
            +
                c.associations.sort_by{|x| x.to_s}.should == [:parent, :parent2]
         
     | 
| 
      
 1676 
     | 
    
         
            +
                c.instance_methods.map{|x| x.to_s}.should include('parent')
         
     | 
| 
      
 1677 
     | 
    
         
            +
              end
         
     | 
| 
       1517 
1678 
     | 
    
         
             
            end
         
     | 
| 
         @@ -18,7 +18,7 @@ describe Sequel::Model, "#eager" do 
     | 
|
| 
       18 
18 
     | 
    
         
             
                end
         
     | 
| 
       19 
19 
     | 
    
         | 
| 
       20 
20 
     | 
    
         
             
                class ::EagerBand < Sequel::Model(:bands)
         
     | 
| 
       21 
     | 
    
         
            -
                  columns :id
         
     | 
| 
      
 21 
     | 
    
         
            +
                  columns :id, :p_k
         
     | 
| 
       22 
22 
     | 
    
         
             
                  one_to_many :albums, :class=>'EagerAlbum', :key=>:band_id, :eager=>:tracks
         
     | 
| 
       23 
23 
     | 
    
         
             
                  one_to_many :graph_albums, :class=>'EagerAlbum', :key=>:band_id, :eager_graph=>:tracks
         
     | 
| 
       24 
24 
     | 
    
         
             
                  many_to_many :members, :class=>'EagerBandMember', :left_key=>:band_id, :right_key=>:member_id, :join_table=>:bm
         
     | 
| 
         @@ -38,7 +38,7 @@ describe Sequel::Model, "#eager" do 
     | 
|
| 
       38 
38 
     | 
    
         
             
                end
         
     | 
| 
       39 
39 
     | 
    
         | 
| 
       40 
40 
     | 
    
         
             
                class ::EagerGenre < Sequel::Model(:genres)
         
     | 
| 
       41 
     | 
    
         
            -
                  columns :id
         
     | 
| 
      
 41 
     | 
    
         
            +
                  columns :id, :xxx
         
     | 
| 
       42 
42 
     | 
    
         
             
                  many_to_many :albums, :class=>'EagerAlbum', :left_key=>:genre_id, :right_key=>:album_id, :join_table=>:ag
         
     | 
| 
       43 
43 
     | 
    
         
             
                end
         
     | 
| 
       44 
44 
     | 
    
         | 
| 
         @@ -418,6 +418,47 @@ describe Sequel::Model, "#eager" do 
     | 
|
| 
       418 
418 
     | 
    
         
             
                MODEL_DB.sqls.should == ['SELECT * FROM albums', "SELECT id, ag.album_id AS x_foreign_key_x FROM genres INNER JOIN ag ON ((ag.genre_id = genres.id) AND (ag.album_id IN (1)))"]
         
     | 
| 
       419 
419 
     | 
    
         
             
              end
         
     | 
| 
       420 
420 
     | 
    
         | 
| 
      
 421 
     | 
    
         
            +
              it "should respect the association's :primary_key option" do
         
     | 
| 
      
 422 
     | 
    
         
            +
                EagerAlbum.many_to_one :special_band, :class=>:EagerBand, :primary_key=>:p_k, :key=>:band_id
         
     | 
| 
      
 423 
     | 
    
         
            +
                EagerBand.dataset.extend(Module.new {
         
     | 
| 
      
 424 
     | 
    
         
            +
                  def fetch_rows(sql)
         
     | 
| 
      
 425 
     | 
    
         
            +
                    MODEL_DB.sqls << sql
         
     | 
| 
      
 426 
     | 
    
         
            +
                    yield({:p_k=>2, :id=>1})
         
     | 
| 
      
 427 
     | 
    
         
            +
                  end
         
     | 
| 
      
 428 
     | 
    
         
            +
                })
         
     | 
| 
      
 429 
     | 
    
         
            +
                as = EagerAlbum.eager(:special_band).all
         
     | 
| 
      
 430 
     | 
    
         
            +
                MODEL_DB.sqls.should == ['SELECT * FROM albums', "SELECT * FROM bands WHERE (bands.p_k IN (2))"]
         
     | 
| 
      
 431 
     | 
    
         
            +
                as.length.should == 1
         
     | 
| 
      
 432 
     | 
    
         
            +
                as.first.special_band.should == EagerBand.load(:p_k=>2, :id=>1)
         
     | 
| 
      
 433 
     | 
    
         
            +
                MODEL_DB.sqls.clear
         
     | 
| 
      
 434 
     | 
    
         
            +
                EagerAlbum.one_to_many :special_tracks, :class=>:EagerTrack, :primary_key=>:band_id, :key=>:album_id
         
     | 
| 
      
 435 
     | 
    
         
            +
                EagerTrack.dataset.extend(Module.new {
         
     | 
| 
      
 436 
     | 
    
         
            +
                  def fetch_rows(sql)
         
     | 
| 
      
 437 
     | 
    
         
            +
                    MODEL_DB.sqls << sql
         
     | 
| 
      
 438 
     | 
    
         
            +
                    yield({:album_id=>2, :id=>1})
         
     | 
| 
      
 439 
     | 
    
         
            +
                  end
         
     | 
| 
      
 440 
     | 
    
         
            +
                })
         
     | 
| 
      
 441 
     | 
    
         
            +
                as = EagerAlbum.eager(:special_tracks).all
         
     | 
| 
      
 442 
     | 
    
         
            +
                MODEL_DB.sqls.should == ['SELECT * FROM albums', "SELECT * FROM tracks WHERE (tracks.album_id IN (2))"]
         
     | 
| 
      
 443 
     | 
    
         
            +
                as.length.should == 1
         
     | 
| 
      
 444 
     | 
    
         
            +
                as.first.special_tracks.should == [EagerTrack.load(:album_id=>2, :id=>1)]
         
     | 
| 
      
 445 
     | 
    
         
            +
              end
         
     | 
| 
      
 446 
     | 
    
         
            +
             
     | 
| 
      
 447 
     | 
    
         
            +
              it "should respect many_to_many association's :left_primary_key and :right_primary_key options" do
         
     | 
| 
      
 448 
     | 
    
         
            +
                EagerAlbum.many_to_many :special_genres, :class=>:EagerGenre, :left_primary_key=>:band_id, :left_key=>:album_id, :right_primary_key=>:xxx, :right_key=>:genre_id, :join_table=>:ag
         
     | 
| 
      
 449 
     | 
    
         
            +
                EagerGenre.dataset.extend(Module.new {
         
     | 
| 
      
 450 
     | 
    
         
            +
                  def fetch_rows(sql)
         
     | 
| 
      
 451 
     | 
    
         
            +
                    MODEL_DB.sqls << sql
         
     | 
| 
      
 452 
     | 
    
         
            +
                    yield({:x_foreign_key_x=>2, :id=>5})
         
     | 
| 
      
 453 
     | 
    
         
            +
                    yield({:x_foreign_key_x=>2, :id=>6})
         
     | 
| 
      
 454 
     | 
    
         
            +
                  end
         
     | 
| 
      
 455 
     | 
    
         
            +
                })
         
     | 
| 
      
 456 
     | 
    
         
            +
                as = EagerAlbum.eager(:special_genres).all
         
     | 
| 
      
 457 
     | 
    
         
            +
                MODEL_DB.sqls.should == ['SELECT * FROM albums', "SELECT genres.*, ag.album_id AS x_foreign_key_x FROM genres INNER JOIN ag ON ((ag.genre_id = genres.xxx) AND (ag.album_id IN (2)))"]
         
     | 
| 
      
 458 
     | 
    
         
            +
                as.length.should == 1
         
     | 
| 
      
 459 
     | 
    
         
            +
                as.first.special_genres.should == [EagerGenre.load(:id=>5), EagerGenre.load(:id=>6)]
         
     | 
| 
      
 460 
     | 
    
         
            +
              end
         
     | 
| 
      
 461 
     | 
    
         
            +
             
     | 
| 
       421 
462 
     | 
    
         
             
              it "should use the :eager_loader association option when eager loading" do
         
     | 
| 
       422 
463 
     | 
    
         
             
                EagerAlbum.many_to_one :special_band, :eager_loader=>(proc do |key_hash, records, assocs| 
         
     | 
| 
       423 
464 
     | 
    
         
             
                  item = EagerBand.filter(:album_id=>records.collect{|r| [r.pk, r.pk*2]}.flatten).order(:name).first
         
     | 
| 
         @@ -427,7 +468,7 @@ describe Sequel::Model, "#eager" do 
     | 
|
| 
       427 
468 
     | 
    
         
             
                  items = EagerTrack.filter(:album_id=>records.collect{|r| [r.pk, r.pk*2]}.flatten).all
         
     | 
| 
       428 
469 
     | 
    
         
             
                  records.each{|r| r.associations[:special_tracks] = items}
         
     | 
| 
       429 
470 
     | 
    
         
             
                end)
         
     | 
| 
       430 
     | 
    
         
            -
                EagerAlbum.many_to_many :special_genres, :eager_loader=>(proc do |key_hash, records, assocs| 
         
     | 
| 
      
 471 
     | 
    
         
            +
                EagerAlbum.many_to_many :special_genres, :class=>:EagerGenre, :eager_loader=>(proc do |key_hash, records, assocs| 
         
     | 
| 
       431 
472 
     | 
    
         
             
                  items = EagerGenre.inner_join(:ag, [:genre_id]).filter(:album_id=>records.collect{|r| r.pk}).all
         
     | 
| 
       432 
473 
     | 
    
         
             
                  records.each{|r| r.associations[:special_genres] = items}
         
     | 
| 
       433 
474 
     | 
    
         
             
                end)
         
     | 
| 
         @@ -455,6 +496,16 @@ describe Sequel::Model, "#eager" do 
     | 
|
| 
       455 
496 
     | 
    
         
             
                MODEL_DB.sqls.length.should == 4
         
     | 
| 
       456 
497 
     | 
    
         
             
              end
         
     | 
| 
       457 
498 
     | 
    
         | 
| 
      
 499 
     | 
    
         
            +
              it "should respect :after_load callbacks on associations when eager loading" do
         
     | 
| 
      
 500 
     | 
    
         
            +
                EagerAlbum.many_to_one :al_band, :class=>'EagerBand', :key=>:band_id, :after_load=>proc{|o, a| a.id *=2}
         
     | 
| 
      
 501 
     | 
    
         
            +
                EagerAlbum.one_to_many :al_tracks, :class=>'EagerTrack', :key=>:album_id, :after_load=>proc{|o, os| os.each{|a| a.id *=2}}
         
     | 
| 
      
 502 
     | 
    
         
            +
                EagerAlbum.many_to_many :al_genres, :class=>'EagerGenre', :left_key=>:album_id, :right_key=>:genre_id, :join_table=>:ag, :after_load=>proc{|o, os| os.each{|a| a.id *=2}}
         
     | 
| 
      
 503 
     | 
    
         
            +
                a = EagerAlbum.eager(:al_band, :al_tracks, :al_genres).all.first
         
     | 
| 
      
 504 
     | 
    
         
            +
                a.should == EagerAlbum.load(:id => 1, :band_id => 2)
         
     | 
| 
      
 505 
     | 
    
         
            +
                a.al_band.should == EagerBand.load(:id=>4)
         
     | 
| 
      
 506 
     | 
    
         
            +
                a.al_tracks.should == [EagerTrack.load(:id=>6, :album_id=>1)]
         
     | 
| 
      
 507 
     | 
    
         
            +
                a.al_genres.should == [EagerGenre.load(:id=>8)]
         
     | 
| 
      
 508 
     | 
    
         
            +
              end
         
     | 
| 
       458 
509 
     | 
    
         
             
            end
         
     | 
| 
       459 
510 
     | 
    
         | 
| 
       460 
511 
     | 
    
         
             
            describe Sequel::Model, "#eager_graph" do
         
     | 
| 
         @@ -902,6 +953,42 @@ describe Sequel::Model, "#eager_graph" do 
     | 
|
| 
       902 
953 
     | 
    
         
             
                a[3].album.band.members.last.values.should == {:id => 6}
         
     | 
| 
       903 
954 
     | 
    
         
             
              end
         
     | 
| 
       904 
955 
     | 
    
         | 
| 
      
 956 
     | 
    
         
            +
              it "should respect the association's :primary_key option" do 
         
     | 
| 
      
 957 
     | 
    
         
            +
                GraphAlbum.many_to_one :inner_band, :class=>'GraphBand', :key=>:band_id, :primary_key=>:vocalist_id
         
     | 
| 
      
 958 
     | 
    
         
            +
                ds = GraphAlbum.eager_graph(:inner_band)
         
     | 
| 
      
 959 
     | 
    
         
            +
                ds.sql.should == 'SELECT albums.id, albums.band_id, inner_band.id AS inner_band_id, inner_band.vocalist_id FROM albums LEFT OUTER JOIN bands AS inner_band ON (inner_band.vocalist_id = albums.band_id)'
         
     | 
| 
      
 960 
     | 
    
         
            +
                def ds.fetch_rows(sql, &block)
         
     | 
| 
      
 961 
     | 
    
         
            +
                  yield({:id=>3, :band_id=>2, :inner_band_id=>5, :vocalist_id=>2})
         
     | 
| 
      
 962 
     | 
    
         
            +
                end
         
     | 
| 
      
 963 
     | 
    
         
            +
                as = ds.all
         
     | 
| 
      
 964 
     | 
    
         
            +
                as.should == [GraphAlbum.load(:id=>3, :band_id=>2)]
         
     | 
| 
      
 965 
     | 
    
         
            +
                as.first.inner_band.should == GraphBand.load(:id=>5, :vocalist_id=>2)
         
     | 
| 
      
 966 
     | 
    
         
            +
             
     | 
| 
      
 967 
     | 
    
         
            +
                GraphAlbum.one_to_many :right_tracks, :class=>'GraphTrack', :key=>:album_id, :primary_key=>:band_id
         
     | 
| 
      
 968 
     | 
    
         
            +
                ds = GraphAlbum.eager_graph(:right_tracks)
         
     | 
| 
      
 969 
     | 
    
         
            +
                ds.sql.should == 'SELECT albums.id, albums.band_id, right_tracks.id AS right_tracks_id, right_tracks.album_id FROM albums LEFT OUTER JOIN tracks AS right_tracks ON (right_tracks.album_id = albums.band_id)'
         
     | 
| 
      
 970 
     | 
    
         
            +
                def ds.fetch_rows(sql, &block)
         
     | 
| 
      
 971 
     | 
    
         
            +
                  yield({:id=>3, :band_id=>2, :right_tracks_id=>5, :album_id=>2})
         
     | 
| 
      
 972 
     | 
    
         
            +
                  yield({:id=>3, :band_id=>2, :right_tracks_id=>6, :album_id=>2})
         
     | 
| 
      
 973 
     | 
    
         
            +
                end
         
     | 
| 
      
 974 
     | 
    
         
            +
                as = ds.all
         
     | 
| 
      
 975 
     | 
    
         
            +
                as.should == [GraphAlbum.load(:id=>3, :band_id=>2)]
         
     | 
| 
      
 976 
     | 
    
         
            +
                as.first.right_tracks.should == [GraphTrack.load(:id=>5, :album_id=>2), GraphTrack.load(:id=>6, :album_id=>2)]
         
     | 
| 
      
 977 
     | 
    
         
            +
              end
         
     | 
| 
      
 978 
     | 
    
         
            +
             
     | 
| 
      
 979 
     | 
    
         
            +
              it "should respect many_to_many association's :left_primary_key and :right_primary_key options" do 
         
     | 
| 
      
 980 
     | 
    
         
            +
                GraphAlbum.many_to_many :inner_genres, :class=>'GraphGenre', :left_key=>:album_id, :left_primary_key=>:band_id, :right_key=>:genre_id, :right_primary_key=>:xxx, :join_table=>:ag
         
     | 
| 
      
 981 
     | 
    
         
            +
                ds = GraphAlbum.eager_graph(:inner_genres)
         
     | 
| 
      
 982 
     | 
    
         
            +
                ds.sql.should == 'SELECT albums.id, albums.band_id, inner_genres.id AS inner_genres_id FROM albums LEFT OUTER JOIN ag ON (ag.album_id = albums.band_id) LEFT OUTER JOIN genres AS inner_genres ON (inner_genres.xxx = ag.genre_id)'
         
     | 
| 
      
 983 
     | 
    
         
            +
                def ds.fetch_rows(sql, &block)
         
     | 
| 
      
 984 
     | 
    
         
            +
                  yield({:id=>3, :band_id=>2, :inner_genres_id=>5, :xxx=>12})
         
     | 
| 
      
 985 
     | 
    
         
            +
                  yield({:id=>3, :band_id=>2, :inner_genres_id=>6, :xxx=>22})
         
     | 
| 
      
 986 
     | 
    
         
            +
                end
         
     | 
| 
      
 987 
     | 
    
         
            +
                as = ds.all
         
     | 
| 
      
 988 
     | 
    
         
            +
                as.should == [GraphAlbum.load(:id=>3, :band_id=>2)]
         
     | 
| 
      
 989 
     | 
    
         
            +
                as.first.inner_genres.should == [GraphGenre.load(:id=>5), GraphGenre.load(:id=>6)]
         
     | 
| 
      
 990 
     | 
    
         
            +
              end
         
     | 
| 
      
 991 
     | 
    
         
            +
             
     | 
| 
       905 
992 
     | 
    
         
             
              it "should respect the association's :graph_select option" do 
         
     | 
| 
       906 
993 
     | 
    
         
             
                GraphAlbum.many_to_one :inner_band, :class=>'GraphBand', :key=>:band_id, :graph_select=>:vocalist_id
         
     | 
| 
       907 
994 
     | 
    
         
             
                GraphAlbum.eager_graph(:inner_band).sql.should == 'SELECT albums.id, albums.band_id, inner_band.vocalist_id FROM albums LEFT OUTER JOIN bands AS inner_band ON (inner_band.id = albums.band_id)'
         
     | 
| 
         @@ -970,6 +1057,17 @@ describe Sequel::Model, "#eager_graph" do 
     | 
|
| 
       970 
1057 
     | 
    
         
             
                GraphAlbum.eager_graph(:active_genres).sql.should == "SELECT albums.id, albums.band_id, active_genres.id AS active_genres_id FROM albums LEFT OUTER JOIN ag ON ((ag.album_id = albums.id) AND ('t' = albums.active)) LEFT OUTER JOIN genres AS active_genres ON ((active_genres.id = ag.genre_id) AND ('t' = ag.active))"
         
     | 
| 
       971 
1058 
     | 
    
         
             
              end
         
     | 
| 
       972 
1059 
     | 
    
         | 
| 
      
 1060 
     | 
    
         
            +
              it "should respect the association's :eager_grapher option" do 
         
     | 
| 
      
 1061 
     | 
    
         
            +
                GraphAlbum.many_to_one :active_band, :class=>'GraphBand', :key=>:band_id, :eager_grapher=>proc{|ds, aa, ta| ds.graph(GraphBand, {:active=>true}, :table_alias=>aa, :join_type=>:inner)}
         
     | 
| 
      
 1062 
     | 
    
         
            +
                GraphAlbum.eager_graph(:active_band).sql.should == "SELECT albums.id, albums.band_id, active_band.id AS active_band_id, active_band.vocalist_id FROM albums INNER JOIN bands AS active_band ON (active_band.active = 't')"
         
     | 
| 
      
 1063 
     | 
    
         
            +
             
     | 
| 
      
 1064 
     | 
    
         
            +
                GraphAlbum.one_to_many :right_tracks, :class=>'GraphTrack', :key=>:album_id, :eager_grapher=>proc{|ds, aa, ta| ds.graph(GraphTrack, nil, :join_type=>:natural, :table_alias=>aa)}
         
     | 
| 
      
 1065 
     | 
    
         
            +
                GraphAlbum.eager_graph(:right_tracks).sql.should == 'SELECT albums.id, albums.band_id, right_tracks.id AS right_tracks_id, right_tracks.album_id FROM albums NATURAL JOIN tracks AS right_tracks'
         
     | 
| 
      
 1066 
     | 
    
         
            +
             
     | 
| 
      
 1067 
     | 
    
         
            +
                GraphAlbum.many_to_many :active_genres, :class=>'GraphGenre', :eager_grapher=>proc{|ds, aa, ta| ds.graph(:ag, {:album_id=>:id}, :table_alias=>:a123, :implicit_qualifier=>ta).graph(GraphGenre, [:album_id], :table_alias=>aa)}
         
     | 
| 
      
 1068 
     | 
    
         
            +
                GraphAlbum.eager_graph(:active_genres).sql.should == "SELECT albums.id, albums.band_id, active_genres.id AS active_genres_id FROM albums LEFT OUTER JOIN ag AS a123 ON (a123.album_id = albums.id) LEFT OUTER JOIN genres AS active_genres USING (album_id)"
         
     | 
| 
      
 1069 
     | 
    
         
            +
              end
         
     | 
| 
      
 1070 
     | 
    
         
            +
             
     | 
| 
       973 
1071 
     | 
    
         
             
              it "should respect the association's :graph_only_conditions option" do 
         
     | 
| 
       974 
1072 
     | 
    
         
             
                GraphAlbum.many_to_one :active_band, :class=>'GraphBand', :key=>:band_id, :graph_only_conditions=>{:active=>true}
         
     | 
| 
       975 
1073 
     | 
    
         
             
                GraphAlbum.eager_graph(:active_band).sql.should == "SELECT albums.id, albums.band_id, active_band.id AS active_band_id, active_band.vocalist_id FROM albums LEFT OUTER JOIN bands AS active_band ON (active_band.active = 't')"
         
     | 
| 
         @@ -1026,4 +1124,10 @@ describe Sequel::Model, "#eager_graph" do 
     | 
|
| 
       1026 
1124 
     | 
    
         
             
                GraphAlbum.one_to_many :b_tracks, :class=>'GraphTrack', :key=>:album_id, :order=>[:id, :album_id]
         
     | 
| 
       1027 
1125 
     | 
    
         
             
                GraphAlbum.eager_graph(:a_genres, :b_tracks).sql.should == 'SELECT albums.id, albums.band_id, a_genres.id AS a_genres_id, b_tracks.id AS b_tracks_id, b_tracks.album_id FROM albums LEFT OUTER JOIN ag ON (ag.album_id = albums.id) LEFT OUTER JOIN genres AS a_genres ON (a_genres.id = ag.genre_id) LEFT OUTER JOIN tracks AS b_tracks ON (b_tracks.album_id = albums.id) ORDER BY a_genres.id, b_tracks.id, b_tracks.album_id'
         
     | 
| 
       1028 
1126 
     | 
    
         
             
              end
         
     | 
| 
      
 1127 
     | 
    
         
            +
             
     | 
| 
      
 1128 
     | 
    
         
            +
              it "should use the correct qualifier when graphing multiple tables with extra conditions" do
         
     | 
| 
      
 1129 
     | 
    
         
            +
                GraphAlbum.many_to_many :a_genres, :class=>'GraphGenre', :left_key=>:album_id, :right_key=>:genre_id, :join_table=>:ag
         
     | 
| 
      
 1130 
     | 
    
         
            +
                GraphAlbum.one_to_many :b_tracks, :class=>'GraphTrack', :key=>:album_id, :graph_conditions=>{:a=>:b}
         
     | 
| 
      
 1131 
     | 
    
         
            +
                GraphAlbum.eager_graph(:a_genres, :b_tracks).sql.should == 'SELECT albums.id, albums.band_id, a_genres.id AS a_genres_id, b_tracks.id AS b_tracks_id, b_tracks.album_id FROM albums LEFT OUTER JOIN ag ON (ag.album_id = albums.id) LEFT OUTER JOIN genres AS a_genres ON (a_genres.id = ag.genre_id) LEFT OUTER JOIN tracks AS b_tracks ON ((b_tracks.album_id = albums.id) AND (b_tracks.a = albums.b))'
         
     | 
| 
      
 1132 
     | 
    
         
            +
              end
         
     | 
| 
       1029 
1133 
     | 
    
         
             
            end
         
     |