sequel 3.29.0 → 3.30.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (106) hide show
  1. data/CHANGELOG +35 -3
  2. data/Rakefile +2 -1
  3. data/doc/association_basics.rdoc +11 -0
  4. data/doc/opening_databases.rdoc +2 -0
  5. data/doc/release_notes/3.30.0.txt +135 -0
  6. data/doc/testing.rdoc +17 -3
  7. data/lib/sequel/adapters/amalgalite.rb +2 -2
  8. data/lib/sequel/adapters/do/mysql.rb +5 -2
  9. data/lib/sequel/adapters/ibmdb.rb +2 -2
  10. data/lib/sequel/adapters/jdbc.rb +126 -43
  11. data/lib/sequel/adapters/jdbc/as400.rb +11 -3
  12. data/lib/sequel/adapters/jdbc/db2.rb +2 -1
  13. data/lib/sequel/adapters/jdbc/derby.rb +44 -19
  14. data/lib/sequel/adapters/jdbc/h2.rb +32 -19
  15. data/lib/sequel/adapters/jdbc/hsqldb.rb +21 -17
  16. data/lib/sequel/adapters/jdbc/jtds.rb +9 -4
  17. data/lib/sequel/adapters/jdbc/mssql.rb +3 -1
  18. data/lib/sequel/adapters/jdbc/mysql.rb +2 -1
  19. data/lib/sequel/adapters/jdbc/oracle.rb +21 -7
  20. data/lib/sequel/adapters/jdbc/postgresql.rb +3 -2
  21. data/lib/sequel/adapters/jdbc/sqlite.rb +2 -1
  22. data/lib/sequel/adapters/jdbc/sqlserver.rb +48 -18
  23. data/lib/sequel/adapters/mock.rb +2 -1
  24. data/lib/sequel/adapters/mysql.rb +4 -2
  25. data/lib/sequel/adapters/mysql2.rb +2 -2
  26. data/lib/sequel/adapters/odbc/mssql.rb +1 -1
  27. data/lib/sequel/adapters/openbase.rb +1 -1
  28. data/lib/sequel/adapters/oracle.rb +6 -6
  29. data/lib/sequel/adapters/postgres.rb +25 -12
  30. data/lib/sequel/adapters/shared/access.rb +14 -6
  31. data/lib/sequel/adapters/shared/db2.rb +36 -13
  32. data/lib/sequel/adapters/shared/firebird.rb +12 -5
  33. data/lib/sequel/adapters/shared/informix.rb +11 -3
  34. data/lib/sequel/adapters/shared/mssql.rb +94 -47
  35. data/lib/sequel/adapters/shared/mysql.rb +107 -49
  36. data/lib/sequel/adapters/shared/mysql_prepared_statements.rb +2 -2
  37. data/lib/sequel/adapters/shared/oracle.rb +54 -27
  38. data/lib/sequel/adapters/shared/postgres.rb +65 -26
  39. data/lib/sequel/adapters/shared/progress.rb +4 -1
  40. data/lib/sequel/adapters/shared/sqlite.rb +36 -20
  41. data/lib/sequel/adapters/sqlite.rb +2 -3
  42. data/lib/sequel/adapters/swift/mysql.rb +3 -2
  43. data/lib/sequel/adapters/swift/sqlite.rb +2 -2
  44. data/lib/sequel/adapters/tinytds.rb +14 -8
  45. data/lib/sequel/adapters/utils/emulate_offset_with_row_number.rb +7 -4
  46. data/lib/sequel/database/misc.rb +6 -2
  47. data/lib/sequel/dataset/graph.rb +33 -7
  48. data/lib/sequel/dataset/prepared_statements.rb +19 -5
  49. data/lib/sequel/dataset/sql.rb +611 -201
  50. data/lib/sequel/model/associations.rb +12 -5
  51. data/lib/sequel/model/base.rb +20 -5
  52. data/lib/sequel/plugins/sharding.rb +9 -29
  53. data/lib/sequel/sql.rb +2 -1
  54. data/lib/sequel/timezones.rb +14 -4
  55. data/lib/sequel/version.rb +1 -1
  56. data/spec/adapters/mysql_spec.rb +10 -0
  57. data/spec/adapters/oracle_spec.rb +1 -1
  58. data/spec/core/core_sql_spec.rb +3 -1
  59. data/spec/core/database_spec.rb +42 -0
  60. data/spec/core/dataset_spec.rb +10 -3
  61. data/spec/core/mock_adapter_spec.rb +4 -0
  62. data/spec/core/object_graph_spec.rb +38 -0
  63. data/spec/extensions/association_autoreloading_spec.rb +1 -10
  64. data/spec/extensions/association_dependencies_spec.rb +2 -12
  65. data/spec/extensions/association_pks_spec.rb +35 -39
  66. data/spec/extensions/caching_spec.rb +23 -50
  67. data/spec/extensions/class_table_inheritance_spec.rb +30 -82
  68. data/spec/extensions/composition_spec.rb +18 -13
  69. data/spec/extensions/hook_class_methods_spec.rb +65 -91
  70. data/spec/extensions/identity_map_spec.rb +33 -103
  71. data/spec/extensions/instance_filters_spec.rb +10 -21
  72. data/spec/extensions/instance_hooks_spec.rb +6 -24
  73. data/spec/extensions/json_serializer_spec.rb +4 -5
  74. data/spec/extensions/lazy_attributes_spec.rb +16 -20
  75. data/spec/extensions/list_spec.rb +17 -39
  76. data/spec/extensions/many_through_many_spec.rb +135 -277
  77. data/spec/extensions/migration_spec.rb +18 -15
  78. data/spec/extensions/named_timezones_spec.rb +1 -1
  79. data/spec/extensions/nested_attributes_spec.rb +97 -92
  80. data/spec/extensions/optimistic_locking_spec.rb +9 -20
  81. data/spec/extensions/prepared_statements_associations_spec.rb +22 -37
  82. data/spec/extensions/prepared_statements_safe_spec.rb +9 -27
  83. data/spec/extensions/prepared_statements_spec.rb +11 -30
  84. data/spec/extensions/prepared_statements_with_pk_spec.rb +6 -13
  85. data/spec/extensions/pretty_table_spec.rb +1 -6
  86. data/spec/extensions/rcte_tree_spec.rb +41 -43
  87. data/spec/extensions/schema_dumper_spec.rb +3 -6
  88. data/spec/extensions/serialization_spec.rb +20 -32
  89. data/spec/extensions/sharding_spec.rb +66 -140
  90. data/spec/extensions/single_table_inheritance_spec.rb +14 -36
  91. data/spec/extensions/spec_helper.rb +10 -64
  92. data/spec/extensions/sql_expr_spec.rb +20 -60
  93. data/spec/extensions/tactical_eager_loading_spec.rb +9 -19
  94. data/spec/extensions/timestamps_spec.rb +6 -6
  95. data/spec/extensions/to_dot_spec.rb +1 -2
  96. data/spec/extensions/touch_spec.rb +13 -14
  97. data/spec/extensions/tree_spec.rb +11 -26
  98. data/spec/extensions/update_primary_key_spec.rb +30 -24
  99. data/spec/extensions/validation_class_methods_spec.rb +30 -51
  100. data/spec/extensions/validation_helpers_spec.rb +16 -35
  101. data/spec/integration/dataset_test.rb +16 -4
  102. data/spec/integration/prepared_statement_test.rb +4 -2
  103. data/spec/model/eager_loading_spec.rb +16 -0
  104. data/spec/model/model_spec.rb +15 -1
  105. data/spec/model/record_spec.rb +60 -0
  106. metadata +23 -40
@@ -2,19 +2,8 @@ require File.join(File.dirname(File.expand_path(__FILE__)), "spec_helper")
2
2
 
3
3
  describe "instance_filters plugin" do
4
4
  before do
5
- @c = Class.new(Sequel::Model(:people)) do
6
- end
7
- @sql = sql = ''
8
- @v = v = [1]
5
+ @c = Class.new(Sequel::Model(:people))
9
6
  @c.dataset.quote_identifiers = false
10
- @c.dataset.meta_def(:update) do |opts|
11
- sql.replace(update_sql(opts))
12
- return v.first
13
- end
14
- @c.dataset.meta_def(:delete) do
15
- sql.replace(delete_sql)
16
- return v.first
17
- end
18
7
  @c.columns :id, :name, :num
19
8
  @c.plugin :instance_filters
20
9
  @p = @c.load(:id=>1, :name=>'John', :num=>1)
@@ -22,34 +11,34 @@ describe "instance_filters plugin" do
22
11
 
23
12
  specify "should raise an error when updating a stale record" do
24
13
  @p.update(:name=>'Bob')
25
- @sql.should == "UPDATE people SET name = 'Bob' WHERE (id = 1)"
14
+ MODEL_DB.sqls.should == ["UPDATE people SET name = 'Bob' WHERE (id = 1)"]
26
15
  @p.instance_filter(:name=>'Jim')
27
- @v.replace([0])
16
+ @p.this.numrows = 0
28
17
  proc{@p.update(:name=>'Joe')}.should raise_error(Sequel::Plugins::InstanceFilters::Error)
29
- @sql.should == "UPDATE people SET name = 'Joe' WHERE ((id = 1) AND (name = 'Jim'))"
18
+ MODEL_DB.sqls.should == ["UPDATE people SET name = 'Joe' WHERE ((id = 1) AND (name = 'Jim'))"]
30
19
  end
31
20
 
32
21
  specify "should raise an error when destroying a stale record" do
33
22
  @p.destroy
34
- @sql.should == "DELETE FROM people WHERE (id = 1)"
23
+ MODEL_DB.sqls.should == ["DELETE FROM people WHERE (id = 1)"]
35
24
  @p.instance_filter(:name=>'Jim')
36
- @v.replace([0])
25
+ @p.this.numrows = 0
37
26
  proc{@p.destroy}.should raise_error(Sequel::Plugins::InstanceFilters::Error)
38
- @sql.should == "DELETE FROM people WHERE ((id = 1) AND (name = 'Jim'))"
27
+ MODEL_DB.sqls.should == ["DELETE FROM people WHERE ((id = 1) AND (name = 'Jim'))"]
39
28
  end
40
29
 
41
30
  specify "should apply all instance filters" do
42
31
  @p.instance_filter(:name=>'Jim')
43
32
  @p.instance_filter{num > 2}
44
33
  @p.update(:name=>'Bob')
45
- @sql.should == "UPDATE people SET name = 'Bob' WHERE ((id = 1) AND (name = 'Jim') AND (num > 2))"
34
+ MODEL_DB.sqls.should == ["UPDATE people SET name = 'Bob' WHERE ((id = 1) AND (name = 'Jim') AND (num > 2))"]
46
35
  end
47
36
 
48
37
  specify "should drop instance filters after updating" do
49
38
  @p.instance_filter(:name=>'Joe')
50
39
  @p.update(:name=>'Joe')
51
- @sql.should == "UPDATE people SET name = 'Joe' WHERE ((id = 1) AND (name = 'Joe'))"
40
+ MODEL_DB.sqls.should == ["UPDATE people SET name = 'Joe' WHERE ((id = 1) AND (name = 'Joe'))"]
52
41
  @p.update(:name=>'Bob')
53
- @sql.should == "UPDATE people SET name = 'Bob' WHERE (id = 1)"
42
+ MODEL_DB.sqls.should == ["UPDATE people SET name = 'Bob' WHERE (id = 1)"]
54
43
  end
55
44
  end
@@ -180,29 +180,10 @@ end
180
180
 
181
181
  describe "InstanceHooks plugin with transactions" do
182
182
  before do
183
- @logger = Object.new
184
- def @logger.method_missing(meth, sql)
185
- (@sqls ||= []) << sql
186
- end
187
- def @logger.sqls
188
- @sqls
189
- end
190
- @db = Class.new(Sequel::Database) do
191
- def connect(*)
192
- Object.new
193
- end
194
- def log_connection_execute(conn, sql)
195
- execute(sql)
196
- end
197
- def execute(sql, opts={})
198
- @loggers.each{|l| l.info(sql)}
199
- end
200
- end.new(:loggers=>[@logger])
183
+ @db = Sequel.mock(:numrows=>1)
201
184
  pr = proc{|x| r(x)}
202
185
  @c = Class.new(Sequel::Model(@db[:items])) do
203
186
  attr_accessor :rb
204
- def _delete
205
- end
206
187
  def after_save
207
188
  db.execute('as')
208
189
  raise Sequel::Rollback if rb
@@ -218,33 +199,34 @@ describe "InstanceHooks plugin with transactions" do
218
199
  @or = @c.load({:id=>1})
219
200
  @or.rb = true
220
201
  @r = []
202
+ @db.sqls
221
203
  end
222
204
 
223
205
  it "should support after_commit_hook" do
224
206
  @o.after_commit_hook{@db.execute('ac1')}
225
207
  @o.after_commit_hook{@db.execute('ac2')}
226
208
  @o.save.should_not be_nil
227
- @logger.sqls.should == ['BEGIN', 'as', 'COMMIT', 'ac1', 'ac2']
209
+ @db.sqls.should == ['BEGIN', 'as', 'COMMIT', 'ac1', 'ac2']
228
210
  end
229
211
 
230
212
  it "should support after_rollback_hook" do
231
213
  @or.after_rollback_hook{@db.execute('ar1')}
232
214
  @or.after_rollback_hook{@db.execute('ar2')}
233
215
  @or.save.should be_nil
234
- @logger.sqls.should == ['BEGIN', 'as', 'ROLLBACK', 'ar1', 'ar2']
216
+ @db.sqls.should == ['BEGIN', 'as', 'ROLLBACK', 'ar1', 'ar2']
235
217
  end
236
218
 
237
219
  it "should support after_commit_hook" do
238
220
  @o.after_destroy_commit_hook{@db.execute('adc1')}
239
221
  @o.after_destroy_commit_hook{@db.execute('adc2')}
240
222
  @o.destroy.should_not be_nil
241
- @logger.sqls.should == ['BEGIN', 'ad', 'COMMIT', 'adc1', 'adc2']
223
+ @db.sqls.should == ['BEGIN', "DELETE FROM items WHERE (id = 1)", 'ad', 'COMMIT', 'adc1', 'adc2']
242
224
  end
243
225
 
244
226
  it "should support after_rollback_hook" do
245
227
  @or.after_destroy_rollback_hook{@db.execute('adr1')}
246
228
  @or.after_destroy_rollback_hook{@db.execute('adr2')}
247
229
  @or.destroy.should be_nil
248
- @logger.sqls.should == ['BEGIN', 'ad', 'ROLLBACK', 'adr1', 'adr2']
230
+ @db.sqls.should == ['BEGIN', "DELETE FROM items WHERE (id = 1)", 'ad', 'ROLLBACK', 'adr1', 'adr2']
249
231
  end
250
232
  end
@@ -102,8 +102,8 @@ describe "Sequel::Plugins::JsonSerializer" do
102
102
  end
103
103
 
104
104
  it "should support a to_json class and dataset method" do
105
- album = @album
106
- Album.dataset.meta_def(:all){[album]}
105
+ Album.dataset._fetch = {:id=>1, :name=>'RF', :artist_id=>2}
106
+ Artist.dataset._fetch = {:id=>2, :name=>'YJM'}
107
107
  JSON.parse(Album.to_json).should == [@album]
108
108
  JSON.parse(Album.to_json(:include=>:artist)).map{|x| x.artist}.should == [@artist]
109
109
  JSON.parse(Album.dataset.to_json(:only=>:name)).should == [Album.load(:name=>@album.name)]
@@ -112,7 +112,7 @@ describe "Sequel::Plugins::JsonSerializer" do
112
112
  it "should have dataset to_json method work with naked datasets" do
113
113
  album = @album
114
114
  ds = Album.dataset.naked
115
- ds.meta_def(:all){[album.values]}
115
+ ds._fetch = {:id=>1, :name=>'RF', :artist_id=>2}
116
116
  JSON.parse(ds.to_json).should == [@album.values.inject({}){|h, (k, v)| h[k.to_s] = v; h}]
117
117
  end
118
118
 
@@ -137,8 +137,7 @@ describe "Sequel::Plugins::JsonSerializer" do
137
137
  end
138
138
 
139
139
  it "should handle the :root option to qualify a dataset of records" do
140
- album = @album
141
- Album.dataset.meta_def(:all){[album, album]}
140
+ Album.dataset._fetch = [{:id=>1, :name=>'RF'}, {:id=>1, :name=>'RF'}]
142
141
  Album.dataset.to_json(:root=>true, :only => :id).to_s.should == '{"albums":[{"album":{"id":1}},{"album":{"id":1}}]}'
143
142
  end
144
143
 
@@ -1,8 +1,9 @@
1
1
  require File.join(File.dirname(File.expand_path(__FILE__)), "spec_helper")
2
+ require 'yaml'
2
3
 
3
4
  describe "Sequel::Plugins::LazyAttributes" do
4
5
  before do
5
- @db = MockDatabase.new
6
+ @db = Sequel.mock
6
7
  @db.meta_def(:schema){|*a| [[:id, {:type=>:integer}], [:name,{:type=>:string}]]}
7
8
  class ::LazyAttributesModel < Sequel::Model(@db[:la])
8
9
  plugin :lazy_attributes
@@ -10,27 +11,23 @@ describe "Sequel::Plugins::LazyAttributes" do
10
11
  meta_def(:columns){[:id, :name]}
11
12
  lazy_attributes :name
12
13
  meta_def(:columns){[:id]}
13
- ds = dataset
14
- def ds.fetch_rows(sql)
15
- execute(sql)
16
- select = @opts[:select]
17
- where = @opts[:where]
18
- block = @mod_block || proc{|s| s}
19
- if !where
20
- if select.include?(:name)
21
- yield(block[:id=>1, :name=>'1'])
22
- yield(block[:id=>2, :name=>'2'])
14
+ dataset._fetch = proc do |sql|
15
+ if sql !~ /WHERE/
16
+ if sql =~ /name/
17
+ [{:id=>1, :name=>'1'}, {:id=>2, :name=>'2'}]
23
18
  else
24
- yield(:id=>1)
25
- yield(:id=>2)
19
+ [{:id=>1}, {:id=>2}]
26
20
  end
27
21
  else
28
- i = where.args.last
29
- Array(i).each do |x|
22
+ if sql =~ /id IN \(([\d, ]+)\)/
23
+ $1.split(', ')
24
+ elsif sql =~ /id = (\d)/
25
+ [$1]
26
+ end.map do |x|
30
27
  if sql =~ /SELECT name FROM/
31
- yield(block[:name=>x.to_s])
28
+ {:name=>x.to_s}
32
29
  else
33
- yield(block[:id=>x, :name=>x.to_s])
30
+ {:id=>x.to_i, :name=>x.to_s}
34
31
  end
35
32
  end
36
33
  end
@@ -38,7 +35,7 @@ describe "Sequel::Plugins::LazyAttributes" do
38
35
  end
39
36
  @c = ::LazyAttributesModel
40
37
  @ds = LazyAttributesModel.dataset
41
- @db.reset
38
+ @db.sqls
42
39
  end
43
40
  after do
44
41
  Object.send(:remove_const, :LazyAttributesModel)
@@ -136,7 +133,7 @@ describe "Sequel::Plugins::LazyAttributes" do
136
133
 
137
134
  it "should work with the serialization plugin" do
138
135
  @c.plugin :serialization, :yaml, :name
139
- @ds.instance_variable_set(:@mod_block, proc{|s| s.merge(:name=>"--- #{s[:name].to_i*3}\n")})
136
+ @ds._fetch = [[{:id=>1}, {:id=>2}], [{:id=>1, :name=>"--- 3\n"}, {:id=>2, :name=>"--- 6\n"}], [{:id=>1}], [{:name=>"--- 3\n"}]]
140
137
  @c.with_identity_map do
141
138
  ms = @ds.all
142
139
  ms.map{|m| m.values}.should == [{:id=>1}, {:id=>2}]
@@ -146,7 +143,6 @@ describe "Sequel::Plugins::LazyAttributes" do
146
143
  ms.map{|m| m.name}.should == [3,6]
147
144
  @db.sqls.should == ['SELECT id FROM la', 'SELECT id, name FROM la WHERE (id IN (1, 2))']
148
145
  end
149
- @db.reset
150
146
  @c.with_identity_map do
151
147
  m = @ds.first
152
148
  m.values.should == {:id=>1}
@@ -8,32 +8,10 @@ describe "List plugin" do
8
8
  columns :id, :position, :scope_id, :pos
9
9
  plugin :list, opts
10
10
  self.use_transactions = false
11
-
12
- class << self
13
- attr_accessor :rows
14
- end
15
-
16
- def checked_transaction(opts={})
17
- return super if @in_transaction || !use_transaction?(opts)
18
- @in_transaction = true
19
- db.execute 'BEGIN'
20
- super
21
- db.execute 'COMMIT'
22
- @in_transaction = false
23
- end
24
11
  end
25
12
  c
26
13
  end
27
14
 
28
- def y(c, *hs)
29
- c.rows = hs
30
- ds = c.dataset
31
- def ds.fetch_rows(sql)
32
- db.execute(sql)
33
- yield model.rows.shift
34
- end
35
- end
36
-
37
15
  before do
38
16
  @c = klass
39
17
  @o = @c.load(:id=>7, :position=>3)
@@ -89,18 +67,18 @@ describe "List plugin" do
89
67
  end
90
68
 
91
69
  it "should have at_position return the model object at the given position" do
92
- y(@c, :id=>1, :position=>1)
70
+ @c.dataset._fetch = {:id=>1, :position=>1}
93
71
  @o.at_position(10).should == @c.load(:id=>1, :position=>1)
94
- y(@sc, :id=>2, :position=>2, :scope_id=>5)
72
+ @sc.dataset._fetch = {:id=>2, :position=>2, :scope_id=>5}
95
73
  @so.at_position(20).should == @sc.load(:id=>2, :position=>2, :scope_id=>5)
96
74
  @db.sqls.should == ["SELECT * FROM items WHERE (position = 10) ORDER BY position LIMIT 1",
97
75
  "SELECT * FROM items WHERE ((scope_id = 5) AND (position = 20)) ORDER BY scope_id, position LIMIT 1"]
98
76
  end
99
77
 
100
78
  it "should have last_position return the last position in the list" do
101
- y(@c, :max=>10)
79
+ @c.dataset._fetch = {:max=>10}
102
80
  @o.last_position.should == 10
103
- y(@sc, :max=>20)
81
+ @sc.dataset._fetch = {:max=>20}
104
82
  @so.last_position.should == 20
105
83
  @db.sqls.should == ["SELECT max(position) FROM items LIMIT 1",
106
84
  "SELECT max(position) FROM items WHERE (scope_id = 5) LIMIT 1"]
@@ -115,7 +93,7 @@ describe "List plugin" do
115
93
  end
116
94
 
117
95
  it "should have move_down without an argument move down a single position" do
118
- y(@c, :max=>10)
96
+ @c.dataset._fetch = {:max=>10}
119
97
  @o.move_down.should == @o
120
98
  @o.position.should == 4
121
99
  @db.sqls.should == ["SELECT max(position) FROM items LIMIT 1",
@@ -124,7 +102,7 @@ describe "List plugin" do
124
102
  end
125
103
 
126
104
  it "should have move_down with an argument move down the given number of positions" do
127
- y(@c, :max=>10)
105
+ @c.dataset._fetch = {:max=>10}
128
106
  @o.move_down(3).should == @o
129
107
  @o.position.should == 6
130
108
  @db.sqls.should == ["SELECT max(position) FROM items LIMIT 1",
@@ -141,11 +119,11 @@ describe "List plugin" do
141
119
 
142
120
  it "should have move_to raise an error if an invalid target is used" do
143
121
  proc{@o.move_to(0)}.should raise_error(Sequel::Error)
144
- y(@c, :max=>10)
122
+ @c.dataset._fetch = {:max=>10}
145
123
  proc{@o.move_to(11)}.should raise_error(Sequel::Error)
146
124
  end
147
125
 
148
- it "should have move_to use a transaction is the instance is configured to use transactions" do
126
+ it "should have move_to use a transaction if the instance is configured to use transactions" do
149
127
  @o.use_transactions = true
150
128
  @o.move_to(2)
151
129
  @db.sqls.should == ["BEGIN",
@@ -167,13 +145,13 @@ describe "List plugin" do
167
145
  end
168
146
 
169
147
  it "should have move to shift entries correctly between current and target if moving down" do
170
- y(@c, :max=>10)
148
+ @c.dataset._fetch = {:max=>10}
171
149
  @o.move_to(4)
172
150
  @db.sqls[1].should == "UPDATE items SET position = (position - 1) WHERE ((position >= 4) AND (position <= 4))"
173
151
  end
174
152
 
175
153
  it "should have move_to_bottom move the item to the last position" do
176
- y(@c, :max=>10)
154
+ @c.dataset._fetch = {:max=>10}
177
155
  @o.move_to_bottom
178
156
  @db.sqls.should == ["SELECT max(position) FROM items LIMIT 1",
179
157
  "UPDATE items SET position = (position - 1) WHERE ((position >= 4) AND (position <= 10))",
@@ -201,7 +179,7 @@ describe "List plugin" do
201
179
  end
202
180
 
203
181
  it "should have move_up with a negative argument move down the given number of positions" do
204
- y(@c, :max=>10)
182
+ @c.dataset._fetch = {:max=>10}
205
183
  @o.move_up(-1).should == @o
206
184
  @o.position.should == 4
207
185
  @db.sqls.should == ["SELECT max(position) FROM items LIMIT 1",
@@ -210,19 +188,19 @@ describe "List plugin" do
210
188
  end
211
189
 
212
190
  it "should have next return the next entry in the list if not given an argument" do
213
- y(@c, :id=>9, :position=>4)
191
+ @c.dataset._fetch = {:id=>9, :position=>4}
214
192
  @o.next.should == @c.load(:id=>9, :position=>4)
215
193
  @db.sqls.should == ["SELECT * FROM items WHERE (position = 4) ORDER BY position LIMIT 1"]
216
194
  end
217
195
 
218
196
  it "should have next return the entry the given number of positions below the instance if given an argument" do
219
- y(@c, :id=>9, :position=>5)
197
+ @c.dataset._fetch = {:id=>9, :position=>5}
220
198
  @o.next(2).should == @c.load(:id=>9, :position=>5)
221
199
  @db.sqls.should == ["SELECT * FROM items WHERE (position = 5) ORDER BY position LIMIT 1"]
222
200
  end
223
201
 
224
202
  it "should have next return a previous entry if given a negative argument" do
225
- y(@c, :id=>9, :position=>2)
203
+ @c.dataset._fetch = {:id=>9, :position=>2}
226
204
  @o.next(-1).should == @c.load(:id=>9, :position=>2)
227
205
  @db.sqls.should == ["SELECT * FROM items WHERE (position = 2) ORDER BY position LIMIT 1"]
228
206
  end
@@ -232,19 +210,19 @@ describe "List plugin" do
232
210
  end
233
211
 
234
212
  it "should have prev return the previous entry in the list if not given an argument" do
235
- y(@c, :id=>9, :position=>2)
213
+ @c.dataset._fetch = {:id=>9, :position=>2}
236
214
  @o.prev.should == @c.load(:id=>9, :position=>2)
237
215
  @db.sqls.should == ["SELECT * FROM items WHERE (position = 2) ORDER BY position LIMIT 1"]
238
216
  end
239
217
 
240
218
  it "should have prev return the entry the given number of positions above the instance if given an argument" do
241
- y(@c, :id=>9, :position=>1)
219
+ @c.dataset._fetch = {:id=>9, :position=>1}
242
220
  @o.prev(2).should == @c.load(:id=>9, :position=>1)
243
221
  @db.sqls.should == ["SELECT * FROM items WHERE (position = 1) ORDER BY position LIMIT 1"]
244
222
  end
245
223
 
246
224
  it "should have prev return a following entry if given a negative argument" do
247
- y(@c, :id=>9, :position=>4)
225
+ @c.dataset._fetch = {:id=>9, :position=>4}
248
226
  @o.prev(-1).should == @c.load(:id=>9, :position=>4)
249
227
  @db.sqls.should == ["SELECT * FROM items WHERE (position = 4) ORDER BY position LIMIT 1"]
250
228
  end
@@ -10,14 +10,11 @@ describe Sequel::Model, "many_through_many" do
10
10
  class ::Tag < Sequel::Model
11
11
  columns :id, :h1, :h2
12
12
  end
13
- MODEL_DB.reset
14
13
  @c1 = Artist
15
14
  @c2 = Tag
16
15
  @dataset = @c2.dataset
17
- def @dataset.fetch_rows(sql)
18
- @db << sql
19
- yield({:id=>1})
20
- end
16
+ @dataset._fetch = {:id=>1}
17
+ MODEL_DB.reset
21
18
  end
22
19
  after do
23
20
  Object.send(:remove_const, :Artist)
@@ -25,16 +22,20 @@ describe Sequel::Model, "many_through_many" do
25
22
  end
26
23
 
27
24
  it "should default to associating to other models in the same scope" do
28
- class ::AssociationModuleTest
29
- class Artist < Sequel::Model
30
- plugin :many_through_many
31
- many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]]
32
- end
33
- class Tag < Sequel::Model
25
+ begin
26
+ class ::AssociationModuleTest
27
+ class Artist < Sequel::Model
28
+ plugin :many_through_many
29
+ many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]]
30
+ end
31
+ class Tag < Sequel::Model
32
+ end
34
33
  end
35
- end
36
-
37
- ::AssociationModuleTest::Artist.association_reflection(:tags).associated_class.should == ::AssociationModuleTest::Tag
34
+
35
+ ::AssociationModuleTest::Artist.association_reflection(:tags).associated_class.should == ::AssociationModuleTest::Tag
36
+ ensure
37
+ Object.send(:remove_const, :AssociationModuleTest)
38
+ end
38
39
  end
39
40
 
40
41
  it "should raise an error if in invalid form of through is used" do
@@ -46,9 +47,7 @@ describe Sequel::Model, "many_through_many" do
46
47
  it "should allow only two arguments with the :through option" do
47
48
  @c1.many_through_many :tags, :through=>[[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]]
48
49
  n = @c1.load(:id => 1234)
49
- a = n.tags_dataset
50
- a.should be_a_kind_of(Sequel::Dataset)
51
- a.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234))'
50
+ n.tags_dataset.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234))'
52
51
  n.tags.should == [@c2.load(:id=>1)]
53
52
  end
54
53
 
@@ -56,18 +55,14 @@ describe Sequel::Model, "many_through_many" do
56
55
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]]
57
56
  @c1.many_through_many :other_tags, :clone=>:tags
58
57
  n = @c1.load(:id => 1234)
59
- a = n.other_tags_dataset
60
- a.should be_a_kind_of(Sequel::Dataset)
61
- a.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234))'
58
+ n.other_tags_dataset.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234))'
62
59
  n.tags.should == [@c2.load(:id=>1)]
63
60
  end
64
61
 
65
62
  it "should use join tables given" do
66
63
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]]
67
64
  n = @c1.load(:id => 1234)
68
- a = n.tags_dataset
69
- a.should be_a_kind_of(Sequel::Dataset)
70
- a.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234))'
65
+ n.tags_dataset.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234))'
71
66
  n.tags.should == [@c2.load(:id=>1)]
72
67
  end
73
68
 
@@ -76,9 +71,7 @@ describe Sequel::Model, "many_through_many" do
76
71
  end
77
72
  @c1.many_through_many :albums, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_artists, :album_id, :artist_id], [:artists, :id, :id], [:albums_artists, :artist_id, :album_id]]
78
73
  n = @c1.load(:id => 1234)
79
- a = n.albums_dataset
80
- a.should be_a_kind_of(Sequel::Dataset)
81
- a.sql.should == 'SELECT albums.* FROM albums INNER JOIN albums_artists ON (albums_artists.album_id = albums.id) INNER JOIN artists ON (artists.id = albums_artists.artist_id) INNER JOIN albums_artists AS albums_artists_0 ON (albums_artists_0.artist_id = artists.id) INNER JOIN albums AS albums_0 ON (albums_0.id = albums_artists_0.album_id) INNER JOIN albums_artists AS albums_artists_1 ON ((albums_artists_1.album_id = albums_0.id) AND (albums_artists_1.artist_id = 1234))'
74
+ n.albums_dataset.sql.should == 'SELECT albums.* FROM albums INNER JOIN albums_artists ON (albums_artists.album_id = albums.id) INNER JOIN artists ON (artists.id = albums_artists.artist_id) INNER JOIN albums_artists AS albums_artists_0 ON (albums_artists_0.artist_id = artists.id) INNER JOIN albums AS albums_0 ON (albums_0.id = albums_artists_0.album_id) INNER JOIN albums_artists AS albums_artists_1 ON ((albums_artists_1.album_id = albums_0.id) AND (albums_artists_1.artist_id = 1234))'
82
75
  n.albums.should == [Album.load(:id=>1, :x=>1)]
83
76
  Object.send(:remove_const, :Album)
84
77
  end
@@ -86,9 +79,7 @@ describe Sequel::Model, "many_through_many" do
86
79
  it "should use explicit class if given" do
87
80
  @c1.many_through_many :albums_tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :class=>Tag
88
81
  n = @c1.load(:id => 1234)
89
- a = n.albums_tags_dataset
90
- a.should be_a_kind_of(Sequel::Dataset)
91
- a.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234))'
82
+ n.albums_tags_dataset.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234))'
92
83
  n.albums_tags.should == [@c2.load(:id=>1)]
93
84
  end
94
85
 
@@ -96,9 +87,7 @@ describe Sequel::Model, "many_through_many" do
96
87
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :right_primary_key=>:tag_id, :left_primary_key=>:yyy
97
88
  n = @c1.load(:id => 1234)
98
89
  n.yyy = 85
99
- a = n.tags_dataset
100
- a.should be_a_kind_of(Sequel::Dataset)
101
- a.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.tag_id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 85))'
90
+ n.tags_dataset.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.tag_id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 85))'
102
91
  n.tags.should == [@c2.load(:id=>1)]
103
92
  end
104
93
 
@@ -106,9 +95,7 @@ describe Sequel::Model, "many_through_many" do
106
95
  @c1.many_through_many :tags, [[:albums_artists, [:b1, :b2], [:c1, :c2]], [:albums, [:d1, :d2], [:e1, :e2]], [:albums_tags, [:f1, :f2], [:g1, :g2]]], :right_primary_key=>[:h1, :h2], :left_primary_key=>[:id, :yyy]
107
96
  n = @c1.load(:id => 1234)
108
97
  n.yyy = 85
109
- a = n.tags_dataset
110
- a.should be_a_kind_of(Sequel::Dataset)
111
- a.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON ((albums_tags.g1 = tags.h1) AND (albums_tags.g2 = tags.h2)) INNER JOIN albums ON ((albums.e1 = albums_tags.f1) AND (albums.e2 = albums_tags.f2)) INNER JOIN albums_artists ON ((albums_artists.c1 = albums.d1) AND (albums_artists.c2 = albums.d2) AND (albums_artists.b1 = 1234) AND (albums_artists.b2 = 85))'
98
+ n.tags_dataset.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON ((albums_tags.g1 = tags.h1) AND (albums_tags.g2 = tags.h2)) INNER JOIN albums ON ((albums.e1 = albums_tags.f1) AND (albums.e2 = albums_tags.f2)) INNER JOIN albums_artists ON ((albums_artists.c1 = albums.d1) AND (albums_artists.c2 = albums.d2) AND (albums_artists.b1 = 1234) AND (albums_artists.b2 = 85))'
112
99
  n.tags.should == [@c2.load(:id=>1)]
113
100
  end
114
101
 
@@ -191,52 +178,40 @@ describe Sequel::Model, "many_through_many" do
191
178
  it "should support a :conditions option" do
192
179
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :conditions=>{:a=>32}
193
180
  n = @c1.load(:id => 1234)
194
- a = n.tags_dataset
195
- a.should be_a_kind_of(Sequel::Dataset)
196
- a.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234)) WHERE (a = 32)'
181
+ n.tags_dataset.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234)) WHERE (a = 32)'
197
182
  n.tags.should == [@c2.load(:id=>1)]
198
183
 
199
184
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :conditions=>['a = ?', 42]
200
185
  n = @c1.load(:id => 1234)
201
- a = n.tags_dataset
202
- a.should be_a_kind_of(Sequel::Dataset)
203
- a.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234)) WHERE (a = 42)'
186
+ n.tags_dataset.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234)) WHERE (a = 42)'
204
187
  n.tags.should == [@c2.load(:id=>1)]
205
188
  end
206
189
 
207
190
  it "should support an :order option" do
208
191
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :order=>:blah
209
192
  n = @c1.load(:id => 1234)
210
- a = n.tags_dataset
211
- a.should be_a_kind_of(Sequel::Dataset)
212
- a.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234)) ORDER BY blah'
193
+ n.tags_dataset.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234)) ORDER BY blah'
213
194
  n.tags.should == [@c2.load(:id=>1)]
214
195
  end
215
196
 
216
197
  it "should support an array for the :order option" do
217
198
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :order=>[:blah1, :blah2]
218
199
  n = @c1.load(:id => 1234)
219
- a = n.tags_dataset
220
- a.should be_a_kind_of(Sequel::Dataset)
221
- a.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234)) ORDER BY blah1, blah2'
200
+ n.tags_dataset.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234)) ORDER BY blah1, blah2'
222
201
  n.tags.should == [@c2.load(:id=>1)]
223
202
  end
224
203
 
225
204
  it "should support a select option" do
226
205
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :select=>:blah
227
206
  n = @c1.load(:id => 1234)
228
- a = n.tags_dataset
229
- a.should be_a_kind_of(Sequel::Dataset)
230
- a.sql.should == 'SELECT blah FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234))'
207
+ n.tags_dataset.sql.should == 'SELECT blah FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234))'
231
208
  n.tags.should == [@c2.load(:id=>1)]
232
209
  end
233
210
 
234
211
  it "should support an array for the select option" do
235
212
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :select=>[:tags.*, :albums__name]
236
213
  n = @c1.load(:id => 1234)
237
- a = n.tags_dataset
238
- a.should be_a_kind_of(Sequel::Dataset)
239
- a.sql.should == 'SELECT tags.*, albums.name FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234))'
214
+ n.tags_dataset.sql.should == 'SELECT tags.*, albums.name FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234))'
240
215
  n.tags.should == [@c2.load(:id=>1)]
241
216
  end
242
217
 
@@ -244,9 +219,7 @@ describe Sequel::Model, "many_through_many" do
244
219
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]] do |ds| ds.filter(:yyy=>@yyy) end
245
220
  n = @c1.load(:id => 1234)
246
221
  n.yyy = 85
247
- a = n.tags_dataset
248
- a.should be_a_kind_of(Sequel::Dataset)
249
- a.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234)) WHERE (yyy = 85)'
222
+ n.tags_dataset.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234)) WHERE (yyy = 85)'
250
223
  n.tags.should == [@c2.load(:id=>1)]
251
224
  end
252
225
 
@@ -254,34 +227,26 @@ describe Sequel::Model, "many_through_many" do
254
227
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :order=>:blah do |ds| ds.filter(:yyy=>@yyy) end
255
228
  n = @c1.load(:id => 1234)
256
229
  n.yyy = 85
257
- a = n.tags_dataset
258
- a.should be_a_kind_of(Sequel::Dataset)
259
- a.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234)) WHERE (yyy = 85) ORDER BY blah'
230
+ n.tags_dataset.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234)) WHERE (yyy = 85) ORDER BY blah'
260
231
  n.tags.should == [@c2.load(:id=>1)]
261
232
  end
262
233
 
263
234
  it "should support a :dataset option that is used instead of the default" do
264
235
  @c1.many_through_many :tags, [[:a, :b, :c]], :dataset=>proc{Tag.join(:albums_tags, [:tag_id]).join(:albums, [:album_id]).join(:albums_artists, [:album_id]).filter(:albums_artists__artist_id=>id)}
265
236
  n = @c1.load(:id => 1234)
266
- a = n.tags_dataset
267
- a.should be_a_kind_of(Sequel::Dataset)
268
- a.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags USING (tag_id) INNER JOIN albums USING (album_id) INNER JOIN albums_artists USING (album_id) WHERE (albums_artists.artist_id = 1234)'
237
+ n.tags_dataset.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags USING (tag_id) INNER JOIN albums USING (album_id) INNER JOIN albums_artists USING (album_id) WHERE (albums_artists.artist_id = 1234)'
269
238
  n.tags.should == [@c2.load(:id=>1)]
270
239
  end
271
240
 
272
241
  it "should support a :limit option" do
273
242
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :limit=>10
274
243
  n = @c1.load(:id => 1234)
275
- a = n.tags_dataset
276
- a.should be_a_kind_of(Sequel::Dataset)
277
- a.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234)) LIMIT 10'
244
+ n.tags_dataset.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234)) LIMIT 10'
278
245
  n.tags.should == [@c2.load(:id=>1)]
279
246
 
280
247
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :limit=>[10, 10]
281
248
  n = @c1.load(:id => 1234)
282
- a = n.tags_dataset
283
- a.should be_a_kind_of(Sequel::Dataset)
284
- a.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234)) LIMIT 10 OFFSET 10'
249
+ n.tags_dataset.sql.should == 'SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234)) LIMIT 10 OFFSET 10'
285
250
  n.tags.should == [@c2.load(:id=>1)]
286
251
  end
287
252
 
@@ -305,7 +270,7 @@ describe Sequel::Model, "many_through_many" do
305
270
  n.tags.should == [@c2.load(:id=>1)]
306
271
  MODEL_DB.sqls.should == ['SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234))']
307
272
  n.associations[:tags].should == n.tags
308
- MODEL_DB.sqls.length.should == 1
273
+ MODEL_DB.sqls.length.should == 0
309
274
  end
310
275
 
311
276
  it "should use cached instance variable if available" do
@@ -324,7 +289,7 @@ describe Sequel::Model, "many_through_many" do
324
289
  n.tags(true).should == [@c2.load(:id=>1)]
325
290
  MODEL_DB.sqls.should == ['SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1234))']
326
291
  n.associations[:tags].should == n.tags
327
- MODEL_DB.sqls.length.should == 1
292
+ MODEL_DB.sqls.length.should == 0
328
293
  end
329
294
 
330
295
  it "should not add associations methods directly to class" do
@@ -341,18 +306,13 @@ describe Sequel::Model, "many_through_many" do
341
306
  h = []
342
307
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :after_load=>:al
343
308
  @c1.class_eval do
344
- class_variable_set(:@@blah, h)
309
+ self::Foo = h
345
310
  def al(v)
346
- v.each{|x| self.class.send(:class_variable_get, :@@blah) << x.pk * 20}
347
- end
348
- end
349
- @c2.class_eval do
350
- def @dataset.fetch_rows(sql)
351
- yield({:id=>20})
352
- yield({:id=>30})
311
+ v.each{|x| model::Foo << x.pk * 20}
353
312
  end
354
313
  end
355
- p = @c1.load(:id=>10, :parent_id=>20)
314
+ @c2.dataset._fetch = [{:id=>20}, {:id=>30}]
315
+ p = @c1.load(:id=>10, :parent_id=>20)
356
316
  p.tags
357
317
  h.should == [400, 600]
358
318
  p.tags.collect{|a| a.pk}.should == [20, 30]
@@ -361,14 +321,7 @@ describe Sequel::Model, "many_through_many" do
361
321
  it "should support a :uniq option that removes duplicates from the association" do
362
322
  h = []
363
323
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :uniq=>true
364
- @c2.class_eval do
365
- def @dataset.fetch_rows(sql)
366
- yield({:id=>20})
367
- yield({:id=>30})
368
- yield({:id=>20})
369
- yield({:id=>30})
370
- end
371
- end
324
+ @c2.dataset._fetch = [{:id=>20}, {:id=>30}, {:id=>20}, {:id=>30}]
372
325
  @c1.load(:id=>10).tags.should == [@c2.load(:id=>20), @c2.load(:id=>30)]
373
326
  end
374
327
  end
@@ -429,57 +382,40 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
429
382
  end
430
383
  class ::Track < Sequel::Model
431
384
  end
432
-
433
- Artist.dataset.extend(Module.new {
434
- def columns
435
- [:id]
436
- end
437
-
438
- def fetch_rows(sql)
439
- @db << sql
440
- h = {:id => 1}
441
- if sql =~ /FROM artists LEFT OUTER JOIN albums_artists/
442
- h[:tags_id] = 2
443
- h[:albums_0_id] = 3 if sql =~ /LEFT OUTER JOIN albums AS albums_0/
444
- h[:tracks_id] = 4 if sql =~ /LEFT OUTER JOIN tracks/
445
- h[:other_tags_id] = 9 if sql =~ /other_tags\.id AS other_tags_id/
446
- h[:artists_0_id] = 10 if sql =~ /artists_0\.id AS artists_0_id/
447
- end
448
- yield h
449
- end
450
- })
451
-
452
- Tag.dataset.extend(Module.new {
453
- def fetch_rows(sql)
454
- @db << sql
455
- h = {:id => 2}
456
- if sql =~ /albums_artists.artist_id IN \(([18])\)/
457
- h.merge!(:x_foreign_key_x=>$1.to_i)
458
- elsif sql =~ /\(\(albums_artists.b1, albums_artists.b2\) IN \(\(1, 8\)\)\)/
459
- h.merge!(:x_foreign_key_0_x=>1, :x_foreign_key_1_x=>8)
460
- end
461
- h[:tag_id] = h.delete(:id) if sql =~ /albums_artists.artist_id IN \(8\)/
462
- yield h
385
+ Artist.dataset.columns(:id)._fetch = proc do |sql|
386
+ h = {:id => 1}
387
+ if sql =~ /FROM artists LEFT OUTER JOIN albums_artists/
388
+ h[:tags_id] = 2
389
+ h[:albums_0_id] = 3 if sql =~ /LEFT OUTER JOIN albums AS albums_0/
390
+ h[:tracks_id] = 4 if sql =~ /LEFT OUTER JOIN tracks/
391
+ h[:other_tags_id] = 9 if sql =~ /other_tags\.id AS other_tags_id/
392
+ h[:artists_0_id] = 10 if sql =~ /artists_0\.id AS artists_0_id/
463
393
  end
464
- })
394
+ h
395
+ end
465
396
 
466
- Album.dataset.extend(Module.new {
467
- def fetch_rows(sql)
468
- @db << sql
469
- h = {:id => 3}
470
- h.merge!(:x_foreign_key_x=>1) if sql =~ /albums_artists.artist_id IN \(1\)/
471
- yield h
397
+ Tag.dataset._fetch = proc do |sql|
398
+ h = {:id => 2}
399
+ if sql =~ /albums_artists.artist_id IN \(([18])\)/
400
+ h[:x_foreign_key_x] = $1.to_i
401
+ elsif sql =~ /\(\(albums_artists.b1, albums_artists.b2\) IN \(\(1, 8\)\)\)/
402
+ h.merge!(:x_foreign_key_0_x=>1, :x_foreign_key_1_x=>8)
472
403
  end
473
- })
404
+ h[:tag_id] = h.delete(:id) if sql =~ /albums_artists.artist_id IN \(8\)/
405
+ h
406
+ end
474
407
 
475
- Track.dataset.extend(Module.new {
476
- def fetch_rows(sql)
477
- @db << sql
478
- h = {:id => 4}
479
- h.merge!(:x_foreign_key_x=>2) if sql =~ /albums_tags.tag_id IN \(2\)/
480
- yield h
481
- end
482
- })
408
+ Album.dataset._fetch = proc do |sql|
409
+ h = {:id => 3}
410
+ h[:x_foreign_key_x] = 1 if sql =~ /albums_artists.artist_id IN \(1\)/
411
+ h
412
+ end
413
+
414
+ Track.dataset._fetch = proc do |sql|
415
+ h = {:id => 4}
416
+ h[:x_foreign_key_x] = 2 if sql =~ /albums_tags.tag_id IN \(2\)/
417
+ h
418
+ end
483
419
 
484
420
  @c1 = Artist
485
421
  MODEL_DB.reset
@@ -493,33 +429,35 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
493
429
  a.should == [@c1.load(:id=>1)]
494
430
  MODEL_DB.sqls.should == ['SELECT * FROM artists', 'SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1)))']
495
431
  a.first.tags.should == [Tag.load(:id=>2)]
496
- MODEL_DB.sqls.length.should == 2
432
+ MODEL_DB.sqls.length.should == 0
497
433
  end
498
434
 
499
435
  it "should eagerly load multiple associations in a single call" do
500
436
  a = @c1.eager(:tags, :albums).all
501
437
  a.should == [@c1.load(:id=>1)]
502
- MODEL_DB.sqls.length.should == 3
503
- MODEL_DB.sqls[0].should == 'SELECT * FROM artists'
504
- MODEL_DB.sqls[1..-1].should(include('SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1)))'))
505
- MODEL_DB.sqls[1..-1].should(include('SELECT albums.*, albums_artists.artist_id AS x_foreign_key_x FROM albums INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1)))'))
438
+ sqls = MODEL_DB.sqls
439
+ sqls.length.should == 3
440
+ sqls[0].should == 'SELECT * FROM artists'
441
+ sqls[1..-1].should(include('SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1)))'))
442
+ sqls[1..-1].should(include('SELECT albums.*, albums_artists.artist_id AS x_foreign_key_x FROM albums INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1)))'))
506
443
  a = a.first
507
444
  a.tags.should == [Tag.load(:id=>2)]
508
445
  a.albums.should == [Album.load(:id=>3)]
509
- MODEL_DB.sqls.length.should == 3
446
+ MODEL_DB.sqls.length.should == 0
510
447
  end
511
448
 
512
449
  it "should eagerly load multiple associations in separate" do
513
450
  a = @c1.eager(:tags).eager(:albums).all
514
451
  a.should == [@c1.load(:id=>1)]
515
- MODEL_DB.sqls.length.should == 3
516
- MODEL_DB.sqls[0].should == 'SELECT * FROM artists'
517
- MODEL_DB.sqls[1..-1].should(include('SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1)))'))
518
- MODEL_DB.sqls[1..-1].should(include('SELECT albums.*, albums_artists.artist_id AS x_foreign_key_x FROM albums INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1)))'))
452
+ sqls = MODEL_DB.sqls
453
+ sqls.length.should == 3
454
+ sqls[0].should == 'SELECT * FROM artists'
455
+ sqls[1..-1].should(include('SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1)))'))
456
+ sqls[1..-1].should(include('SELECT albums.*, albums_artists.artist_id AS x_foreign_key_x FROM albums INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1)))'))
519
457
  a = a.first
520
458
  a.tags.should == [Tag.load(:id=>2)]
521
459
  a.albums.should == [Album.load(:id=>3)]
522
- MODEL_DB.sqls.length.should == 3
460
+ MODEL_DB.sqls.length.should == 0
523
461
  end
524
462
 
525
463
  it "should allow cascading of eager loading for associations of associated models" do
@@ -531,7 +469,7 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
531
469
  a = a.first
532
470
  a.tags.should == [Tag.load(:id=>2)]
533
471
  a.tags.first.tracks.should == [Track.load(:id=>4)]
534
- MODEL_DB.sqls.length.should == 3
472
+ MODEL_DB.sqls.length.should == 0
535
473
  end
536
474
 
537
475
  it "should cascade eagerly loading when the :eager association option is used" do
@@ -544,7 +482,7 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
544
482
  a = a.first
545
483
  a.tags.should == [Tag.load(:id=>2)]
546
484
  a.tags.first.tracks.should == [Track.load(:id=>4)]
547
- MODEL_DB.sqls.length.should == 3
485
+ MODEL_DB.sqls.length.should == 0
548
486
  end
549
487
 
550
488
  it "should respect :eager when lazily loading an association" do
@@ -554,7 +492,7 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
554
492
  MODEL_DB.sqls.should == ['SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1))',
555
493
  'SELECT tracks.*, albums_tags.tag_id AS x_foreign_key_x FROM tracks INNER JOIN albums ON (albums.id = tracks.album_id) INNER JOIN albums_tags ON ((albums_tags.album_id = albums.id) AND (albums_tags.tag_id IN (2)))']
556
494
  a.tags.first.tracks.should == [Track.load(:id=>4)]
557
- MODEL_DB.sqls.length.should == 2
495
+ MODEL_DB.sqls.length.should == 0
558
496
  end
559
497
 
560
498
  it "should cascade eagerly loading when the :eager_graph association option is used" do
@@ -563,14 +501,11 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
563
501
  end
564
502
 
565
503
  it "should respect :eager_graph when lazily loading an association" do
504
+ Tag.dataset._fetch = {:id=>2, :tracks_id=>4}
566
505
  Tag.dataset.extend(Module.new {
567
506
  def columns
568
507
  [:id]
569
508
  end
570
- def fetch_rows(sql)
571
- @db << sql
572
- yield({:id=>2, :tracks_id=>4})
573
- end
574
509
  })
575
510
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :eager_graph=>:tracks
576
511
  a = @c1.load(:id=>1)
@@ -578,7 +513,7 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
578
513
  MODEL_DB.sqls.should == [ 'SELECT tags.id, tracks.id AS tracks_id FROM (SELECT tags.* FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id = 1))) AS tags LEFT OUTER JOIN albums_tags AS albums_tags_0 ON (albums_tags_0.tag_id = tags.id) LEFT OUTER JOIN albums ON (albums.id = albums_tags_0.album_id) LEFT OUTER JOIN tracks ON (tracks.album_id = albums.id)']
579
514
  a.tags.should == [Tag.load(:id=>2)]
580
515
  a.tags.first.tracks.should == [Track.load(:id=>4)]
581
- MODEL_DB.sqls.length.should == 1
516
+ MODEL_DB.sqls.length.should == 0
582
517
  end
583
518
 
584
519
  it "should respect :conditions when eagerly loading" do
@@ -588,7 +523,7 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
588
523
  MODEL_DB.sqls.should == ['SELECT * FROM artists',
589
524
  'SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1))) WHERE (a = 32)']
590
525
  a.first.tags.should == [Tag.load(:id=>2)]
591
- MODEL_DB.sqls.length.should == 2
526
+ MODEL_DB.sqls.length.should == 0
592
527
  end
593
528
 
594
529
  it "should respect :order when eagerly loading" do
@@ -598,7 +533,7 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
598
533
  MODEL_DB.sqls.should == ['SELECT * FROM artists',
599
534
  'SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1))) ORDER BY blah']
600
535
  a.first.tags.should == [Tag.load(:id=>2)]
601
- MODEL_DB.sqls.length.should == 2
536
+ MODEL_DB.sqls.length.should == 0
602
537
  end
603
538
 
604
539
  it "should use the association's block when eager loading by default" do
@@ -608,7 +543,7 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
608
543
  MODEL_DB.sqls.should == ['SELECT * FROM artists',
609
544
  'SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1))) WHERE a']
610
545
  a.first.tags.should == [Tag.load(:id=>2)]
611
- MODEL_DB.sqls.length.should == 2
546
+ MODEL_DB.sqls.length.should == 0
612
547
  end
613
548
 
614
549
  it "should use the :eager_block option when eager loading if given" do
@@ -618,121 +553,87 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
618
553
  MODEL_DB.sqls.should == ['SELECT * FROM artists',
619
554
  'SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1))) WHERE b']
620
555
  a.first.tags.should == [Tag.load(:id=>2)]
621
- MODEL_DB.sqls.length.should == 2
556
+ MODEL_DB.sqls.length.should == 0
622
557
  end
623
558
 
624
559
  it "should respect the :limit option on a many_through_many association" do
625
560
  @c1.many_through_many :first_two_tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :class=>Tag, :limit=>2
626
- Tag.dataset.extend(Module.new {
627
- def fetch_rows(sql)
628
- MODEL_DB.sqls << sql
629
- yield({:x_foreign_key_x=>1, :id=>5})
630
- yield({:x_foreign_key_x=>1, :id=>6})
631
- yield({:x_foreign_key_x=>1, :id=>7})
632
- end
633
- })
561
+ Tag.dataset._fetch = [{:x_foreign_key_x=>1, :id=>5},{:x_foreign_key_x=>1, :id=>6}, {:x_foreign_key_x=>1, :id=>7}]
634
562
  a = @c1.eager(:first_two_tags).all
635
563
  a.should == [@c1.load(:id=>1)]
636
564
  MODEL_DB.sqls.should == ['SELECT * FROM artists',
637
565
  'SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1)))']
638
566
  a.first.first_two_tags.should == [Tag.load(:id=>5), Tag.load(:id=>6)]
639
- MODEL_DB.sqls.length.should == 2
567
+ MODEL_DB.sqls.length.should == 0
640
568
 
641
- MODEL_DB.reset
642
569
  @c1.many_through_many :first_two_tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :class=>Tag, :limit=>[2,1]
643
570
  a = @c1.eager(:first_two_tags).all
644
571
  a.should == [@c1.load(:id=>1)]
645
572
  MODEL_DB.sqls.should == ['SELECT * FROM artists',
646
573
  'SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1)))']
647
574
  a.first.first_two_tags.should == [Tag.load(:id=>6), Tag.load(:id=>7)]
648
- MODEL_DB.sqls.length.should == 2
575
+ MODEL_DB.sqls.length.should == 0
649
576
  end
650
577
 
651
578
  it "should respect the :limit option on a many_through_many association using a :window_function strategy" do
652
579
  Tag.dataset.meta_def(:supports_window_functions?){true}
653
580
  @c1.many_through_many :first_two_tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :class=>Tag, :limit=>2, :eager_limit_strategy=>true, :order=>:name
654
- Tag.dataset.extend(Module.new {
655
- def fetch_rows(sql)
656
- MODEL_DB.sqls << sql
657
- yield({:x_foreign_key_x=>1, :id=>5})
658
- yield({:x_foreign_key_x=>1, :id=>6})
659
- end
660
- })
581
+ Tag.dataset._fetch = [{:x_foreign_key_x=>1, :id=>5},{:x_foreign_key_x=>1, :id=>6}]
661
582
  a = @c1.eager(:first_two_tags).all
662
583
  a.should == [@c1.load(:id=>1)]
663
584
  MODEL_DB.sqls.should == ['SELECT * FROM artists',
664
585
  'SELECT * FROM (SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x, row_number() OVER (PARTITION BY albums_artists.artist_id ORDER BY name) AS x_sequel_row_number_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1)))) AS t1 WHERE (x_sequel_row_number_x <= 2)']
665
586
  a.first.first_two_tags.should == [Tag.load(:id=>5), Tag.load(:id=>6)]
666
- MODEL_DB.sqls.length.should == 2
587
+ MODEL_DB.sqls.length.should == 0
667
588
 
668
- MODEL_DB.reset
669
589
  @c1.many_through_many :first_two_tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :class=>Tag, :limit=>[2,1], :eager_limit_strategy=>true, :order=>:name
670
590
  a = @c1.eager(:first_two_tags).all
671
591
  a.should == [@c1.load(:id=>1)]
672
592
  MODEL_DB.sqls.should == ['SELECT * FROM artists',
673
593
  'SELECT * FROM (SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x, row_number() OVER (PARTITION BY albums_artists.artist_id ORDER BY name) AS x_sequel_row_number_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1)))) AS t1 WHERE ((x_sequel_row_number_x >= 2) AND (x_sequel_row_number_x < 4))']
674
594
  a.first.first_two_tags.should == [Tag.load(:id=>5), Tag.load(:id=>6)]
675
- MODEL_DB.sqls.length.should == 2
595
+ MODEL_DB.sqls.length.should == 0
676
596
  end
677
597
 
678
598
  it "should respect the :limit option on a many_through_many association with composite primary keys on the main table using a :window_function strategy" do
679
599
  Tag.dataset.meta_def(:supports_window_functions?){true}
680
600
  @c1.set_primary_key([:id1, :id2])
681
601
  @c1.many_through_many :first_two_tags, [[:albums_artists, [:artist_id1, :artist_id2], :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :class=>Tag, :limit=>2, :eager_limit_strategy=>true, :order=>:name
682
- @c1.dataset.extend(Module.new {
683
- def fetch_rows(sql)
684
- MODEL_DB.sqls << sql
685
- yield({:id1=>1, :id2=>2})
686
- end
687
- })
688
- Tag.dataset.extend(Module.new {
689
- def fetch_rows(sql)
690
- MODEL_DB.sqls << sql
691
- yield({:x_foreign_key_0_x=>1, :x_foreign_key_1_x=>2, :id=>5})
692
- yield({:x_foreign_key_0_x=>1, :x_foreign_key_1_x=>2, :id=>6})
693
- end
694
- })
602
+ @c1.dataset._fetch = [{:id1=>1, :id2=>2}]
603
+ Tag.dataset._fetch = [{:x_foreign_key_0_x=>1, :x_foreign_key_1_x=>2, :id=>5}, {:x_foreign_key_0_x=>1, :x_foreign_key_1_x=>2, :id=>6}]
695
604
  a = @c1.eager(:first_two_tags).all
696
605
  a.should == [@c1.load(:id1=>1, :id2=>2)]
697
606
  MODEL_DB.sqls.should == ['SELECT * FROM artists',
698
607
  'SELECT * FROM (SELECT tags.*, albums_artists.artist_id1 AS x_foreign_key_0_x, albums_artists.artist_id2 AS x_foreign_key_1_x, row_number() OVER (PARTITION BY albums_artists.artist_id1, albums_artists.artist_id2 ORDER BY name) AS x_sequel_row_number_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND ((albums_artists.artist_id1, albums_artists.artist_id2) IN ((1, 2))))) AS t1 WHERE (x_sequel_row_number_x <= 2)']
699
608
  a.first.first_two_tags.should == [Tag.load(:id=>5), Tag.load(:id=>6)]
700
- MODEL_DB.sqls.length.should == 2
609
+ MODEL_DB.sqls.length.should == 0
701
610
 
702
- MODEL_DB.reset
703
611
  @c1.many_through_many :first_two_tags, [[:albums_artists, [:artist_id1, :artist_id2], :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :class=>Tag, :limit=>[2,1], :eager_limit_strategy=>true, :order=>:name
704
612
  a = @c1.eager(:first_two_tags).all
705
613
  a.should == [@c1.load(:id1=>1, :id2=>2)]
706
614
  MODEL_DB.sqls.should == ['SELECT * FROM artists',
707
615
  'SELECT * FROM (SELECT tags.*, albums_artists.artist_id1 AS x_foreign_key_0_x, albums_artists.artist_id2 AS x_foreign_key_1_x, row_number() OVER (PARTITION BY albums_artists.artist_id1, albums_artists.artist_id2 ORDER BY name) AS x_sequel_row_number_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND ((albums_artists.artist_id1, albums_artists.artist_id2) IN ((1, 2))))) AS t1 WHERE ((x_sequel_row_number_x >= 2) AND (x_sequel_row_number_x < 4))']
708
616
  a.first.first_two_tags.should == [Tag.load(:id=>5), Tag.load(:id=>6)]
709
- MODEL_DB.sqls.length.should == 2
617
+ MODEL_DB.sqls.length.should == 0
710
618
  end
711
619
 
712
620
  it "should respect the :limit option on a many_through_many association using a :correlated_subquery strategy" do
713
621
  @c1.many_through_many :first_two_tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :class=>Tag, :limit=>2, :eager_limit_strategy=>:correlated_subquery, :order=>:name
714
- Tag.dataset.extend(Module.new {
715
- def fetch_rows(sql)
716
- MODEL_DB.sqls << sql
717
- yield({:x_foreign_key_x=>1, :id=>5})
718
- yield({:x_foreign_key_x=>1, :id=>6})
719
- end
720
- })
622
+ Tag.dataset._fetch = [{:x_foreign_key_x=>1, :id=>5},{:x_foreign_key_x=>1, :id=>6}]
721
623
  a = @c1.eager(:first_two_tags).all
722
624
  a.should == [@c1.load(:id=>1)]
723
625
  MODEL_DB.sqls.should == ['SELECT * FROM artists',
724
626
  'SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1))) WHERE (tags.id IN (SELECT t1.id FROM tags AS t1 INNER JOIN albums_tags ON (albums_tags.tag_id = t1.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists AS t2 ON ((t2.album_id = albums.id) AND (t2.artist_id = albums_artists.artist_id)) ORDER BY name LIMIT 2)) ORDER BY name']
725
627
  a.first.first_two_tags.should == [Tag.load(:id=>5), Tag.load(:id=>6)]
726
- MODEL_DB.sqls.length.should == 2
628
+ MODEL_DB.sqls.length.should == 0
727
629
 
728
- MODEL_DB.reset
729
630
  @c1.many_through_many :first_two_tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :class=>Tag, :limit=>[2,1], :eager_limit_strategy=>:correlated_subquery, :order=>:name
730
631
  a = @c1.eager(:first_two_tags).all
731
632
  a.should == [@c1.load(:id=>1)]
732
633
  MODEL_DB.sqls.should == ['SELECT * FROM artists',
733
634
  'SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1))) WHERE (tags.id IN (SELECT t1.id FROM tags AS t1 INNER JOIN albums_tags ON (albums_tags.tag_id = t1.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists AS t2 ON ((t2.album_id = albums.id) AND (t2.artist_id = albums_artists.artist_id)) ORDER BY name LIMIT 2 OFFSET 1)) ORDER BY name']
734
635
  a.first.first_two_tags.should == [Tag.load(:id=>5), Tag.load(:id=>6)]
735
- MODEL_DB.sqls.length.should == 2
636
+ MODEL_DB.sqls.length.should == 0
736
637
  end
737
638
 
738
639
  it "should raise an error when attempting to eagerly load an association with the :allow_eager option set to false" do
@@ -748,47 +649,33 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
748
649
  MODEL_DB.sqls.should == ['SELECT * FROM artists',
749
650
  'SELECT tags.name, albums_artists.artist_id AS x_foreign_key_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1)))']
750
651
  a.first.tags.should == [Tag.load(:id=>2)]
751
- MODEL_DB.sqls.length.should == 2
652
+ MODEL_DB.sqls.length.should == 0
752
653
  end
753
654
 
754
655
  it "should respect many_through_many association's :left_primary_key and :right_primary_key options" do
755
656
  @c1.send(:define_method, :yyy){values[:yyy]}
756
- @c1.dataset.extend(Module.new {
757
- def columns
758
- [:id, :yyy]
759
- end
760
- def fetch_rows(sql)
761
- @db << sql
762
- yield({:id=>1, :yyy=>8})
763
- end
764
- })
657
+ @c1.dataset._fetch = {:id=>1, :yyy=>8}
658
+ @c1.dataset.meta_def(:columns){[:id, :yyy]}
765
659
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :left_primary_key=>:yyy, :right_primary_key=>:tag_id
766
660
  a = @c1.eager(:tags).all
767
661
  a.should == [@c1.load(:id=>1, :yyy=>8)]
768
662
  MODEL_DB.sqls.should == ['SELECT * FROM artists',
769
663
  'SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.tag_id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (8)))']
770
664
  a.first.tags.should == [Tag.load(:tag_id=>2)]
771
- MODEL_DB.sqls.length.should == 2
665
+ MODEL_DB.sqls.length.should == 0
772
666
  end
773
667
 
774
668
  it "should handle composite keys" do
775
669
  @c1.send(:define_method, :yyy){values[:yyy]}
776
- @c1.dataset.extend(Module.new {
777
- def columns
778
- [:id, :yyy]
779
- end
780
- def fetch_rows(sql)
781
- @db << sql
782
- yield({:id=>1, :yyy=>8})
783
- end
784
- })
670
+ @c1.dataset._fetch = {:id=>1, :yyy=>8}
671
+ @c1.dataset.meta_def(:columns){[:id, :yyy]}
785
672
  @c1.many_through_many :tags, [[:albums_artists, [:b1, :b2], [:c1, :c2]], [:albums, [:d1, :d2], [:e1, :e2]], [:albums_tags, [:f1, :f2], [:g1, :g2]]], :right_primary_key=>[:h1, :h2], :left_primary_key=>[:id, :yyy]
786
673
  a = @c1.eager(:tags).all
787
674
  a.should == [@c1.load(:id=>1, :yyy=>8)]
788
675
  MODEL_DB.sqls.should == ['SELECT * FROM artists',
789
676
  'SELECT tags.*, albums_artists.b1 AS x_foreign_key_0_x, albums_artists.b2 AS x_foreign_key_1_x FROM tags INNER JOIN albums_tags ON ((albums_tags.g1 = tags.h1) AND (albums_tags.g2 = tags.h2)) INNER JOIN albums ON ((albums.e1 = albums_tags.f1) AND (albums.e2 = albums_tags.f2)) INNER JOIN albums_artists ON ((albums_artists.c1 = albums.d1) AND (albums_artists.c2 = albums.d2) AND ((albums_artists.b1, albums_artists.b2) IN ((1, 8))))']
790
677
  a.first.tags.should == [Tag.load(:id=>2)]
791
- MODEL_DB.sqls.length.should == 2
678
+ MODEL_DB.sqls.length.should == 0
792
679
  end
793
680
 
794
681
  it "should respect :after_load callbacks on associations when eager loading" do
@@ -798,7 +685,7 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
798
685
  MODEL_DB.sqls.should == ['SELECT * FROM artists',
799
686
  'SELECT tags.*, albums_artists.artist_id AS x_foreign_key_x FROM tags INNER JOIN albums_tags ON (albums_tags.tag_id = tags.id) INNER JOIN albums ON (albums.id = albums_tags.album_id) INNER JOIN albums_artists ON ((albums_artists.album_id = albums.id) AND (albums_artists.artist_id IN (1)))']
800
687
  a.first.tags.should == [Tag.load(:id=>6)]
801
- MODEL_DB.sqls.length.should == 2
688
+ MODEL_DB.sqls.length.should == 0
802
689
  end
803
690
 
804
691
  it "should raise an error if called without a symbol or hash" do
@@ -810,7 +697,7 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
810
697
  a.should == [@c1.load(:id=>1)]
811
698
  MODEL_DB.sqls.should == ['SELECT artists.id, tags.id AS tags_id FROM artists LEFT OUTER JOIN albums_artists ON (albums_artists.artist_id = artists.id) LEFT OUTER JOIN albums ON (albums.id = albums_artists.album_id) LEFT OUTER JOIN albums_tags ON (albums_tags.album_id = albums.id) LEFT OUTER JOIN tags ON (tags.id = albums_tags.tag_id)']
812
699
  a.first.tags.should == [Tag.load(:id=>2)]
813
- MODEL_DB.sqls.length.should == 1
700
+ MODEL_DB.sqls.length.should == 0
814
701
  end
815
702
 
816
703
  it "should eagerly graph multiple associations in a single call" do
@@ -820,7 +707,7 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
820
707
  a = a.first
821
708
  a.tags.should == [Tag.load(:id=>2)]
822
709
  a.albums.should == [Album.load(:id=>3)]
823
- MODEL_DB.sqls.length.should == 1
710
+ MODEL_DB.sqls.length.should == 0
824
711
  end
825
712
 
826
713
  it "should eagerly graph multiple associations in separate calls" do
@@ -830,7 +717,7 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
830
717
  a = a.first
831
718
  a.tags.should == [Tag.load(:id=>2)]
832
719
  a.albums.should == [Album.load(:id=>3)]
833
- MODEL_DB.sqls.length.should == 1
720
+ MODEL_DB.sqls.length.should == 0
834
721
  end
835
722
 
836
723
  it "should allow cascading of eager graphing for associations of associated models" do
@@ -840,24 +727,18 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
840
727
  a = a.first
841
728
  a.tags.should == [Tag.load(:id=>2)]
842
729
  a.tags.first.tracks.should == [Track.load(:id=>4)]
843
- MODEL_DB.sqls.length.should == 1
730
+ MODEL_DB.sqls.length.should == 0
844
731
  end
845
732
 
846
733
  it "eager graphing should eliminate duplicates caused by cartesian products" do
847
734
  ds = @c1.eager_graph(:tags)
848
- def ds.fetch_rows(sql, &block)
849
- @db << sql
850
- # Assume artist has 2 albums each with 2 tags
851
- yield({:id=>1, :tags_id=>2})
852
- yield({:id=>1, :tags_id=>3})
853
- yield({:id=>1, :tags_id=>2})
854
- yield({:id=>1, :tags_id=>3})
855
- end
735
+ # Assume artist has 2 albums each with 2 tags
736
+ ds._fetch = [{:id=>1, :tags_id=>2}, {:id=>1, :tags_id=>3}, {:id=>1, :tags_id=>2}, {:id=>1, :tags_id=>3}]
856
737
  a = ds.all
857
738
  a.should == [@c1.load(:id=>1)]
858
739
  MODEL_DB.sqls.should == ['SELECT artists.id, tags.id AS tags_id FROM artists LEFT OUTER JOIN albums_artists ON (albums_artists.artist_id = artists.id) LEFT OUTER JOIN albums ON (albums.id = albums_artists.album_id) LEFT OUTER JOIN albums_tags ON (albums_tags.album_id = albums.id) LEFT OUTER JOIN tags ON (tags.id = albums_tags.tag_id)']
859
740
  a.first.tags.should == [Tag.load(:id=>2), Tag.load(:id=>3)]
860
- MODEL_DB.sqls.length.should == 1
741
+ MODEL_DB.sqls.length.should == 0
861
742
  end
862
743
 
863
744
  it "should eager graph multiple associations from the same table" do
@@ -867,7 +748,7 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
867
748
  a = a.first
868
749
  a.tags.should == [Tag.load(:id=>2)]
869
750
  a.other_tags.should == [Tag.load(:id=>9)]
870
- MODEL_DB.sqls.length.should == 1
751
+ MODEL_DB.sqls.length.should == 0
871
752
  end
872
753
 
873
754
  it "should eager graph a self_referential association" do
@@ -877,7 +758,7 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
877
758
  a = a.first
878
759
  a.tags.should == [Tag.load(:id=>2)]
879
760
  a.artists.should == [@c1.load(:id=>10)]
880
- MODEL_DB.sqls.length.should == 1
761
+ MODEL_DB.sqls.length.should == 0
881
762
  end
882
763
 
883
764
  it "eager graphing should give you a plain hash when called without .all" do
@@ -892,31 +773,22 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
892
773
  a = a.first
893
774
  a.tags.should == [Tag.load(:id=>2)]
894
775
  a.albums.should == [Album.load(:id=>3)]
895
- MODEL_DB.sqls.length.should == 2
776
+ MODEL_DB.sqls.length.should == 0
896
777
  end
897
778
 
898
779
  it "should handle no associated records when eagerly graphing a single many_through_many association" do
899
780
  ds = @c1.eager_graph(:tags)
900
- def ds.fetch_rows(sql)
901
- @db << sql
902
- yield({:id=>1, :tags_id=>nil})
903
- end
781
+ ds._fetch = {:id=>1, :tags_id=>nil}
904
782
  a = ds.all
905
783
  a.should == [@c1.load(:id=>1)]
906
784
  MODEL_DB.sqls.should == ['SELECT artists.id, tags.id AS tags_id FROM artists LEFT OUTER JOIN albums_artists ON (albums_artists.artist_id = artists.id) LEFT OUTER JOIN albums ON (albums.id = albums_artists.album_id) LEFT OUTER JOIN albums_tags ON (albums_tags.album_id = albums.id) LEFT OUTER JOIN tags ON (tags.id = albums_tags.tag_id)']
907
785
  a.first.tags.should == []
908
- MODEL_DB.sqls.length.should == 1
786
+ MODEL_DB.sqls.length.should == 0
909
787
  end
910
788
 
911
789
  it "should handle no associated records when eagerly graphing multiple many_through_many associations" do
912
790
  ds = @c1.eager_graph(:tags, :albums)
913
- def ds.fetch_rows(sql)
914
- @db << sql
915
- yield({:id=>1, :tags_id=>nil, :albums_0_id=>3})
916
- yield({:id=>1, :tags_id=>2, :albums_0_id=>nil})
917
- yield({:id=>1, :tags_id=>5, :albums_0_id=>6})
918
- yield({:id=>7, :tags_id=>nil, :albums_0_id=>nil})
919
- end
791
+ ds._fetch = [{:id=>1, :tags_id=>nil, :albums_0_id=>3}, {:id=>1, :tags_id=>2, :albums_0_id=>nil}, {:id=>1, :tags_id=>5, :albums_0_id=>6}, {:id=>7, :tags_id=>nil, :albums_0_id=>nil}]
920
792
  a = ds.all
921
793
  a.should == [@c1.load(:id=>1), @c1.load(:id=>7)]
922
794
  MODEL_DB.sqls.should == ['SELECT artists.id, tags.id AS tags_id, albums_0.id AS albums_0_id FROM artists LEFT OUTER JOIN albums_artists ON (albums_artists.artist_id = artists.id) LEFT OUTER JOIN albums ON (albums.id = albums_artists.album_id) LEFT OUTER JOIN albums_tags ON (albums_tags.album_id = albums.id) LEFT OUTER JOIN tags ON (tags.id = albums_tags.tag_id) LEFT OUTER JOIN albums_artists AS albums_artists_0 ON (albums_artists_0.artist_id = artists.id) LEFT OUTER JOIN albums AS albums_0 ON (albums_0.id = albums_artists_0.album_id)']
@@ -924,17 +796,12 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
924
796
  a.first.albums.should == [Album.load(:id=>3), Album.load(:id=>6)]
925
797
  a.last.tags.should == []
926
798
  a.last.albums.should == []
927
- MODEL_DB.sqls.length.should == 1
799
+ MODEL_DB.sqls.length.should == 0
928
800
  end
929
801
 
930
802
  it "should handle missing associated records when cascading eager graphing for associations of associated models" do
931
803
  ds = @c1.eager_graph(:tags=>:tracks)
932
- def ds.fetch_rows(sql)
933
- @db << sql
934
- yield({:id=>1, :tags_id=>2, :tracks_id=>4})
935
- yield({:id=>1, :tags_id=>3, :tracks_id=>nil})
936
- yield({:id=>2, :tags_id=>nil, :tracks_id=>nil})
937
- end
804
+ ds._fetch = [{:id=>1, :tags_id=>2, :tracks_id=>4}, {:id=>1, :tags_id=>3, :tracks_id=>nil}, {:id=>2, :tags_id=>nil, :tracks_id=>nil}]
938
805
  a = ds.all
939
806
  a.should == [@c1.load(:id=>1), @c1.load(:id=>2)]
940
807
  MODEL_DB.sqls.should == ['SELECT artists.id, tags.id AS tags_id, tracks.id AS tracks_id FROM artists LEFT OUTER JOIN albums_artists ON (albums_artists.artist_id = artists.id) LEFT OUTER JOIN albums ON (albums.id = albums_artists.album_id) LEFT OUTER JOIN albums_tags ON (albums_tags.album_id = albums.id) LEFT OUTER JOIN tags ON (tags.id = albums_tags.tag_id) LEFT OUTER JOIN albums_tags AS albums_tags_0 ON (albums_tags_0.tag_id = tags.id) LEFT OUTER JOIN albums AS albums_0 ON (albums_0.id = albums_tags_0.album_id) LEFT OUTER JOIN tracks ON (tracks.album_id = albums_0.id)']
@@ -943,7 +810,7 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
943
810
  a.tags.should == [Tag.load(:id=>2), Tag.load(:id=>3)]
944
811
  a.tags.first.tracks.should == [Track.load(:id=>4)]
945
812
  a.tags.last.tracks.should == []
946
- MODEL_DB.sqls.length.should == 1
813
+ MODEL_DB.sqls.length.should == 0
947
814
  end
948
815
 
949
816
  it "eager graphing should respect :left_primary_key and :right_primary_key options" do
@@ -951,15 +818,12 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
951
818
  @c1.dataset.meta_def(:columns){[:id, :yyy]}
952
819
  Tag.dataset.meta_def(:columns){[:id, :tag_id]}
953
820
  ds = @c1.eager_graph(:tags)
954
- def ds.fetch_rows(sql)
955
- @db << sql
956
- yield({:id=>1, :yyy=>8, :tags_id=>2, :tag_id=>4})
957
- end
821
+ ds._fetch = {:id=>1, :yyy=>8, :tags_id=>2, :tag_id=>4}
958
822
  a = ds.all
959
823
  a.should == [@c1.load(:id=>1, :yyy=>8)]
960
824
  MODEL_DB.sqls.should == ['SELECT artists.id, artists.yyy, tags.id AS tags_id, tags.tag_id FROM artists LEFT OUTER JOIN albums_artists ON (albums_artists.artist_id = artists.yyy) LEFT OUTER JOIN albums ON (albums.id = albums_artists.album_id) LEFT OUTER JOIN albums_tags ON (albums_tags.album_id = albums.id) LEFT OUTER JOIN tags ON (tags.tag_id = albums_tags.tag_id)']
961
825
  a.first.tags.should == [Tag.load(:id=>2, :tag_id=>4)]
962
- MODEL_DB.sqls.length.should == 1
826
+ MODEL_DB.sqls.length.should == 0
963
827
  end
964
828
 
965
829
  it "eager graphing should respect composite keys" do
@@ -967,29 +831,23 @@ describe "Sequel::Plugins::ManyThroughMany eager loading methods" do
967
831
  @c1.dataset.meta_def(:columns){[:id, :yyy]}
968
832
  Tag.dataset.meta_def(:columns){[:id, :tag_id]}
969
833
  ds = @c1.eager_graph(:tags)
970
- def ds.fetch_rows(sql)
971
- @db << sql
972
- yield({:id=>1, :yyy=>8, :tags_id=>2, :tag_id=>4})
973
- end
834
+ ds._fetch = {:id=>1, :yyy=>8, :tags_id=>2, :tag_id=>4}
974
835
  a = ds.all
975
836
  a.should == [@c1.load(:id=>1, :yyy=>8)]
976
837
  MODEL_DB.sqls.should == ['SELECT artists.id, artists.yyy, tags.id AS tags_id, tags.tag_id FROM artists LEFT OUTER JOIN albums_artists ON ((albums_artists.b1 = artists.id) AND (albums_artists.b2 = artists.yyy)) LEFT OUTER JOIN albums ON ((albums.d1 = albums_artists.c1) AND (albums.d2 = albums_artists.c2)) LEFT OUTER JOIN albums_tags ON ((albums_tags.f1 = albums.e1) AND (albums_tags.f2 = albums.e2)) LEFT OUTER JOIN tags ON ((tags.id = albums_tags.g1) AND (tags.tag_id = albums_tags.g2))']
977
838
  a.first.tags.should == [Tag.load(:id=>2, :tag_id=>4)]
978
- MODEL_DB.sqls.length.should == 1
839
+ MODEL_DB.sqls.length.should == 0
979
840
  end
980
841
 
981
842
  it "should respect the association's :graph_select option" do
982
843
  @c1.many_through_many :tags, [[:albums_artists, :artist_id, :album_id], [:albums, :id, :id], [:albums_tags, :album_id, :tag_id]], :graph_select=>:b
983
844
  ds = @c1.eager_graph(:tags)
984
- def ds.fetch_rows(sql)
985
- @db << sql
986
- yield({:id=>1, :b=>2})
987
- end
845
+ ds._fetch = {:id=>1, :b=>2}
988
846
  a = ds.all
989
847
  a.should == [@c1.load(:id=>1)]
990
848
  MODEL_DB.sqls.should == ['SELECT artists.id, tags.b FROM artists LEFT OUTER JOIN albums_artists ON (albums_artists.artist_id = artists.id) LEFT OUTER JOIN albums ON (albums.id = albums_artists.album_id) LEFT OUTER JOIN albums_tags ON (albums_tags.album_id = albums.id) LEFT OUTER JOIN tags ON (tags.id = albums_tags.tag_id)']
991
849
  a.first.tags.should == [Tag.load(:b=>2)]
992
- MODEL_DB.sqls.length.should == 1
850
+ MODEL_DB.sqls.length.should == 0
993
851
  end
994
852
 
995
853
  it "should respect the association's :graph_join_type option" do