sequel 2.2.0 → 2.3.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (98) hide show
  1. data/CHANGELOG +1551 -4
  2. data/README +306 -19
  3. data/Rakefile +84 -56
  4. data/bin/sequel +106 -0
  5. data/doc/cheat_sheet.rdoc +225 -0
  6. data/doc/dataset_filtering.rdoc +182 -0
  7. data/lib/sequel_core.rb +136 -0
  8. data/lib/sequel_core/adapters/adapter_skeleton.rb +54 -0
  9. data/lib/sequel_core/adapters/ado.rb +80 -0
  10. data/lib/sequel_core/adapters/db2.rb +148 -0
  11. data/lib/sequel_core/adapters/dbi.rb +117 -0
  12. data/lib/sequel_core/adapters/informix.rb +78 -0
  13. data/lib/sequel_core/adapters/jdbc.rb +186 -0
  14. data/lib/sequel_core/adapters/jdbc/mysql.rb +55 -0
  15. data/lib/sequel_core/adapters/jdbc/postgresql.rb +66 -0
  16. data/lib/sequel_core/adapters/jdbc/sqlite.rb +47 -0
  17. data/lib/sequel_core/adapters/mysql.rb +231 -0
  18. data/lib/sequel_core/adapters/odbc.rb +155 -0
  19. data/lib/sequel_core/adapters/odbc_mssql.rb +106 -0
  20. data/lib/sequel_core/adapters/openbase.rb +64 -0
  21. data/lib/sequel_core/adapters/oracle.rb +170 -0
  22. data/lib/sequel_core/adapters/postgres.rb +199 -0
  23. data/lib/sequel_core/adapters/shared/mysql.rb +275 -0
  24. data/lib/sequel_core/adapters/shared/postgres.rb +351 -0
  25. data/lib/sequel_core/adapters/shared/sqlite.rb +146 -0
  26. data/lib/sequel_core/adapters/sqlite.rb +138 -0
  27. data/lib/sequel_core/connection_pool.rb +194 -0
  28. data/lib/sequel_core/core_ext.rb +203 -0
  29. data/lib/sequel_core/core_sql.rb +184 -0
  30. data/lib/sequel_core/database.rb +471 -0
  31. data/lib/sequel_core/database/schema.rb +156 -0
  32. data/lib/sequel_core/dataset.rb +457 -0
  33. data/lib/sequel_core/dataset/callback.rb +13 -0
  34. data/lib/sequel_core/dataset/convenience.rb +245 -0
  35. data/lib/sequel_core/dataset/pagination.rb +96 -0
  36. data/lib/sequel_core/dataset/query.rb +41 -0
  37. data/lib/sequel_core/dataset/schema.rb +15 -0
  38. data/lib/sequel_core/dataset/sql.rb +889 -0
  39. data/lib/sequel_core/deprecated.rb +26 -0
  40. data/lib/sequel_core/exceptions.rb +42 -0
  41. data/lib/sequel_core/migration.rb +187 -0
  42. data/lib/sequel_core/object_graph.rb +216 -0
  43. data/lib/sequel_core/pretty_table.rb +71 -0
  44. data/lib/sequel_core/schema.rb +2 -0
  45. data/lib/sequel_core/schema/generator.rb +239 -0
  46. data/lib/sequel_core/schema/sql.rb +325 -0
  47. data/lib/sequel_core/sql.rb +812 -0
  48. data/lib/sequel_model.rb +5 -1
  49. data/lib/sequel_model/association_reflection.rb +3 -8
  50. data/lib/sequel_model/base.rb +15 -10
  51. data/lib/sequel_model/inflector.rb +3 -5
  52. data/lib/sequel_model/plugins.rb +1 -1
  53. data/lib/sequel_model/record.rb +11 -3
  54. data/lib/sequel_model/schema.rb +4 -4
  55. data/lib/sequel_model/validations.rb +6 -1
  56. data/spec/adapters/ado_spec.rb +17 -0
  57. data/spec/adapters/informix_spec.rb +96 -0
  58. data/spec/adapters/mysql_spec.rb +764 -0
  59. data/spec/adapters/oracle_spec.rb +222 -0
  60. data/spec/adapters/postgres_spec.rb +441 -0
  61. data/spec/adapters/spec_helper.rb +7 -0
  62. data/spec/adapters/sqlite_spec.rb +400 -0
  63. data/spec/integration/dataset_test.rb +51 -0
  64. data/spec/integration/eager_loader_test.rb +702 -0
  65. data/spec/integration/schema_test.rb +102 -0
  66. data/spec/integration/spec_helper.rb +44 -0
  67. data/spec/integration/type_test.rb +43 -0
  68. data/spec/rcov.opts +2 -0
  69. data/spec/sequel_core/connection_pool_spec.rb +363 -0
  70. data/spec/sequel_core/core_ext_spec.rb +156 -0
  71. data/spec/sequel_core/core_sql_spec.rb +427 -0
  72. data/spec/sequel_core/database_spec.rb +964 -0
  73. data/spec/sequel_core/dataset_spec.rb +2977 -0
  74. data/spec/sequel_core/expression_filters_spec.rb +346 -0
  75. data/spec/sequel_core/migration_spec.rb +261 -0
  76. data/spec/sequel_core/object_graph_spec.rb +234 -0
  77. data/spec/sequel_core/pretty_table_spec.rb +58 -0
  78. data/spec/sequel_core/schema_generator_spec.rb +122 -0
  79. data/spec/sequel_core/schema_spec.rb +497 -0
  80. data/spec/sequel_core/spec_helper.rb +51 -0
  81. data/spec/{association_reflection_spec.rb → sequel_model/association_reflection_spec.rb} +6 -6
  82. data/spec/{associations_spec.rb → sequel_model/associations_spec.rb} +47 -18
  83. data/spec/{base_spec.rb → sequel_model/base_spec.rb} +2 -1
  84. data/spec/{caching_spec.rb → sequel_model/caching_spec.rb} +0 -0
  85. data/spec/{dataset_methods_spec.rb → sequel_model/dataset_methods_spec.rb} +13 -1
  86. data/spec/{eager_loading_spec.rb → sequel_model/eager_loading_spec.rb} +75 -14
  87. data/spec/{hooks_spec.rb → sequel_model/hooks_spec.rb} +4 -4
  88. data/spec/sequel_model/inflector_spec.rb +119 -0
  89. data/spec/{model_spec.rb → sequel_model/model_spec.rb} +30 -11
  90. data/spec/{plugins_spec.rb → sequel_model/plugins_spec.rb} +0 -0
  91. data/spec/{record_spec.rb → sequel_model/record_spec.rb} +47 -6
  92. data/spec/{schema_spec.rb → sequel_model/schema_spec.rb} +18 -4
  93. data/spec/{spec_helper.rb → sequel_model/spec_helper.rb} +3 -2
  94. data/spec/{validations_spec.rb → sequel_model/validations_spec.rb} +37 -17
  95. data/spec/spec_config.rb +9 -0
  96. data/spec/spec_config.rb.example +10 -0
  97. metadata +110 -37
  98. data/spec/inflector_spec.rb +0 -34
data/README CHANGED
@@ -1,3 +1,309 @@
1
+ == Sequel: The Database Toolkit for Ruby
2
+
3
+ Sequel is a lightweight database access toolkit for Ruby.
4
+
5
+ * Sequel provides thread safety, connection pooling and a concise DSL
6
+ for constructing database queries and table schemas.
7
+ * Sequel also includes a lightweight but comprehensive ORM layer for
8
+ mapping records to Ruby objects and handling associated records.
9
+ * Sequel makes it easy to deal with multiple records without having
10
+ to break your teeth on SQL.
11
+ * Sequel currently has adapters for ADO, DB2, DBI, Informix, JDBC,
12
+ MySQL, ODBC, OpenBase, Oracle, PostgreSQL and SQLite3.
13
+
14
+ == Resources
15
+
16
+ * {Source code}[http://github.com/jeremyevans/sequel]
17
+ * {Bug tracking}[http://code.google.com/p/ruby-sequel/issues/list]
18
+ * {Google group}[http://groups.google.com/group/sequel-talk]
19
+ * {RDoc}[http://sequel.rubyforge.org]
20
+
21
+ To check out the source code:
22
+
23
+ git clone git://github.com/jeremyevans/sequel.git
24
+
25
+ === Contact
26
+
27
+ If you have any comments or suggestions please post to the Google group.
28
+
29
+ == Installation
30
+
31
+ sudo gem install sequel
32
+
33
+ == A Short Example
34
+
35
+ require 'rubygems'
36
+ require 'sequel'
37
+
38
+ DB = Sequel.sqlite # memory database
39
+
40
+ DB.create_table :items do # Create a new table
41
+ column :name, :text
42
+ column :price, :float
43
+ end
44
+
45
+ items = DB[:items] # Create a dataset
46
+
47
+ # Populate the table
48
+ items << {:name => 'abc', :price => rand * 100}
49
+ items << {:name => 'def', :price => rand * 100}
50
+ items << {:name => 'ghi', :price => rand * 100}
51
+
52
+ # Print out the number of records
53
+ puts "Item count: #{items.count}"
54
+
55
+ # Print out the records in descending order by price
56
+ items.reverse_order(:price).print
57
+
58
+ # Print out the average price
59
+ puts "The average price is: #{items.avg(:price)}"
60
+
61
+ == The Sequel Console
62
+
63
+ Sequel includes an IRB console for quick'n'dirty access to databases. You can use it like this:
64
+
65
+ sequel sqlite://test.db # test.db in current directory
66
+
67
+ You get an IRB session with the database object stored in DB.
68
+
69
+ == An Introduction
70
+
71
+ Sequel is designed to take the hassle away from connecting to databases and manipulating them. Sequel deals with all the boring stuff like maintaining connections, formatting SQL correctly and fetching records so you can concentrate on your application.
72
+
73
+ Sequel uses the concept of datasets to retrieve data. A Dataset object encapsulates an SQL query and supports chainability, letting you fetch data using a convenient Ruby DSL that is both concise and infinitely flexible.
74
+
75
+ For example, the following one-liner returns the average GDP for the five biggest countries in the middle east region:
76
+
77
+ DB[:countries].filter(:region => 'Middle East').reverse_order(:area).limit(5).avg(:GDP)
78
+
79
+ Which is equivalent to:
80
+
81
+ SELECT avg(GDP) FROM countries WHERE region = 'Middle East' ORDER BY area DESC LIMIT 5
82
+
83
+ Since datasets retrieve records only when needed, they can be stored and later reused. Records are fetched as hashes (they can also be fetched as custom model objects), and are accessed using an Enumerable interface:
84
+
85
+ middle_east = DB[:countries].filter(:region => 'Middle East')
86
+ middle_east.order(:name).each {|r| puts r[:name]}
87
+
88
+ Sequel also offers convenience methods for extracting data from Datasets, such as an extended map method:
89
+
90
+ middle_east.map(:name) #=> ['Egypt', 'Greece', 'Israel', ...]
91
+
92
+ Or getting results as a transposed hash, with one column as key and another as value:
93
+
94
+ middle_east.to_hash(:name, :area) #=> {'Israel' => 20000, 'Greece' => 120000, ...}
95
+
96
+ == Getting Started
97
+
98
+ === Connecting to a database
99
+
100
+ To connect to a database you simply provide Sequel with a URL:
101
+
102
+ require 'sequel'
103
+ DB = Sequel.connect('sqlite://blog.db')
104
+
105
+ The connection URL can also include such stuff as the user name and password:
106
+
107
+ DB = Sequel.connect('postgres://cico:12345@localhost:5432/mydb')
108
+
109
+ You can also specify optional parameters, such as the connection pool size, or loggers for logging SQL queries:
110
+
111
+ DB = Sequel.connect("postgres://postgres:postgres@localhost/my_db",
112
+ :max_connections => 10, :loggers => [Logger.new('log/db.log']))
113
+
114
+ You can specify a block to connect, which will disconnect from the database after it completes:
115
+
116
+ Sequel.connect('postgres://cico:12345@localhost:5432/mydb'){|db| db[:posts].delete}
117
+
118
+ === Arbitrary SQL queries
119
+
120
+ DB.execute("create table t (a text, b text)")
121
+ DB.execute("insert into t values ('a', 'b')")
122
+
123
+ Or more succinctly:
124
+
125
+ DB << "create table t (a text, b text)"
126
+ DB << "insert into t values ('a', 'b')"
127
+
128
+ You can also create datasets based on raw SQL:
129
+
130
+ dataset = DB['select * from items']
131
+ dataset.count # will return the number of records in the result set
132
+ dataset.map(:id) # will return an array containing all values of the id column in the result set
133
+
134
+ You can also fetch records with raw SQL through the dataset:
135
+
136
+ DB['select * from items'].each do |row|
137
+ p row
138
+ end
139
+
140
+ === Getting Dataset Instances
141
+
142
+ Dataset is the primary means through which records are retrieved and manipulated. You can create an blank dataset by using the dataset method:
143
+
144
+ dataset = DB.dataset
145
+
146
+ Or by using the from methods:
147
+
148
+ posts = DB.from(:posts)
149
+
150
+ The recommended way is the equivalent shorthand:
151
+
152
+ posts = DB[:posts]
153
+
154
+ Datasets will only fetch records when you explicitly ask for them. Datasets can be manipulated to filter through records, change record order, join tables, etc..
155
+
156
+ === Retrieving Records
157
+
158
+ You can retrieve records by using the all method:
159
+
160
+ posts.all
161
+
162
+ The all method returns an array of hashes, where each hash corresponds to a record.
163
+
164
+ You can also iterate through records one at a time:
165
+
166
+ posts.each{|row| p row}
167
+
168
+ Or perform more advanced stuff:
169
+
170
+ posts.map(:id)
171
+ posts.inject({}){|h, r| h[r[:id]] = r[:name]}
172
+
173
+ You can also retrieve the first record in a dataset:
174
+
175
+ posts.first
176
+
177
+ Or retrieve a single record with a specific value:
178
+
179
+ posts[:id => 1]
180
+
181
+ If the dataset is ordered, you can also ask for the last record:
182
+
183
+ posts.order(:stamp).last
184
+
185
+ === Filtering Records
186
+
187
+ The simplest way to filter records is to provide a hash of values to match:
188
+
189
+ my_posts = posts.filter(:category => 'ruby', :author => 'david')
190
+
191
+ You can also specify ranges:
192
+
193
+ my_posts = posts.filter(:stamp => (Date.today - 14)..(Date.today - 7))
194
+
195
+ Or lists of values:
196
+
197
+ my_posts = posts.filter(:category => ['ruby', 'postgres', 'linux'])
198
+
199
+ Sequel also accepts expressions:
200
+
201
+ my_posts = posts.filter(:stamp > Date.today << 1)
202
+
203
+ Some adapters (like postgresql) will also let you specify Regexps:
204
+
205
+ my_posts = posts.filter(:category => /ruby/i)
206
+
207
+ You can also use an inverse filter:
208
+
209
+ my_posts = posts.exclude(:category => /ruby/i)
210
+ my_posts = posts.filter(:category => /ruby/i).invert # same as above
211
+
212
+ You can also specify a custom WHERE clause using a string:
213
+
214
+ posts.filter('stamp IS NOT NULL')
215
+
216
+ You can use parameters in your string, as well (ActiveRecord style):
217
+
218
+ posts.filter('(stamp < ?) AND (author != ?)', Date.today - 3, author_name)
219
+ posts.filter((:stamp < Date.today - 3) & ~(:author => author_name)) # same as above
220
+
221
+ Datasets can also be used as subqueries:
222
+
223
+ DB[:items].filter('price > ?', DB[:items].select('AVG(price) + 100'))
224
+
225
+ After filtering you can retrieve the matching records by using any of the retrieval methods:
226
+
227
+ my_posts.each{|row| p row}
228
+
229
+ See the doc/dataset_filtering.rdoc file for more details.
230
+
231
+ === Summarizing Records
232
+
233
+ Counting records is easy:
234
+ posts.filter(:category => /ruby/i).count
235
+
236
+ And you can also query maximum/minimum values:
237
+ max_value = DB[:history].max(:value)
238
+
239
+ Or calculate a sum:
240
+ total = DB[:items].sum(:price)
241
+
242
+ === Ordering Records
243
+
244
+ Ordering datasets is simple:
245
+
246
+ posts.order(:stamp) # ORDER BY stamp
247
+ posts.order(:stamp, :name) # ORDER BY stamp, name
248
+
249
+ You can also specify descending order
250
+
251
+ posts.order(:stamp.desc) # ORDER BY stamp DESC
252
+
253
+ === Deleting Records
254
+
255
+ Deleting records from the table is done with delete:
256
+
257
+ posts.filter('stamp < ?', Date.today - 3).delete
258
+
259
+ === Inserting Records
260
+
261
+ Inserting records into the table is done with insert:
262
+
263
+ posts.insert(:category => 'ruby', :author => 'david')
264
+ posts << {:category => 'ruby', :author => 'david'} # same as above
265
+
266
+ === Updating Records
267
+
268
+ Updating records in the table is done with update:
269
+
270
+ posts.filter('stamp < ?', Date.today - 7).update(:state => 'archived')
271
+
272
+ === Joining Tables
273
+
274
+ Joining is very useful in a variety of scenarios, for example many-to-many relationships. With Sequel it's really easy:
275
+
276
+ order_items = DB[:items].join(:order_items, :item_id => :id).
277
+ filter(:order_items__order_id => 1234)
278
+
279
+ This is equivalent to the SQL:
280
+
281
+ SELECT * FROM items LEFT OUTER JOIN order_items
282
+ ON order_items.item_id = items.id
283
+ WHERE order_items.order_id = 1234
284
+
285
+ You can then do anything you like with the dataset:
286
+
287
+ order_total = order_items.sum(:price)
288
+
289
+ Which is equivalent to the SQL:
290
+
291
+ SELECT sum(price) FROM items LEFT OUTER JOIN order_items
292
+ ON order_items.item_id = items.id
293
+ WHERE order_items.order_id = 1234
294
+
295
+ === Graphing Datasets
296
+
297
+ When retrieving records from joined datasets, you get the results in a single hash, which is subject to clobbering:
298
+
299
+ DB[:items].join(:order_items, :item_id => :id).first
300
+ => {:id=>(could be items.id or order_items.id), :item_id=>order_items.order_id}
301
+
302
+ Using graph, you can split the result hashes into subhashes, one per join:
303
+
304
+ DB[:items].graph(:order_items, :item_id => :id).first
305
+ => {:items=>{:id=>items.id}, :order_items=>{:id=>order_items.id, :item_id=>order_items.item_id}}
306
+
1
307
  == Sequel Models
2
308
 
3
309
  Models in Sequel are based on the Active Record pattern described by Martin Fowler (http://www.martinfowler.com/eaaCatalog/activeRecord.html). A model class corresponds to a table or a dataset, and an instance of that class wraps a single record in the model's underlying dataset.
@@ -21,25 +327,6 @@ You can, however, explicitly set the table name or even the dataset used:
21
327
  # or:
22
328
  Post.set_dataset DB[:my_posts].where(:category => 'ruby')
23
329
 
24
- === Resources
25
-
26
- * {Source code}[http://github.com/jeremyevans/sequel]
27
- * {Bug tracking}[http://code.google.com/p/ruby-sequel/issues/list]
28
- * {Google group}[http://groups.google.com/group/sequel-talk]
29
- * {RDoc}[http://sequel.rubyforge.org]
30
-
31
- To check out the source code:
32
-
33
- git clone git://github.com/jeremyevans/sequel.git
34
-
35
- === Contact
36
-
37
- If you have any comments or suggestions please post to the Google group.
38
-
39
- === Installation
40
-
41
- sudo gem install sequel
42
-
43
330
  === Model instances
44
331
 
45
332
  Model instance are identified by a primary key. By default, Sequel assumes the primary key column to be :id. The Model#[] method can be used to fetch records by their primary key:
data/Rakefile CHANGED
@@ -3,33 +3,21 @@ require "rake/clean"
3
3
  require "rake/gempackagetask"
4
4
  require "rake/rdoctask"
5
5
  require "fileutils"
6
+ require "spec/rake/spectask"
7
+
6
8
  include FileUtils
7
9
 
8
- ##############################################################################
9
- # Configuration
10
- ##############################################################################
11
- NAME = "sequel"
12
- VERS = "2.2.0"
13
- SEQUEL_CORE_VERS= "2.2.0"
10
+ NAME = 'sequel'
11
+ VERS = '2.3.0'
14
12
  CLEAN.include ["**/.*.sw?", "pkg", ".config", "rdoc", "coverage"]
15
13
  RDOC_OPTS = ["--quiet", "--line-numbers", "--inline-source", '--title', \
16
- 'Sequel: The Database Toolkit for Ruby: Model Classes', '--main', 'README']
17
-
18
- ##############################################################################
19
- # RDoc
20
- ##############################################################################
21
- Rake::RDocTask.new do |rdoc|
22
- rdoc.rdoc_dir = "rdoc"
23
- rdoc.options += RDOC_OPTS
24
- rdoc.rdoc_files.add ["README", "COPYING", "doc/*.rdoc", "lib/**/*.rb"]
25
- end
14
+ 'Sequel: The Database Toolkit for Ruby', '--main', 'README']
26
15
 
27
16
  ##############################################################################
28
- # Gem packaging
17
+ # gem packaging and release
29
18
  ##############################################################################
30
- desc "Packages up Sequel."
31
- task :package => [:clean]
32
-
19
+ desc "Packages sequel"
20
+ task :package=>[:clean]
33
21
  spec = Gem::Specification.new do |s|
34
22
  s.name = NAME
35
23
  s.rubyforge_project = 'sequel'
@@ -37,80 +25,120 @@ spec = Gem::Specification.new do |s|
37
25
  s.platform = Gem::Platform::RUBY
38
26
  s.has_rdoc = true
39
27
  s.extra_rdoc_files = ["README", "CHANGELOG", "COPYING"] + Dir["doc/*.rdoc"]
40
- s.rdoc_options += RDOC_OPTS + ["--exclude", "^(examples|extras)\/"]
41
- s.summary = "The Database Toolkit for Ruby: Model Classes"
28
+ s.rdoc_options += RDOC_OPTS
29
+ s.summary = "The Database Toolkit for Ruby"
42
30
  s.description = s.summary
43
31
  s.author = "Jeremy Evans"
44
32
  s.email = "code@jeremyevans.net"
45
33
  s.homepage = "http://sequel.rubyforge.org"
46
34
  s.required_ruby_version = ">= 1.8.4"
47
- s.add_dependency("sequel_core", "= #{SEQUEL_CORE_VERS}")
48
- s.files = %w(COPYING README Rakefile) + Dir.glob("{doc,spec,lib}/**/*")
35
+ s.files = %w(COPYING CHANGELOG README Rakefile) + Dir.glob("{bin,doc,spec,lib}/**/*")
49
36
  s.require_path = "lib"
37
+ s.bindir = 'bin'
38
+ s.executables << 'sequel'
50
39
  end
51
-
52
40
  Rake::GemPackageTask.new(spec) do |p|
53
41
  p.need_tar = true
54
42
  p.gem_spec = spec
55
43
  end
56
44
 
57
- ##############################################################################
58
- # installation & removal
59
- ##############################################################################
60
45
  desc "Install sequel gem"
61
- task :install do
62
- sh %{rake package}
46
+ task :install=>[:package] do
63
47
  sh %{sudo gem install pkg/#{NAME}-#{VERS} --local}
64
48
  end
65
49
 
66
- desc "Install sequel gem without docs"
67
- task :install_no_docs do
68
- sh %{rake package}
50
+ desc "Install sequel gem without RDoc"
51
+ task :install_no_docs=>[:package] do
69
52
  sh %{sudo gem install pkg/#{NAME}-#{VERS} --no-rdoc --no-ri --local}
70
53
  end
71
54
 
72
55
  desc "Uninstall sequel gem"
73
- task :uninstall => [:clean] do
56
+ task :uninstall=>[:clean] do
74
57
  sh %{sudo gem uninstall #{NAME}}
75
58
  end
76
59
 
77
- ##############################################################################
78
- # gem and rdoc release
79
- ##############################################################################
80
- desc "Upload sequel gem to rubyforge"
81
- task :release => [:package] do
60
+ desc "Upload sequel and sequel_core gems to rubyforge"
61
+ task :release=>[:package] do
82
62
  sh %{rubyforge login}
83
63
  sh %{rubyforge add_release sequel #{NAME} #{VERS} pkg/#{NAME}-#{VERS}.tgz}
84
- sh %{rubyforge add_file sequel #{NAME} #{VERS} pkg/#{NAME}-#{VERS}.gem}
64
+ sh %{rubyforge add_file sequel #{NAME} #{VERS} pkg/#{NAME}-#{VERS}.gem}
65
+ end
66
+
67
+ ##############################################################################
68
+ # rdoc
69
+ ##############################################################################
70
+ Rake::RDocTask.new do |rdoc|
71
+ rdoc.rdoc_dir = "rdoc"
72
+ rdoc.options += RDOC_OPTS
73
+ rdoc.rdoc_files.add %w"README CHANGELOG COPYING lib/**/*.rb doc/*.rdoc"
74
+ end
75
+
76
+ desc "Update docs and upload to rubyforge.org"
77
+ task :doc_rforge => [:rdoc]
78
+ task :doc_rforge do
79
+ sh %{chmod -R g+w rdoc/*}
80
+ sh %{scp -rp rdoc/* rubyforge.org:/var/www/gforge-projects/sequel}
85
81
  end
86
82
 
87
83
  ##############################################################################
88
84
  # specs
89
85
  ##############################################################################
90
- require "spec/rake/spectask"
91
- sqcdir = File.join(File.dirname(File.dirname(__FILE__)), 'sequel_core', 'lib')
92
- fixRUBYLIB = Proc.new{ENV['RUBYLIB'] ? (ENV['RUBYLIB'] += ":#{sqcdir}") : (ENV['RUBYLIB'] = sqcdir)}
86
+ lib_dir = File.join(File.dirname(__FILE__), 'lib')
87
+ fixRUBYLIB = Proc.new{ENV['RUBYLIB'] ? (ENV['RUBYLIB'] += ":#{lib_dir}") : (ENV['RUBYLIB'] = lib_dir)}
88
+ sequel_core_specs = "spec/sequel_core/*_spec.rb"
89
+ sequel_model_specs = "spec/sequel_model/*_spec.rb"
90
+ spec_opts = proc{File.read("spec/spec.opts").split("\n")}
91
+ rcov_opts = proc{File.read("spec/rcov.opts").split("\n")}
92
+
93
+ desc "Run core and model specs with coverage"
94
+ Spec::Rake::SpecTask.new("spec_coverage") do |t|
95
+ fixRUBYLIB.call
96
+ t.spec_files = FileList[sequel_core_specs, sequel_model_specs]
97
+ t.spec_opts = spec_opts.call
98
+ t.rcov_opts = rcov_opts.call
99
+ t.rcov = true
100
+ end
93
101
 
94
- desc "Run specs with coverage"
102
+ desc "Run core and model specs"
103
+ task :default => [:spec]
95
104
  Spec::Rake::SpecTask.new("spec") do |t|
96
105
  fixRUBYLIB.call
97
- t.spec_files = FileList["spec/**/*_spec.rb"]
98
- t.spec_opts = File.read("spec/spec.opts").split("\n")
99
- t.rcov_opts = File.read("spec/rcov.opts").split("\n")
100
- t.rcov = true
106
+ t.spec_files = FileList[sequel_core_specs, sequel_model_specs]
107
+ t.spec_opts = spec_opts.call
101
108
  end
102
109
 
103
- desc "Run specs without coverage"
104
- task :default => [:spec_no_cov]
105
- Spec::Rake::SpecTask.new("spec_no_cov") do |t|
110
+ desc "Run core specs"
111
+ Spec::Rake::SpecTask.new("spec_core") do |t|
106
112
  fixRUBYLIB.call
107
- t.spec_files = FileList["spec/**/*_spec.rb"]
108
- t.spec_opts = File.read("spec/spec.opts").split("\n")
113
+ t.spec_files = FileList[sequel_core_specs]
114
+ t.spec_opts = spec_opts.call
115
+ end
116
+
117
+ desc "Run model specs"
118
+ Spec::Rake::SpecTask.new("spec_model") do |t|
119
+ fixRUBYLIB.call
120
+ t.spec_files = FileList[sequel_model_specs]
121
+ t.spec_opts = spec_opts.call
122
+ end
123
+
124
+ desc "Run integration tests"
125
+ Spec::Rake::SpecTask.new("integration") do |t|
126
+ fixRUBYLIB.call
127
+ t.spec_files = FileList["spec/integration/*_test.rb"]
128
+ t.spec_opts = spec_opts.call
129
+ end
130
+
131
+ %w'postgres sqlite mysql informix oracle ado'.each do |adapter|
132
+ desc "Run #{adapter} specs without coverage"
133
+ Spec::Rake::SpecTask.new("spec_#{adapter}") do |t|
134
+ t.spec_files = ["spec/adapters/#{adapter}_spec.rb"]
135
+ t.spec_opts = spec_opts.call
136
+ end
109
137
  end
110
138
 
111
139
  desc "check documentation coverage"
112
140
  task :dcov do
113
- sh "find lib -name '*.rb' | xargs dcov"
141
+ sh %{find lib -name '*.rb' | xargs dcov}
114
142
  end
115
143
 
116
144
  ##############################################################################
@@ -119,12 +147,12 @@ end
119
147
 
120
148
  STATS_DIRECTORIES = [
121
149
  %w(Code lib/),
122
- %w(Spec spec/)
150
+ %w(Spec spec),
123
151
  ].collect { |name, dir| [ name, "./#{dir}" ] }.select { |name, dir| File.directory?(dir) }
124
152
 
125
153
  desc "Report code statistics (KLOCs, etc) from the application"
126
154
  task :stats do
127
- require "../extra/stats"
155
+ require "extra/stats"
128
156
  verbose = true
129
157
  CodeStatistics.new(*STATS_DIRECTORIES).to_s
130
158
  end