constantrecord 0.1.2 → 0.2.0
Sign up to get free protection for your applications and to get access to all the features.
- data/LICENSE +20 -0
- data/README.rdoc +31 -7
- data/Rakefile +42 -13
- data/VERSION +1 -0
- data/constantrecord.gemspec +29 -11
- data/lib/constantrecord.rb +93 -47
- data/test/helper.rb +26 -0
- data/test/{constantrecord_test.rb → test_constantrecord.rb} +38 -3
- metadata +23 -21
- data/Manifest +0 -6
data/LICENSE
ADDED
@@ -0,0 +1,20 @@
|
|
1
|
+
Copyright (c) 2009 Christoph Petschnig
|
2
|
+
|
3
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
4
|
+
a copy of this software and associated documentation files (the
|
5
|
+
"Software"), to deal in the Software without restriction, including
|
6
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
7
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
8
|
+
permit persons to whom the Software is furnished to do so, subject to
|
9
|
+
the following conditions:
|
10
|
+
|
11
|
+
The above copyright notice and this permission notice shall be
|
12
|
+
included in all copies or substantial portions of the Software.
|
13
|
+
|
14
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
15
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
16
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
17
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
18
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
19
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
20
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.rdoc
CHANGED
@@ -1,5 +1,7 @@
|
|
1
1
|
= ConstantRecord
|
2
2
|
|
3
|
+
A tiny ActiveRecord substitute for small, never changing database tables.
|
4
|
+
|
3
5
|
== Usage
|
4
6
|
|
5
7
|
class Currency < ConstantRecord::Base
|
@@ -9,7 +11,7 @@
|
|
9
11
|
or
|
10
12
|
|
11
13
|
class MoreDetailedCurrency < ConstantRecord::Base
|
12
|
-
columns :
|
14
|
+
columns :name, :description
|
13
15
|
data ['EUR', 'Euro'],
|
14
16
|
['USD', 'United States dollar'],
|
15
17
|
['CAD', 'Canadian dollar'],
|
@@ -22,6 +24,7 @@ Inside ActiveRecord, it works just like a "normal" ActiveRecord association:
|
|
22
24
|
|
23
25
|
class Invoice < ActiveRecord::Base
|
24
26
|
belongs_to :currency # via currency_id database column
|
27
|
+
validates_inclusion_of :currency_id, :in => Currency.ids
|
25
28
|
|
26
29
|
def print_currency
|
27
30
|
# Currency#name is the default attribute
|
@@ -39,10 +42,10 @@ In my current application, my main/parent class has about 35 child classes,
|
|
39
42
|
that use over 40 different constant classes. The use of ConstantRecord meant
|
40
43
|
an estimated 15 to 20 per cent speed gain for my application.
|
41
44
|
|
42
|
-
ConstantRecord classes don't need
|
45
|
+
ConstantRecord classes don't need associations:
|
43
46
|
|
44
47
|
class CanadianProvince < ConstantRecord::Base
|
45
|
-
data
|
48
|
+
data 'Alberta', ...
|
46
49
|
has_many :people # is not necessary, will not work
|
47
50
|
end
|
48
51
|
|
@@ -51,8 +54,12 @@ If you want to fetch all people living in Alberta, use:
|
|
51
54
|
Person.find(:all, :conditions =>
|
52
55
|
{:province_id => CanadianProvince.find_by_name('Alberta').id}
|
53
56
|
|
57
|
+
or, in Rails 3:
|
58
|
+
|
59
|
+
Person.where(:province_id => CanadianProvince.find_by_name('Alberta').id)
|
60
|
+
|
54
61
|
If you ever think, ConstantRecord lacks key features of ActiveRecord, (submit
|
55
|
-
a patch or) create the table and derive
|
62
|
+
a patch or) create the table and derive the class from ActiveRecord instead.
|
56
63
|
This is a key design objective for ConstantRecord.
|
57
64
|
|
58
65
|
== Features
|
@@ -64,14 +71,14 @@ When +data+ is a simple Array, #name is the default attribute.
|
|
64
71
|
|
65
72
|
MoreDetailedCurrency.find(3) >> #<MoreDetailedCurrency:0x2c8d94c
|
66
73
|
@description="Canadian Dollar",
|
67
|
-
@id=3, @
|
74
|
+
@id=3, @name="CAD">
|
68
75
|
|
69
76
|
Currency.find_by_name('CHF') >> #<Currency:0x2c86ef8 @id=3, @name="CHF">
|
70
77
|
|
71
|
-
MoreDetailedCurrency.
|
78
|
+
MoreDetailedCurrency.find_by_name('CAD')
|
72
79
|
>> #<MoreDetailedCurrency:0x2c8d94c
|
73
80
|
@description="Canadian Dollar",
|
74
|
-
@id=3, @
|
81
|
+
@id=3, @name="CAD">
|
75
82
|
|
76
83
|
Currency.count :all >> 5
|
77
84
|
|
@@ -85,3 +92,20 @@ ActiveRecord compatible. In a Form you can use:
|
|
85
92
|
or
|
86
93
|
|
87
94
|
<%= f.select :currency_id, Currency.options_for_select(:include_null => true) %>
|
95
|
+
|
96
|
+
If you want to store the name instead of the ID, then you can use:
|
97
|
+
|
98
|
+
<%= f.select :currency_id, Currency.options_for_select(:value => :name) %>
|
99
|
+
|
100
|
+
In this case, you must also change your validation:
|
101
|
+
|
102
|
+
class Invoice < ActiveRecord::Base
|
103
|
+
validates_inclusion_of :currency_id, :in => Currency.names
|
104
|
+
end
|
105
|
+
|
106
|
+
|
107
|
+
== Copyright
|
108
|
+
|
109
|
+
Copyright (c) 2009 Christoph Petschnig. See LICENSE for details.
|
110
|
+
|
111
|
+
Thanks to Till Salzer, Torsten Schönebaum and Nate Wiger for contributions!
|
data/Rakefile
CHANGED
@@ -1,23 +1,52 @@
|
|
1
|
-
# Rakefile for constantrecord
|
2
1
|
require 'rubygems'
|
3
2
|
require 'rake'
|
4
|
-
require 'echoe'
|
5
3
|
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
4
|
+
begin
|
5
|
+
require 'jeweler'
|
6
|
+
Jeweler::Tasks.new do |gem|
|
7
|
+
gem.name = "constantrecord"
|
8
|
+
gem.summary = %Q{A tiny ActiveRecord substitute for small, never changing database tables.}
|
9
|
+
gem.description = %Q{A tiny ActiveRecord substitute for small, never changing database tables.}
|
10
|
+
gem.email = "info@purevirtual.de"
|
11
|
+
gem.homepage = "http://github.com/cpetschnig/constantrecord"
|
12
|
+
gem.authors = ["Christoph Petschnig"]
|
13
|
+
# gem is a Gem::Specification... see http://www.rubygems.org/read/chapter/20 for additional settings
|
14
|
+
end
|
15
|
+
Jeweler::GemcutterTasks.new
|
16
|
+
rescue LoadError
|
17
|
+
puts "Jeweler (or a dependency) not available. Install it with: gem install jeweler"
|
14
18
|
end
|
15
19
|
|
16
|
-
|
20
|
+
require 'rake/testtask'
|
21
|
+
Rake::TestTask.new(:test) do |test|
|
22
|
+
test.libs << 'lib' << 'test'
|
23
|
+
test.pattern = 'test/**/test_*.rb'
|
24
|
+
test.verbose = true
|
25
|
+
end
|
17
26
|
|
27
|
+
begin
|
28
|
+
require 'rcov/rcovtask'
|
29
|
+
Rcov::RcovTask.new do |test|
|
30
|
+
test.libs << 'test'
|
31
|
+
test.pattern = 'test/**/test_*.rb'
|
32
|
+
test.verbose = true
|
33
|
+
end
|
34
|
+
rescue LoadError
|
35
|
+
task :rcov do
|
36
|
+
abort "RCov is not available. In order to run rcov, you must: sudo gem install spicycode-rcov"
|
37
|
+
end
|
38
|
+
end
|
18
39
|
|
19
|
-
task :
|
40
|
+
task :test => :check_dependencies
|
20
41
|
|
21
|
-
|
42
|
+
task :default => :test
|
22
43
|
|
44
|
+
require 'rake/rdoctask'
|
45
|
+
Rake::RDocTask.new do |rdoc|
|
46
|
+
version = File.exist?('VERSION') ? File.read('VERSION') : ""
|
23
47
|
|
48
|
+
rdoc.rdoc_dir = 'rdoc'
|
49
|
+
rdoc.title = "constantrecord #{version}"
|
50
|
+
rdoc.rdoc_files.include('README*')
|
51
|
+
rdoc.rdoc_files.include('lib/**/*.rb')
|
52
|
+
end
|
data/VERSION
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
0.2.0
|
data/constantrecord.gemspec
CHANGED
@@ -1,31 +1,49 @@
|
|
1
|
+
# Generated by jeweler
|
2
|
+
# DO NOT EDIT THIS FILE DIRECTLY
|
3
|
+
# Instead, edit Jeweler::Tasks in Rakefile, and run the gemspec command
|
1
4
|
# -*- encoding: utf-8 -*-
|
2
5
|
|
3
6
|
Gem::Specification.new do |s|
|
4
7
|
s.name = %q{constantrecord}
|
5
|
-
s.version = "0.
|
8
|
+
s.version = "0.2.0"
|
6
9
|
|
7
|
-
s.required_rubygems_version = Gem::Requirement.new(">=
|
10
|
+
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
8
11
|
s.authors = ["Christoph Petschnig"]
|
9
|
-
s.date = %q{2010-
|
12
|
+
s.date = %q{2010-06-29}
|
10
13
|
s.description = %q{A tiny ActiveRecord substitute for small, never changing database tables.}
|
11
14
|
s.email = %q{info@purevirtual.de}
|
12
|
-
s.extra_rdoc_files = [
|
13
|
-
|
14
|
-
|
15
|
-
|
15
|
+
s.extra_rdoc_files = [
|
16
|
+
"LICENSE",
|
17
|
+
"README.rdoc"
|
18
|
+
]
|
19
|
+
s.files = [
|
20
|
+
"LICENSE",
|
21
|
+
"README.rdoc",
|
22
|
+
"Rakefile",
|
23
|
+
"VERSION",
|
24
|
+
"constantrecord.gemspec",
|
25
|
+
"lib/constantrecord.rb",
|
26
|
+
"test/helper.rb",
|
27
|
+
"test/test_constantrecord.rb"
|
28
|
+
]
|
29
|
+
s.homepage = %q{http://github.com/cpetschnig/constantrecord}
|
30
|
+
s.rdoc_options = ["--charset=UTF-8"]
|
16
31
|
s.require_paths = ["lib"]
|
17
|
-
s.
|
18
|
-
s.rubygems_version = %q{1.3.6}
|
32
|
+
s.rubygems_version = %q{1.3.7}
|
19
33
|
s.summary = %q{A tiny ActiveRecord substitute for small, never changing database tables.}
|
20
|
-
s.test_files = [
|
34
|
+
s.test_files = [
|
35
|
+
"test/test_constantrecord.rb",
|
36
|
+
"test/helper.rb"
|
37
|
+
]
|
21
38
|
|
22
39
|
if s.respond_to? :specification_version then
|
23
40
|
current_version = Gem::Specification::CURRENT_SPECIFICATION_VERSION
|
24
41
|
s.specification_version = 3
|
25
42
|
|
26
|
-
if Gem::Version.new(Gem::
|
43
|
+
if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
|
27
44
|
else
|
28
45
|
end
|
29
46
|
else
|
30
47
|
end
|
31
48
|
end
|
49
|
+
|
data/lib/constantrecord.rb
CHANGED
@@ -1,27 +1,8 @@
|
|
1
|
-
#--
|
2
|
-
# Copyright (c) 2009 Christoph Petschnig
|
3
|
-
#
|
4
|
-
# Permission is hereby granted, free of charge, to any person obtaining
|
5
|
-
# a copy of this software and associated documentation files (the
|
6
|
-
# "Software"), to deal in the Software without restriction, including
|
7
|
-
# without limitation the rights to use, copy, modify, merge, publish,
|
8
|
-
# distribute, sublicense, and/or sell copies of the Software, and to
|
9
|
-
# permit persons to whom the Software is furnished to do so, subject to
|
10
|
-
# the following conditions:
|
11
|
-
#
|
12
|
-
# The above copyright notice and this permission notice shall be
|
13
|
-
# included in all copies or substantial portions of the Software.
|
14
|
-
#
|
15
|
-
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
16
|
-
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
17
|
-
# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
18
|
-
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
19
|
-
# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
20
|
-
# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
21
|
-
# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
22
|
-
#++
|
23
|
-
|
24
1
|
module ConstantRecord #:nodoc:
|
2
|
+
|
3
|
+
class ConstantNotFound < StandardError; end #:nodoc:
|
4
|
+
class LoggerError < StandardError; end #:nodoc:
|
5
|
+
|
25
6
|
# ConstantRecord::Base is a tiny ActiveRecord substitute for small, never
|
26
7
|
# changing database tables.
|
27
8
|
#
|
@@ -34,7 +15,7 @@ module ConstantRecord #:nodoc:
|
|
34
15
|
# or
|
35
16
|
#
|
36
17
|
# class MoreDetailedCurrency < ConstantRecord::Base
|
37
|
-
# columns :
|
18
|
+
# columns :name, :description
|
38
19
|
# data ['EUR', 'Euro'],
|
39
20
|
# ['USD', 'US Dollar'],
|
40
21
|
# ['CAD', 'Canadian Dollar'],
|
@@ -59,23 +40,15 @@ module ConstantRecord #:nodoc:
|
|
59
40
|
def self.columns(*args)
|
60
41
|
# remove the default column name
|
61
42
|
undef_method :name
|
43
|
+
class << self
|
44
|
+
undef_method :names
|
45
|
+
end
|
62
46
|
|
63
|
-
|
64
|
-
col_ar = args.collect do |column|
|
65
|
-
raise TypeError.new("You can only pass Symbol or String object to #{self}::columns.") unless column.kind_of?(Symbol) || column.kind_of?(String)
|
66
|
-
|
67
|
-
class_eval do
|
68
|
-
private
|
69
|
-
attr_writer column
|
70
|
-
public
|
71
|
-
attr_reader column
|
72
|
-
end
|
73
|
-
|
74
|
-
i += 1
|
75
|
-
[column.to_sym, i - 1]
|
76
|
-
end.flatten
|
47
|
+
col_ar = build_column_methods(*args)
|
77
48
|
|
78
49
|
@columns = Hash[*col_ar]
|
50
|
+
|
51
|
+
build_array_over_column_methods
|
79
52
|
end
|
80
53
|
|
81
54
|
# Set the data. Arguments must be an Array.
|
@@ -177,7 +150,7 @@ module ConstantRecord #:nodoc:
|
|
177
150
|
# calculate the maximum width of each column
|
178
151
|
max_size = []
|
179
152
|
cols.each do |index, name|
|
180
|
-
woci =
|
153
|
+
woci = width_of_column(index)
|
181
154
|
max_size << (woci > name.to_s.length ? woci : name.to_s.length)
|
182
155
|
end
|
183
156
|
|
@@ -197,14 +170,14 @@ module ConstantRecord #:nodoc:
|
|
197
170
|
|
198
171
|
# Keep this to spot problems in integration with ActiveRecord
|
199
172
|
def method_missing(symbol, *args) #:nodoc:
|
200
|
-
|
173
|
+
self.class.log(:debug, "#{self.class}#method_missing(:#{symbol})")
|
201
174
|
super symbol, *args
|
202
175
|
end
|
203
176
|
|
204
177
|
# Keep this to spot problems in integration with ActiveRecord
|
205
178
|
def respond_to?(symbol) #:nodoc:
|
206
179
|
result = super(symbol)
|
207
|
-
|
180
|
+
self.class.log(:debug, "#{self.class}#respond_to?(:#{symbol}) => #{result}") if !result
|
208
181
|
result
|
209
182
|
end
|
210
183
|
|
@@ -213,14 +186,14 @@ module ConstantRecord #:nodoc:
|
|
213
186
|
if /^find_by_([_a-zA-Z]\w*)$/ =~ (symbol.to_s)
|
214
187
|
return find(:first, :conditions => {$1.to_sym => args[0]})
|
215
188
|
end
|
216
|
-
|
189
|
+
self.log(:debug, "#{self}::method_missing(:#{symbol})")
|
217
190
|
super symbol, *args
|
218
191
|
end
|
219
192
|
|
220
193
|
# Keep this to spot problems in integration with ActiveRecord
|
221
194
|
def self.respond_to?(symbol) #:nodoc:
|
222
195
|
result = super symbol
|
223
|
-
|
196
|
+
self.log(:debug, "#{self}::respond_to?(:#{symbol}) => #{result}") if !result
|
224
197
|
result
|
225
198
|
end
|
226
199
|
|
@@ -234,7 +207,7 @@ module ConstantRecord #:nodoc:
|
|
234
207
|
# With the class:
|
235
208
|
#
|
236
209
|
# class Currency < ConstantRecord::Base
|
237
|
-
# columns :
|
210
|
+
# columns :name, :description
|
238
211
|
# data ['EUR', 'Euro'],
|
239
212
|
# ['USD', 'US Dollar']
|
240
213
|
# end
|
@@ -253,8 +226,8 @@ module ConstantRecord #:nodoc:
|
|
253
226
|
# While:
|
254
227
|
#
|
255
228
|
# <%= f.select :currency_id, Currency.options_for_select(
|
256
|
-
# :display => Proc.new { |obj| "#{obj.
|
257
|
-
# :value => :
|
229
|
+
# :display => Proc.new { |obj| "#{obj.name} (#{obj.description})" },
|
230
|
+
# :value => :name, :include_null => true,
|
258
231
|
# :null_text => 'Please choose one', :null_value => nil ) %>
|
259
232
|
#
|
260
233
|
# Results to:
|
@@ -305,6 +278,32 @@ module ConstantRecord #:nodoc:
|
|
305
278
|
result
|
306
279
|
end
|
307
280
|
|
281
|
+
# Returns an array of the first column of your data. This method will be
|
282
|
+
# removed, if you override your class with +columns+, that do not include
|
283
|
+
# a column called :name
|
284
|
+
def self.names
|
285
|
+
@data.map(&:first)
|
286
|
+
end
|
287
|
+
|
288
|
+
# Returns an array of all ids
|
289
|
+
def self.ids
|
290
|
+
ret = []
|
291
|
+
@data.length.times{|n| ret << n+1}
|
292
|
+
ret
|
293
|
+
end
|
294
|
+
|
295
|
+
# Get the logger
|
296
|
+
def self.logger
|
297
|
+
@@logger
|
298
|
+
end
|
299
|
+
|
300
|
+
# Set the logger; ConstantRecord will try to use the Rails logger, if it's
|
301
|
+
# there. Otherwise an error will be raised; set your own logger by calling
|
302
|
+
# ConstantRecord::Base.logger = MyAwesomeLogger.new
|
303
|
+
def self.logger=(value)
|
304
|
+
@@logger = value
|
305
|
+
end
|
306
|
+
|
308
307
|
private
|
309
308
|
|
310
309
|
# Get the name of the columns or the default value
|
@@ -335,7 +334,7 @@ module ConstantRecord #:nodoc:
|
|
335
334
|
self.new(id, *@data[id - 1])
|
336
335
|
end
|
337
336
|
|
338
|
-
def self.
|
337
|
+
def self.width_of_column(index)
|
339
338
|
return @data.size.to_s.length if index == 0
|
340
339
|
result = 0
|
341
340
|
@data.each do |row|
|
@@ -345,5 +344,52 @@ module ConstantRecord #:nodoc:
|
|
345
344
|
result
|
346
345
|
end
|
347
346
|
|
347
|
+
# Build the attributes for columns;
|
348
|
+
# Returns an array in the form: [[:name_of_column_1, 0], [:name_of_column_2, 1], ...
|
349
|
+
def self.build_column_methods(*args)
|
350
|
+
i = 0
|
351
|
+
args.collect do |column|
|
352
|
+
raise TypeError.new("You can only pass Symbol or String object to #{self}::columns.") unless column.kind_of?(Symbol) || column.kind_of?(String)
|
353
|
+
|
354
|
+
# TODO: warn, if methods already exist!!
|
355
|
+
|
356
|
+
class_eval do
|
357
|
+
private
|
358
|
+
attr_writer column
|
359
|
+
public
|
360
|
+
attr_reader column
|
361
|
+
end
|
362
|
+
|
363
|
+
i += 1
|
364
|
+
[column.to_sym, i - 1]
|
365
|
+
end.flatten
|
366
|
+
end
|
367
|
+
|
368
|
+
# Create a class method for every column;
|
369
|
+
# class UsState with columns :name, :short_form will give you the methods
|
370
|
+
# :names and :short_forms, which will return an array of their column values
|
371
|
+
def self.build_array_over_column_methods
|
372
|
+
@columns.each do |column, column_index|
|
373
|
+
# try to use (most likely) ActiveSupport inflections, if possible
|
374
|
+
pluralized_name = if String.new.respond_to? :pluralize
|
375
|
+
column.to_s.pluralize
|
376
|
+
else
|
377
|
+
"#{column}s" # better than nothing
|
378
|
+
end
|
379
|
+
|
380
|
+
if self.class.method_defined?(pluralized_name)
|
381
|
+
self.log :warn, "Warning!!! Method #{self}##{pluralized_name} is already defined. Consider using a different column name!"
|
382
|
+
end
|
383
|
+
|
384
|
+
class_eval "def self.#{pluralized_name}; @data.map{|obj| obj[#{column_index}]}; end"
|
385
|
+
end
|
386
|
+
end
|
387
|
+
|
388
|
+
def self.log(level, msg)
|
389
|
+
@@logger ||= Rails.logger if defined?(Rails) # TODO: take a more generic approach; at least try to include Sinatra, Padrino loggers or the Rack logger
|
390
|
+
raise LoggerError unless @@logger && @@logger.respond_to?(level)
|
391
|
+
@@logger.send(level, msg)
|
392
|
+
end
|
393
|
+
|
348
394
|
end
|
349
395
|
end
|
data/test/helper.rb
ADDED
@@ -0,0 +1,26 @@
|
|
1
|
+
require 'rubygems'
|
2
|
+
require 'test/unit'
|
3
|
+
|
4
|
+
$LOAD_PATH.unshift(File.dirname(__FILE__))
|
5
|
+
$LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
|
6
|
+
require 'constantrecord'
|
7
|
+
|
8
|
+
class Test::Unit::TestCase
|
9
|
+
end
|
10
|
+
|
11
|
+
# simply count, how often each log type gets called
|
12
|
+
class MyTestLogger
|
13
|
+
TYPES = %w{debug info warn error fatal}
|
14
|
+
def initialize
|
15
|
+
TYPES.each{|type|instance_variable_set "@#{type}_count", 0}
|
16
|
+
end
|
17
|
+
TYPES.each do |type|
|
18
|
+
attr_reader "#{type}_count"
|
19
|
+
eval "def #{type}(*args); @#{type}_count += 1; end"
|
20
|
+
#eval "def #{type}(*args); puts *args; @#{type}_count += 1; end" # print out log messages for better debugging!
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
|
25
|
+
ConstantRecord::Base.logger = MyTestLogger.new
|
26
|
+
|
@@ -1,5 +1,4 @@
|
|
1
|
-
require '
|
2
|
-
require 'test/unit'
|
1
|
+
require 'helper'
|
3
2
|
|
4
3
|
class SimpleClass < ConstantRecord::Base
|
5
4
|
data 'Lithuania', 'Latvia', 'Estonia'
|
@@ -28,6 +27,18 @@ class MultiColumnClassNotString < ConstantRecord::Base
|
|
28
27
|
[19, false]
|
29
28
|
end
|
30
29
|
|
30
|
+
class ForValidation < ConstantRecord::Base
|
31
|
+
columns :name, :value
|
32
|
+
data ['normal', 1],
|
33
|
+
['gift', 2],
|
34
|
+
['friend', 3]
|
35
|
+
end
|
36
|
+
|
37
|
+
class BadColumnNames < ConstantRecord::Base
|
38
|
+
# columns :instance_method, :class_variable
|
39
|
+
# data ['foo', 'bar']
|
40
|
+
end
|
41
|
+
|
31
42
|
class TestConstantRecord < Test::Unit::TestCase
|
32
43
|
def test_simple_finder
|
33
44
|
assert_equal 'Estonia', SimpleClass.find(3).name
|
@@ -54,6 +65,7 @@ class TestConstantRecord < Test::Unit::TestCase
|
|
54
65
|
assert_equal 'Sgt. Pepper', SimpleClass2.find_by_album('Sgt. Pepper').album
|
55
66
|
assert_equal 1, SimpleClass2.find_by_album('Sgt. Pepper').id
|
56
67
|
assert_raise (RuntimeError) { SimpleClass2.find_by_name('Sgt. Pepper') }
|
68
|
+
assert_raise (NoMethodError) { SimpleClass2.find(1).name }
|
57
69
|
assert_equal [ 'Sgt. Pepper', 'Magical Mystery Tour', 'Abbey Road' ], SimpleClass2.find(:all).collect{|o| o.album}
|
58
70
|
assert_equal [ 1, 2, 3 ], SimpleClass2.find(:all).collect{|o| o.id}
|
59
71
|
assert_equal 3, SimpleClass2.count
|
@@ -102,4 +114,27 @@ class TestConstantRecord < Test::Unit::TestCase
|
|
102
114
|
def test_all_shortcut
|
103
115
|
assert_equal SimpleClass.find(:all).collect{|o| o.name}, SimpleClass.all.collect{|o| o.name}
|
104
116
|
end
|
105
|
-
|
117
|
+
|
118
|
+
def test_validation_methods
|
119
|
+
# validates_inclusion_of :thingy, :in => ForValidation.names
|
120
|
+
assert_equal ['normal','gift','friend'], ForValidation.names
|
121
|
+
assert_equal [1,2,3], ForValidation.values
|
122
|
+
assert_equal [1,2,3,4,5], MultiColumnClass.ids
|
123
|
+
assert_equal ['Sgt. Pepper', 'Magical Mystery Tour', 'Abbey Road'], SimpleClass2.albums
|
124
|
+
assert_equal %w{EUR USD CAD GBP CHF}, MultiColumnClass.shorts
|
125
|
+
assert_raise (NoMethodError) { MultiColumnClass.names }
|
126
|
+
assert_raise (NoMethodError) { MultiColumnClass.values }
|
127
|
+
end
|
128
|
+
|
129
|
+
def test_logger
|
130
|
+
assert_nothing_raised { ConstantRecord::Base.logger = MyTestLogger.new }
|
131
|
+
assert_nothing_raised { SimpleClass.respond_to?(:asdfghjkl) }
|
132
|
+
assert_nothing_raised { MultiColumnClass.find(1).respond_to?(:asdfghjkl) }
|
133
|
+
end
|
134
|
+
|
135
|
+
def test_bad_colum_names
|
136
|
+
warnings_count = ConstantRecord::Base.logger.warn_count
|
137
|
+
BadColumnNames.columns :instance_method, :class_variable # must log 2 warnings
|
138
|
+
assert_equal ConstantRecord::Base.logger.warn_count - warnings_count, 2
|
139
|
+
end
|
140
|
+
end
|
metadata
CHANGED
@@ -1,12 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: constantrecord
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
+
hash: 23
|
4
5
|
prerelease: false
|
5
6
|
segments:
|
6
7
|
- 0
|
7
|
-
- 1
|
8
8
|
- 2
|
9
|
-
|
9
|
+
- 0
|
10
|
+
version: 0.2.0
|
10
11
|
platform: ruby
|
11
12
|
authors:
|
12
13
|
- Christoph Petschnig
|
@@ -14,7 +15,7 @@ autorequire:
|
|
14
15
|
bindir: bin
|
15
16
|
cert_chain: []
|
16
17
|
|
17
|
-
date: 2010-
|
18
|
+
date: 2010-06-29 00:00:00 +02:00
|
18
19
|
default_executable:
|
19
20
|
dependencies: []
|
20
21
|
|
@@ -25,50 +26,51 @@ executables: []
|
|
25
26
|
extensions: []
|
26
27
|
|
27
28
|
extra_rdoc_files:
|
28
|
-
-
|
29
|
+
- LICENSE
|
29
30
|
- README.rdoc
|
30
31
|
files:
|
32
|
+
- LICENSE
|
33
|
+
- README.rdoc
|
34
|
+
- Rakefile
|
35
|
+
- VERSION
|
31
36
|
- constantrecord.gemspec
|
32
37
|
- lib/constantrecord.rb
|
33
|
-
- test/
|
34
|
-
-
|
35
|
-
- Rakefile
|
36
|
-
- README.rdoc
|
38
|
+
- test/helper.rb
|
39
|
+
- test/test_constantrecord.rb
|
37
40
|
has_rdoc: true
|
38
|
-
homepage: http://github.com/
|
41
|
+
homepage: http://github.com/cpetschnig/constantrecord
|
39
42
|
licenses: []
|
40
43
|
|
41
44
|
post_install_message:
|
42
45
|
rdoc_options:
|
43
|
-
- --
|
44
|
-
- --inline-source
|
45
|
-
- --title
|
46
|
-
- Constantrecord
|
47
|
-
- --main
|
48
|
-
- README.rdoc
|
46
|
+
- --charset=UTF-8
|
49
47
|
require_paths:
|
50
48
|
- lib
|
51
49
|
required_ruby_version: !ruby/object:Gem::Requirement
|
50
|
+
none: false
|
52
51
|
requirements:
|
53
52
|
- - ">="
|
54
53
|
- !ruby/object:Gem::Version
|
54
|
+
hash: 3
|
55
55
|
segments:
|
56
56
|
- 0
|
57
57
|
version: "0"
|
58
58
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
59
|
+
none: false
|
59
60
|
requirements:
|
60
61
|
- - ">="
|
61
62
|
- !ruby/object:Gem::Version
|
63
|
+
hash: 3
|
62
64
|
segments:
|
63
|
-
-
|
64
|
-
|
65
|
-
version: "1.2"
|
65
|
+
- 0
|
66
|
+
version: "0"
|
66
67
|
requirements: []
|
67
68
|
|
68
|
-
rubyforge_project:
|
69
|
-
rubygems_version: 1.3.
|
69
|
+
rubyforge_project:
|
70
|
+
rubygems_version: 1.3.7
|
70
71
|
signing_key:
|
71
72
|
specification_version: 3
|
72
73
|
summary: A tiny ActiveRecord substitute for small, never changing database tables.
|
73
74
|
test_files:
|
74
|
-
- test/
|
75
|
+
- test/test_constantrecord.rb
|
76
|
+
- test/helper.rb
|