viking-sequel 3.10.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (237) hide show
  1. data/CHANGELOG +3134 -0
  2. data/COPYING +19 -0
  3. data/README.rdoc +723 -0
  4. data/Rakefile +193 -0
  5. data/bin/sequel +196 -0
  6. data/doc/advanced_associations.rdoc +644 -0
  7. data/doc/cheat_sheet.rdoc +218 -0
  8. data/doc/dataset_basics.rdoc +106 -0
  9. data/doc/dataset_filtering.rdoc +158 -0
  10. data/doc/opening_databases.rdoc +296 -0
  11. data/doc/prepared_statements.rdoc +104 -0
  12. data/doc/reflection.rdoc +84 -0
  13. data/doc/release_notes/1.0.txt +38 -0
  14. data/doc/release_notes/1.1.txt +143 -0
  15. data/doc/release_notes/1.3.txt +101 -0
  16. data/doc/release_notes/1.4.0.txt +53 -0
  17. data/doc/release_notes/1.5.0.txt +155 -0
  18. data/doc/release_notes/2.0.0.txt +298 -0
  19. data/doc/release_notes/2.1.0.txt +271 -0
  20. data/doc/release_notes/2.10.0.txt +328 -0
  21. data/doc/release_notes/2.11.0.txt +215 -0
  22. data/doc/release_notes/2.12.0.txt +534 -0
  23. data/doc/release_notes/2.2.0.txt +253 -0
  24. data/doc/release_notes/2.3.0.txt +88 -0
  25. data/doc/release_notes/2.4.0.txt +106 -0
  26. data/doc/release_notes/2.5.0.txt +137 -0
  27. data/doc/release_notes/2.6.0.txt +157 -0
  28. data/doc/release_notes/2.7.0.txt +166 -0
  29. data/doc/release_notes/2.8.0.txt +171 -0
  30. data/doc/release_notes/2.9.0.txt +97 -0
  31. data/doc/release_notes/3.0.0.txt +221 -0
  32. data/doc/release_notes/3.1.0.txt +406 -0
  33. data/doc/release_notes/3.10.0.txt +286 -0
  34. data/doc/release_notes/3.2.0.txt +268 -0
  35. data/doc/release_notes/3.3.0.txt +192 -0
  36. data/doc/release_notes/3.4.0.txt +325 -0
  37. data/doc/release_notes/3.5.0.txt +510 -0
  38. data/doc/release_notes/3.6.0.txt +366 -0
  39. data/doc/release_notes/3.7.0.txt +179 -0
  40. data/doc/release_notes/3.8.0.txt +151 -0
  41. data/doc/release_notes/3.9.0.txt +233 -0
  42. data/doc/schema.rdoc +36 -0
  43. data/doc/sharding.rdoc +113 -0
  44. data/doc/virtual_rows.rdoc +205 -0
  45. data/lib/sequel.rb +1 -0
  46. data/lib/sequel/adapters/ado.rb +90 -0
  47. data/lib/sequel/adapters/ado/mssql.rb +30 -0
  48. data/lib/sequel/adapters/amalgalite.rb +176 -0
  49. data/lib/sequel/adapters/db2.rb +139 -0
  50. data/lib/sequel/adapters/dbi.rb +113 -0
  51. data/lib/sequel/adapters/do.rb +188 -0
  52. data/lib/sequel/adapters/do/mysql.rb +49 -0
  53. data/lib/sequel/adapters/do/postgres.rb +91 -0
  54. data/lib/sequel/adapters/do/sqlite.rb +40 -0
  55. data/lib/sequel/adapters/firebird.rb +283 -0
  56. data/lib/sequel/adapters/informix.rb +77 -0
  57. data/lib/sequel/adapters/jdbc.rb +587 -0
  58. data/lib/sequel/adapters/jdbc/as400.rb +58 -0
  59. data/lib/sequel/adapters/jdbc/h2.rb +133 -0
  60. data/lib/sequel/adapters/jdbc/mssql.rb +57 -0
  61. data/lib/sequel/adapters/jdbc/mysql.rb +78 -0
  62. data/lib/sequel/adapters/jdbc/oracle.rb +50 -0
  63. data/lib/sequel/adapters/jdbc/postgresql.rb +108 -0
  64. data/lib/sequel/adapters/jdbc/sqlite.rb +55 -0
  65. data/lib/sequel/adapters/mysql.rb +421 -0
  66. data/lib/sequel/adapters/odbc.rb +143 -0
  67. data/lib/sequel/adapters/odbc/mssql.rb +42 -0
  68. data/lib/sequel/adapters/openbase.rb +64 -0
  69. data/lib/sequel/adapters/oracle.rb +131 -0
  70. data/lib/sequel/adapters/postgres.rb +504 -0
  71. data/lib/sequel/adapters/shared/mssql.rb +490 -0
  72. data/lib/sequel/adapters/shared/mysql.rb +498 -0
  73. data/lib/sequel/adapters/shared/oracle.rb +195 -0
  74. data/lib/sequel/adapters/shared/postgres.rb +830 -0
  75. data/lib/sequel/adapters/shared/progress.rb +44 -0
  76. data/lib/sequel/adapters/shared/sqlite.rb +389 -0
  77. data/lib/sequel/adapters/sqlite.rb +224 -0
  78. data/lib/sequel/adapters/utils/stored_procedures.rb +84 -0
  79. data/lib/sequel/connection_pool.rb +99 -0
  80. data/lib/sequel/connection_pool/sharded_single.rb +84 -0
  81. data/lib/sequel/connection_pool/sharded_threaded.rb +211 -0
  82. data/lib/sequel/connection_pool/single.rb +29 -0
  83. data/lib/sequel/connection_pool/threaded.rb +150 -0
  84. data/lib/sequel/core.rb +293 -0
  85. data/lib/sequel/core_sql.rb +241 -0
  86. data/lib/sequel/database.rb +1079 -0
  87. data/lib/sequel/database/schema_generator.rb +327 -0
  88. data/lib/sequel/database/schema_methods.rb +203 -0
  89. data/lib/sequel/database/schema_sql.rb +320 -0
  90. data/lib/sequel/dataset.rb +32 -0
  91. data/lib/sequel/dataset/actions.rb +441 -0
  92. data/lib/sequel/dataset/features.rb +86 -0
  93. data/lib/sequel/dataset/graph.rb +254 -0
  94. data/lib/sequel/dataset/misc.rb +119 -0
  95. data/lib/sequel/dataset/mutation.rb +64 -0
  96. data/lib/sequel/dataset/prepared_statements.rb +227 -0
  97. data/lib/sequel/dataset/query.rb +709 -0
  98. data/lib/sequel/dataset/sql.rb +996 -0
  99. data/lib/sequel/exceptions.rb +51 -0
  100. data/lib/sequel/extensions/blank.rb +43 -0
  101. data/lib/sequel/extensions/inflector.rb +242 -0
  102. data/lib/sequel/extensions/looser_typecasting.rb +21 -0
  103. data/lib/sequel/extensions/migration.rb +239 -0
  104. data/lib/sequel/extensions/named_timezones.rb +61 -0
  105. data/lib/sequel/extensions/pagination.rb +100 -0
  106. data/lib/sequel/extensions/pretty_table.rb +82 -0
  107. data/lib/sequel/extensions/query.rb +52 -0
  108. data/lib/sequel/extensions/schema_dumper.rb +271 -0
  109. data/lib/sequel/extensions/sql_expr.rb +122 -0
  110. data/lib/sequel/extensions/string_date_time.rb +46 -0
  111. data/lib/sequel/extensions/thread_local_timezones.rb +48 -0
  112. data/lib/sequel/metaprogramming.rb +9 -0
  113. data/lib/sequel/model.rb +120 -0
  114. data/lib/sequel/model/associations.rb +1514 -0
  115. data/lib/sequel/model/base.rb +1069 -0
  116. data/lib/sequel/model/default_inflections.rb +45 -0
  117. data/lib/sequel/model/errors.rb +39 -0
  118. data/lib/sequel/model/exceptions.rb +21 -0
  119. data/lib/sequel/model/inflections.rb +162 -0
  120. data/lib/sequel/model/plugins.rb +70 -0
  121. data/lib/sequel/plugins/active_model.rb +59 -0
  122. data/lib/sequel/plugins/association_dependencies.rb +103 -0
  123. data/lib/sequel/plugins/association_proxies.rb +41 -0
  124. data/lib/sequel/plugins/boolean_readers.rb +53 -0
  125. data/lib/sequel/plugins/caching.rb +141 -0
  126. data/lib/sequel/plugins/class_table_inheritance.rb +214 -0
  127. data/lib/sequel/plugins/composition.rb +138 -0
  128. data/lib/sequel/plugins/force_encoding.rb +72 -0
  129. data/lib/sequel/plugins/hook_class_methods.rb +126 -0
  130. data/lib/sequel/plugins/identity_map.rb +116 -0
  131. data/lib/sequel/plugins/instance_filters.rb +98 -0
  132. data/lib/sequel/plugins/instance_hooks.rb +57 -0
  133. data/lib/sequel/plugins/lazy_attributes.rb +77 -0
  134. data/lib/sequel/plugins/many_through_many.rb +208 -0
  135. data/lib/sequel/plugins/nested_attributes.rb +206 -0
  136. data/lib/sequel/plugins/optimistic_locking.rb +81 -0
  137. data/lib/sequel/plugins/rcte_tree.rb +281 -0
  138. data/lib/sequel/plugins/schema.rb +66 -0
  139. data/lib/sequel/plugins/serialization.rb +166 -0
  140. data/lib/sequel/plugins/single_table_inheritance.rb +74 -0
  141. data/lib/sequel/plugins/subclasses.rb +45 -0
  142. data/lib/sequel/plugins/tactical_eager_loading.rb +61 -0
  143. data/lib/sequel/plugins/timestamps.rb +87 -0
  144. data/lib/sequel/plugins/touch.rb +118 -0
  145. data/lib/sequel/plugins/typecast_on_load.rb +72 -0
  146. data/lib/sequel/plugins/validation_class_methods.rb +405 -0
  147. data/lib/sequel/plugins/validation_helpers.rb +223 -0
  148. data/lib/sequel/sql.rb +1020 -0
  149. data/lib/sequel/timezones.rb +161 -0
  150. data/lib/sequel/version.rb +12 -0
  151. data/lib/sequel_core.rb +1 -0
  152. data/lib/sequel_model.rb +1 -0
  153. data/spec/adapters/firebird_spec.rb +407 -0
  154. data/spec/adapters/informix_spec.rb +97 -0
  155. data/spec/adapters/mssql_spec.rb +403 -0
  156. data/spec/adapters/mysql_spec.rb +1019 -0
  157. data/spec/adapters/oracle_spec.rb +286 -0
  158. data/spec/adapters/postgres_spec.rb +969 -0
  159. data/spec/adapters/spec_helper.rb +51 -0
  160. data/spec/adapters/sqlite_spec.rb +432 -0
  161. data/spec/core/connection_pool_spec.rb +808 -0
  162. data/spec/core/core_sql_spec.rb +417 -0
  163. data/spec/core/database_spec.rb +1662 -0
  164. data/spec/core/dataset_spec.rb +3827 -0
  165. data/spec/core/expression_filters_spec.rb +595 -0
  166. data/spec/core/object_graph_spec.rb +296 -0
  167. data/spec/core/schema_generator_spec.rb +159 -0
  168. data/spec/core/schema_spec.rb +830 -0
  169. data/spec/core/spec_helper.rb +56 -0
  170. data/spec/core/version_spec.rb +7 -0
  171. data/spec/extensions/active_model_spec.rb +76 -0
  172. data/spec/extensions/association_dependencies_spec.rb +127 -0
  173. data/spec/extensions/association_proxies_spec.rb +50 -0
  174. data/spec/extensions/blank_spec.rb +67 -0
  175. data/spec/extensions/boolean_readers_spec.rb +92 -0
  176. data/spec/extensions/caching_spec.rb +250 -0
  177. data/spec/extensions/class_table_inheritance_spec.rb +252 -0
  178. data/spec/extensions/composition_spec.rb +194 -0
  179. data/spec/extensions/force_encoding_spec.rb +117 -0
  180. data/spec/extensions/hook_class_methods_spec.rb +470 -0
  181. data/spec/extensions/identity_map_spec.rb +202 -0
  182. data/spec/extensions/inflector_spec.rb +181 -0
  183. data/spec/extensions/instance_filters_spec.rb +55 -0
  184. data/spec/extensions/instance_hooks_spec.rb +133 -0
  185. data/spec/extensions/lazy_attributes_spec.rb +153 -0
  186. data/spec/extensions/looser_typecasting_spec.rb +39 -0
  187. data/spec/extensions/many_through_many_spec.rb +884 -0
  188. data/spec/extensions/migration_spec.rb +332 -0
  189. data/spec/extensions/named_timezones_spec.rb +72 -0
  190. data/spec/extensions/nested_attributes_spec.rb +396 -0
  191. data/spec/extensions/optimistic_locking_spec.rb +100 -0
  192. data/spec/extensions/pagination_spec.rb +99 -0
  193. data/spec/extensions/pretty_table_spec.rb +91 -0
  194. data/spec/extensions/query_spec.rb +85 -0
  195. data/spec/extensions/rcte_tree_spec.rb +205 -0
  196. data/spec/extensions/schema_dumper_spec.rb +357 -0
  197. data/spec/extensions/schema_spec.rb +127 -0
  198. data/spec/extensions/serialization_spec.rb +209 -0
  199. data/spec/extensions/single_table_inheritance_spec.rb +96 -0
  200. data/spec/extensions/spec_helper.rb +91 -0
  201. data/spec/extensions/sql_expr_spec.rb +89 -0
  202. data/spec/extensions/string_date_time_spec.rb +93 -0
  203. data/spec/extensions/subclasses_spec.rb +52 -0
  204. data/spec/extensions/tactical_eager_loading_spec.rb +65 -0
  205. data/spec/extensions/thread_local_timezones_spec.rb +45 -0
  206. data/spec/extensions/timestamps_spec.rb +150 -0
  207. data/spec/extensions/touch_spec.rb +155 -0
  208. data/spec/extensions/typecast_on_load_spec.rb +69 -0
  209. data/spec/extensions/validation_class_methods_spec.rb +984 -0
  210. data/spec/extensions/validation_helpers_spec.rb +438 -0
  211. data/spec/integration/associations_test.rb +281 -0
  212. data/spec/integration/database_test.rb +26 -0
  213. data/spec/integration/dataset_test.rb +963 -0
  214. data/spec/integration/eager_loader_test.rb +734 -0
  215. data/spec/integration/model_test.rb +130 -0
  216. data/spec/integration/plugin_test.rb +814 -0
  217. data/spec/integration/prepared_statement_test.rb +213 -0
  218. data/spec/integration/schema_test.rb +361 -0
  219. data/spec/integration/spec_helper.rb +73 -0
  220. data/spec/integration/timezone_test.rb +55 -0
  221. data/spec/integration/transaction_test.rb +122 -0
  222. data/spec/integration/type_test.rb +96 -0
  223. data/spec/model/association_reflection_spec.rb +175 -0
  224. data/spec/model/associations_spec.rb +2633 -0
  225. data/spec/model/base_spec.rb +418 -0
  226. data/spec/model/dataset_methods_spec.rb +78 -0
  227. data/spec/model/eager_loading_spec.rb +1391 -0
  228. data/spec/model/hooks_spec.rb +240 -0
  229. data/spec/model/inflector_spec.rb +26 -0
  230. data/spec/model/model_spec.rb +593 -0
  231. data/spec/model/plugins_spec.rb +236 -0
  232. data/spec/model/record_spec.rb +1500 -0
  233. data/spec/model/spec_helper.rb +97 -0
  234. data/spec/model/validations_spec.rb +153 -0
  235. data/spec/rcov.opts +6 -0
  236. data/spec/spec_config.rb.example +10 -0
  237. metadata +346 -0
@@ -0,0 +1,209 @@
1
+ require File.join(File.dirname(__FILE__), "spec_helper")
2
+
3
+ require 'yaml'
4
+ require 'json'
5
+
6
+ describe "Serialization plugin" do
7
+ before do
8
+ @c = Class.new(Sequel::Model(:items)) do
9
+ include(Module.new do
10
+ def before_save
11
+ end
12
+ end)
13
+ no_primary_key
14
+ columns :id, :abc, :def, :ghi
15
+ end
16
+ MODEL_DB.reset
17
+ end
18
+
19
+ it "should allow setting additional serializable attributes via plugin :serialization call" do
20
+ @c.plugin :serialization, :yaml, :abc
21
+ @c.create(:abc => 1, :def=> 2)
22
+ MODEL_DB.sqls.last.should =~ /INSERT INTO items \((abc, def|def, abc)\) VALUES \(('--- 1\n', 2|2, '--- 1\n')\)/
23
+
24
+ @c.plugin :serialization, :marshal, :def
25
+ @c.create(:abc => 1, :def=> 1)
26
+ MODEL_DB.sqls.last.should =~ /INSERT INTO items \((abc, def|def, abc)\) VALUES \(('--- 1\n', 'BAhpBg==\n'|'BAhpBg==\n', '--- 1\n')\)/
27
+
28
+ @c.plugin :serialization, :json, :ghi
29
+ @c.create(:ghi => [123])
30
+ MODEL_DB.sqls.last.should =~ /INSERT INTO items \((ghi)\) VALUES \('\[123\]'\)/
31
+ end
32
+
33
+ it "should allow serializing attributes to yaml" do
34
+ @c.plugin :serialization, :yaml, :abc
35
+ @c.create(:abc => 1)
36
+ @c.create(:abc => "hello")
37
+
38
+ MODEL_DB.sqls.should == [ \
39
+ "INSERT INTO items (abc) VALUES ('--- 1\n')", \
40
+ "INSERT INTO items (abc) VALUES ('--- hello\n')", \
41
+ ]
42
+ end
43
+
44
+ it "serialization_format should be the serialization format used" do
45
+ @c.plugin :serialization, :yaml, :abc
46
+ @c.serialization_format.should == :yaml
47
+ end
48
+
49
+ it "serialized_columns should be the columns serialized" do
50
+ @c.plugin :serialization, :yaml, :abc
51
+ @c.serialized_columns.should == [:abc]
52
+ end
53
+
54
+ it "should allow serializing attributes to marshal" do
55
+ @c.plugin :serialization, :marshal, :abc
56
+ @c.create(:abc => 1)
57
+ @c.create(:abc => "hello")
58
+ x = [Marshal.dump("hello")].pack('m')
59
+
60
+ MODEL_DB.sqls.should == [ \
61
+ "INSERT INTO items (abc) VALUES ('BAhpBg==\n')", \
62
+ "INSERT INTO items (abc) VALUES ('#{x}')", \
63
+ ]
64
+ end
65
+
66
+ it "should allow serializing attributes to json" do
67
+ @c.plugin :serialization, :json, :ghi
68
+ @c.create(:ghi => [1])
69
+ @c.create(:ghi => ["hello"])
70
+
71
+ x = JSON.generate ["hello"]
72
+ MODEL_DB.sqls.should == [ \
73
+ "INSERT INTO items (ghi) VALUES ('[1]')", \
74
+ "INSERT INTO items (ghi) VALUES ('#{x}')", \
75
+ ]
76
+ end
77
+
78
+ it "should translate values to and from yaml serialization format using accessor methods" do
79
+ @c.set_primary_key :id
80
+ @c.plugin :serialization, :yaml, :abc, :def
81
+ vals = nil
82
+
83
+ ds = @c.dataset
84
+ def ds.fetch_rows(sql, &block)
85
+ block.call(:id => 1, :abc => "--- 1\n", :def => "--- hello\n")
86
+ end
87
+
88
+ o = @c.first
89
+ o.id.should == 1
90
+ o.abc.should == 1
91
+ o.abc.should == 1
92
+ o.def.should == "hello"
93
+ o.def.should == "hello"
94
+
95
+ o.update(:abc => 23)
96
+ @c.create(:abc => [1, 2, 3])
97
+ MODEL_DB.sqls.should == ["UPDATE items SET abc = '--- 23\n' WHERE (id = 1)",
98
+ "INSERT INTO items (abc) VALUES ('#{[1, 2, 3].to_yaml}')"]
99
+ end
100
+
101
+ it "should translate values to and from marshal serialization format using accessor methods" do
102
+ @c.set_primary_key :id
103
+ @c.plugin :serialization, :marshal, :abc, :def
104
+
105
+ ds = @c.dataset
106
+ def ds.fetch_rows(sql, &block)
107
+ block.call(:id => 1, :abc =>[Marshal.dump(1)].pack('m'), :def =>[Marshal.dump('hello')].pack('m'))
108
+ end
109
+
110
+ o = @c.first
111
+ o.id.should == 1
112
+ o.abc.should == 1
113
+ o.abc.should == 1
114
+ o.def.should == "hello"
115
+ o.def.should == "hello"
116
+
117
+ o.update(:abc => 23)
118
+ @c.create(:abc => [1, 2, 3])
119
+ MODEL_DB.sqls.should == ["UPDATE items SET abc = '#{[Marshal.dump(23)].pack('m')}' WHERE (id = 1)",
120
+ "INSERT INTO items (abc) VALUES ('#{[Marshal.dump([1, 2, 3])].pack('m')}')"]
121
+ end
122
+
123
+ it "should translate values to and from json serialization format using accessor methods" do
124
+ @c.set_primary_key :id
125
+ @c.plugin :serialization, :json, :abc, :def
126
+
127
+ ds = @c.dataset
128
+ def ds.fetch_rows(sql, &block)
129
+ block.call(:id => 1, :abc => JSON.generate([1]), :def => JSON.generate(["hello"]))
130
+ end
131
+
132
+ o = @c.first
133
+ o.id.should == 1
134
+ o.abc.should == [1]
135
+ o.abc.should == [1]
136
+ o.def.should == ["hello"]
137
+ o.def.should == ["hello"]
138
+
139
+ o.update(:abc => [23])
140
+ @c.create(:abc => [1,2,3])
141
+
142
+ MODEL_DB.sqls.should == ["UPDATE items SET abc = '#{JSON.generate([23])}' WHERE (id = 1)",
143
+ "INSERT INTO items (abc) VALUES ('#{JSON.generate([1,2,3])}')"]
144
+ end
145
+
146
+ it "should copy serialization formats and columns to subclasses" do
147
+ @c.set_primary_key :id
148
+ @c.plugin :serialization, :yaml, :abc, :def
149
+
150
+ ds = @c.dataset
151
+ def ds.fetch_rows(sql, &block)
152
+ block.call(:id => 1, :abc => "--- 1\n", :def => "--- hello\n")
153
+ end
154
+
155
+ o = Class.new(@c).first
156
+ o.id.should == 1
157
+ o.abc.should == 1
158
+ o.abc.should == 1
159
+ o.def.should == "hello"
160
+ o.def.should == "hello"
161
+
162
+ o.update(:abc => 23)
163
+ Class.new(@c).create(:abc => [1, 2, 3])
164
+ MODEL_DB.sqls.should == ["UPDATE items SET abc = '--- 23\n' WHERE (id = 1)",
165
+ "INSERT INTO items (abc) VALUES ('#{[1, 2, 3].to_yaml}')"]
166
+ end
167
+
168
+ it "should clear the deserialized columns when refreshing" do
169
+ @c.set_primary_key :id
170
+ @c.plugin :serialization, :yaml, :abc, :def
171
+ o = @c.load(:id => 1, :abc => "--- 1\n", :def => "--- hello\n")
172
+ o.abc = 23
173
+ o.deserialized_values.length.should == 1
174
+ o.abc.should == 23
175
+ o.refresh
176
+ o.deserialized_values.length.should == 0
177
+ end
178
+
179
+ it "should raise an error if calling internal serialization methods with bad columns" do
180
+ @c.set_primary_key :id
181
+ @c.plugin :serialization
182
+ o = @c.load(:id => 1, :abc => "--- 1\n", :def => "--- hello\n")
183
+ lambda{o.send(:serialize_value, :abc, 1)}.should raise_error(Sequel::Error)
184
+ lambda{o.send(:deserialize_value, :abc, "--- hello\n")}.should raise_error(Sequel::Error)
185
+ end
186
+
187
+ it "should add the accessors to a module included in the class, so they can be easily overridden" do
188
+ @c.class_eval do
189
+ def abc
190
+ "#{super}-blah"
191
+ end
192
+ end
193
+ @c.plugin :serialization, :yaml, :abc
194
+ o = @c.load(:abc => "--- 1\n")
195
+ o.abc.should == "1-blah"
196
+ end
197
+
198
+ it "should call super to get the deserialized value from a previous accessor" do
199
+ m = Module.new do
200
+ def abc
201
+ "--- #{@values[:abc]*3}\n"
202
+ end
203
+ end
204
+ @c.send(:include, m)
205
+ @c.plugin :serialization, :yaml, :abc
206
+ o = @c.load(:abc => 3)
207
+ o.abc.should == 9
208
+ end
209
+ end
@@ -0,0 +1,96 @@
1
+ require File.join(File.dirname(__FILE__), "spec_helper")
2
+
3
+ describe Sequel::Model, "#sti_key" do
4
+ before do
5
+ class ::StiTest < Sequel::Model
6
+ def kind; self[:kind]; end
7
+ def kind=(x); self[:kind] = x; end
8
+ def _refresh(x); end
9
+ plugin :single_table_inheritance, :kind
10
+ end
11
+ class ::StiTestSub1 < StiTest
12
+ end
13
+ class ::StiTestSub2 < StiTest
14
+ end
15
+ @ds = StiTest.dataset
16
+ MODEL_DB.reset
17
+ end
18
+ after do
19
+ Object.send(:remove_const, :StiTestSub1)
20
+ Object.send(:remove_const, :StiTestSub2)
21
+ Object.send(:remove_const, :StiTest)
22
+ end
23
+
24
+ specify "should have simple_table = nil" do
25
+ StiTest.simple_table.should == nil
26
+ StiTestSub1.simple_table.should == nil
27
+ end
28
+
29
+ it "should allow changing the inheritance column via a plugin :single_table_inheritance call" do
30
+ StiTest.plugin :single_table_inheritance, :blah
31
+ Object.send(:remove_const, :StiTestSub1)
32
+ Object.send(:remove_const, :StiTestSub2)
33
+ class ::StiTestSub1 < StiTest
34
+ end
35
+ class ::StiTestSub2 < StiTest
36
+ end
37
+ def @ds.fetch_rows(sql)
38
+ yield({:blah=>'StiTest'})
39
+ yield({:blah=>'StiTestSub1'})
40
+ yield({:blah=>'StiTestSub2'})
41
+ end
42
+ StiTest.all.collect{|x| x.class}.should == [StiTest, StiTestSub1, StiTestSub2]
43
+ StiTest.dataset.sql.should == "SELECT * FROM sti_tests"
44
+ StiTestSub1.dataset.sql.should == "SELECT * FROM sti_tests WHERE (sti_tests.blah = 'StiTestSub1')"
45
+ StiTestSub2.dataset.sql.should == "SELECT * FROM sti_tests WHERE (sti_tests.blah = 'StiTestSub2')"
46
+ end
47
+
48
+ it "should return rows with the correct class based on the polymorphic_key value" do
49
+ def @ds.fetch_rows(sql)
50
+ yield({:kind=>'StiTest'})
51
+ yield({:kind=>'StiTestSub1'})
52
+ yield({:kind=>'StiTestSub2'})
53
+ end
54
+ StiTest.all.collect{|x| x.class}.should == [StiTest, StiTestSub1, StiTestSub2]
55
+ end
56
+
57
+ it "should fallback to the main class if the given class does not exist" do
58
+ def @ds.fetch_rows(sql)
59
+ yield({:kind=>'StiTestSub3'})
60
+ end
61
+ StiTest.all.collect{|x| x.class}.should == [StiTest]
62
+ end
63
+
64
+ it "should fallback to the main class if the sti_key field is empty or nil without calling constantize" do
65
+ called = false
66
+ StiTest.meta_def(:constantize) do |s|
67
+ called = true
68
+ Object
69
+ end
70
+ StiTest.plugin :single_table_inheritance, :kind
71
+ def @ds.fetch_rows(sql)
72
+ yield({:kind=>''})
73
+ yield({:kind=>nil})
74
+ end
75
+ StiTest.all.collect{|x| x.class}.should == [StiTest, StiTest]
76
+ called.should == false
77
+ end
78
+
79
+ it "should add a before_create hook that sets the model class name for the key" do
80
+ StiTest.new.save
81
+ StiTestSub1.new.save
82
+ StiTestSub2.new.save
83
+ MODEL_DB.sqls.should == ["INSERT INTO sti_tests (kind) VALUES ('StiTest')", "INSERT INTO sti_tests (kind) VALUES ('StiTestSub1')", "INSERT INTO sti_tests (kind) VALUES ('StiTestSub2')"]
84
+ end
85
+
86
+ it "should have the before_create hook not override an existing value" do
87
+ StiTest.create(:kind=>'StiTestSub1')
88
+ MODEL_DB.sqls.should == ["INSERT INTO sti_tests (kind) VALUES ('StiTestSub1')"]
89
+ end
90
+
91
+ it "should add a filter to model datasets inside subclasses hook to only retreive objects with the matching key" do
92
+ StiTest.dataset.sql.should == "SELECT * FROM sti_tests"
93
+ StiTestSub1.dataset.sql.should == "SELECT * FROM sti_tests WHERE (sti_tests.kind = 'StiTestSub1')"
94
+ StiTestSub2.dataset.sql.should == "SELECT * FROM sti_tests WHERE (sti_tests.kind = 'StiTestSub2')"
95
+ end
96
+ end
@@ -0,0 +1,91 @@
1
+ require 'rubygems'
2
+ unless Object.const_defined?('Sequel')
3
+ $:.unshift(File.join(File.dirname(__FILE__), "../../lib/"))
4
+ require 'sequel/core'
5
+ end
6
+ unless Sequel.const_defined?('Model')
7
+ $:.unshift(File.join(File.dirname(__FILE__), "../../lib/"))
8
+ require 'sequel/model'
9
+ end
10
+
11
+ Sequel.extension(*%w'string_date_time inflector pagination query pretty_table blank migration schema_dumper looser_typecasting sql_expr thread_local_timezones')
12
+ {:hook_class_methods=>[], :schema=>[], :validation_class_methods=>[]}.each{|p, opts| Sequel::Model.plugin(p, *opts)}
13
+
14
+ class MockDataset < Sequel::Dataset
15
+ def insert(*args)
16
+ @db.execute insert_sql(*args)
17
+ end
18
+
19
+ def update(*args)
20
+ @db.execute update_sql(*args)
21
+ 1
22
+ end
23
+
24
+ def delete(*args)
25
+ @db.execute delete_sql(*args)
26
+ 1
27
+ end
28
+
29
+ def fetch_rows(sql)
30
+ return if sql =~ /information_schema/
31
+ @db.execute(sql)
32
+ yield({:id => 1, :x => 1})
33
+ end
34
+
35
+ def quoted_identifier(c)
36
+ "\"#{c}\""
37
+ end
38
+ end
39
+
40
+ class MockDatabase < Sequel::Database
41
+ @@quote_identifiers = false
42
+ self.identifier_input_method = nil
43
+ self.identifier_output_method = nil
44
+ attr_reader :sqls
45
+
46
+ def execute(sql, opts={})
47
+ @sqls ||= []
48
+ @sqls << sql
49
+ end
50
+
51
+ def new_sqls
52
+ s = sqls
53
+ reset
54
+ s
55
+ end
56
+
57
+ def reset
58
+ @sqls = []
59
+ end
60
+
61
+ def schema(table_name, opts)
62
+ if table_name
63
+ [[:id, {:primary_key=>true}]]
64
+ else
65
+ {table_name=>[[:id, {:primary_key=>true}]]}
66
+ end
67
+ end
68
+
69
+ def transaction(opts={}); yield; end
70
+
71
+ def dataset(opts=nil); MockDataset.new(self, opts); end
72
+ end
73
+
74
+ class << Sequel::Model
75
+ alias orig_columns columns
76
+ def columns(*cols)
77
+ return if cols.empty?
78
+ define_method(:columns){cols}
79
+ @dataset.instance_variable_set(:@columns, cols) if @dataset
80
+ def_column_accessor(*cols)
81
+ @columns = cols
82
+ @db_schema = {}
83
+ cols.each{|c| @db_schema[c] = {}}
84
+ end
85
+ def simple_table
86
+ nil
87
+ end
88
+ end
89
+
90
+ Sequel::Model.db = MODEL_DB = MockDatabase.new
91
+ Sequel::Model.use_transactions = false
@@ -0,0 +1,89 @@
1
+ require File.join(File.dirname(__FILE__), 'spec_helper')
2
+
3
+ context "Sequel sql_expr extension" do
4
+ specify "Object#sql_expr should wrap the object in a GenericComplexExpression" do
5
+ o = Object.new
6
+ s = o.sql_expr
7
+ s.should be_a_kind_of(Sequel::SQL::GenericComplexExpression)
8
+ s.op.should == :NOOP
9
+ s.args.should == [o]
10
+ (s+1).should be_a_kind_of(Sequel::SQL::NumericExpression)
11
+ (s & true).should be_a_kind_of(Sequel::SQL::BooleanExpression)
12
+ (s < 1).should be_a_kind_of(Sequel::SQL::BooleanExpression)
13
+ s.sql_subscript(1).should be_a_kind_of(Sequel::SQL::Subscript)
14
+ s.like('a').should be_a_kind_of(Sequel::SQL::BooleanExpression)
15
+ s.as(:a).should be_a_kind_of(Sequel::SQL::AliasedExpression)
16
+ s.cast(Integer).should be_a_kind_of(Sequel::SQL::Cast)
17
+ s.desc.should be_a_kind_of(Sequel::SQL::OrderedExpression)
18
+ s.sql_string.should be_a_kind_of(Sequel::SQL::StringExpression)
19
+ end
20
+
21
+ specify "Numeric#sql_expr should wrap the object in a NumericExpression" do
22
+ [1, 2.0, 2^40, BigDecimal.new('1.0')].each do |o|
23
+ s = o.sql_expr
24
+ s.should be_a_kind_of(Sequel::SQL::NumericExpression)
25
+ s.op.should == :NOOP
26
+ s.args.should == [o]
27
+ end
28
+ end
29
+
30
+ specify "String#sql_expr should wrap the object in a StringExpression" do
31
+ o = ""
32
+ s = o.sql_expr
33
+ s.should be_a_kind_of(Sequel::SQL::StringExpression)
34
+ s.op.should == :NOOP
35
+ s.args.should == [o]
36
+ end
37
+
38
+ specify "NilClass, TrueClass, and FalseClass#sql_expr should wrap the object in a BooleanExpression" do
39
+ [nil, true, false].each do |o|
40
+ s = o.sql_expr
41
+ s.should be_a_kind_of(Sequel::SQL::BooleanExpression)
42
+ s.op.should == :NOOP
43
+ s.args.should == [o]
44
+ end
45
+ end
46
+
47
+ specify "Proc#sql_expr should should treat the object as a virtual row block" do
48
+ s = proc{a}.sql_expr
49
+ s.should be_a_kind_of(Sequel::SQL::Identifier)
50
+ s.value.should == :a
51
+
52
+ s = proc{a__b}.sql_expr
53
+ s.should be_a_kind_of(Sequel::SQL::QualifiedIdentifier)
54
+ s.table.should == "a"
55
+ s.column.should == "b"
56
+
57
+ s = proc{a(b)}.sql_expr
58
+ s.should be_a_kind_of(Sequel::SQL::Function)
59
+ s.f.should == :a
60
+ s.args.length.should == 1
61
+ s.args.first.should be_a_kind_of(Sequel::SQL::Identifier)
62
+ s.args.first.value.should == :b
63
+ end
64
+
65
+ specify "Proc#sql_expr should should wrap the object in a GenericComplexExpression if the object is not already an expression" do
66
+ s = proc{1}.sql_expr
67
+ s.should be_a_kind_of(Sequel::SQL::GenericComplexExpression)
68
+ s.op.should == :NOOP
69
+ s.args.should == [1]
70
+ end
71
+
72
+ specify "Proc#sql_expr should should convert a hash or array of two element arrays to a BooleanExpression" do
73
+ s = proc{{a=>b}}.sql_expr
74
+ s.should be_a_kind_of(Sequel::SQL::BooleanExpression)
75
+ s.op.should == :"="
76
+ s.args.first.should be_a_kind_of(Sequel::SQL::Identifier)
77
+ s.args.first.value.should == :a
78
+ s.args.last.should be_a_kind_of(Sequel::SQL::Identifier)
79
+ s.args.last.value.should == :b
80
+
81
+ s = proc{[[a,b]]}.sql_expr
82
+ s.should be_a_kind_of(Sequel::SQL::BooleanExpression)
83
+ s.op.should == :"="
84
+ s.args.first.should be_a_kind_of(Sequel::SQL::Identifier)
85
+ s.args.first.value.should == :a
86
+ s.args.last.should be_a_kind_of(Sequel::SQL::Identifier)
87
+ s.args.last.value.should == :b
88
+ end
89
+ end