extlib 0.9.13 → 0.9.14

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of extlib might be problematic. Click here for more details.

@@ -115,7 +115,7 @@ class Hash
115
115
  # @param [Object] key The key for the param.
116
116
  # @param [Object] value The value for the param.
117
117
  #
118
- # @return <String> This key value pair as a param
118
+ # @return [String] This key value pair as a param
119
119
  #
120
120
  # @api public
121
121
  def normalize_param(key, value)
@@ -176,7 +176,7 @@ class Hash
176
176
  hash
177
177
  end
178
178
 
179
- # @return <String> The hash as attributes for an XML tag.
179
+ # @return [String] The hash as attributes for an XML tag.
180
180
  #
181
181
  # @example
182
182
  # { :one => 1, "two"=>"TWO" }.to_xml_attributes
@@ -209,7 +209,7 @@ class Hash
209
209
  # Converts all keys into string values. This is used during reloading to
210
210
  # prevent problems when classes are no longer declared.
211
211
  #
212
- # @return <Array> An array of they hash's keys
212
+ # @return [Array] An array of they hash's keys
213
213
  #
214
214
  # @example
215
215
  # hash = { One => 1, Two => 2 }.proctect_keys!
@@ -234,7 +234,7 @@ class Hash
234
234
  # Destructively and non-recursively convert each key to an uppercase string,
235
235
  # deleting nil values along the way.
236
236
  #
237
- # @return <Hash> The newly environmentized hash.
237
+ # @return [Hash] The newly environmentized hash.
238
238
  #
239
239
  # @example
240
240
  # { :name => "Bob", :contact => { :email => "bob@bob.com" } }.environmentize_keys!
@@ -361,7 +361,7 @@ class REXMLUtilityNode
361
361
  # "date"::
362
362
  # Parses +value+ using Date.parse
363
363
  #
364
- # @return <Integer, TrueClass, FalseClass, Time, Date, Object>
364
+ # @return [Integer, Boolean, Time, Date, Object]
365
365
  # The result of typecasting +value+.
366
366
  #
367
367
  # @note
@@ -377,7 +377,7 @@ class REXMLUtilityNode
377
377
  #
378
378
  # @param value<#gsub> An XML fragment.
379
379
  #
380
- # @return <#gsub> The XML fragment after converting entities.
380
+ # @return [#gsub] The XML fragment after converting entities.
381
381
  def translate_xml_entities(value)
382
382
  value.gsub(/&lt;/, "<").
383
383
  gsub(/&gt;/, ">").
@@ -401,7 +401,7 @@ class REXMLUtilityNode
401
401
 
402
402
  # Converts the node into a readable HTML node.
403
403
  #
404
- # @return <String> The HTML node in text form.
404
+ # @return [String] The HTML node in text form.
405
405
  def to_html
406
406
  attributes.merge!(:type => @type ) if @type
407
407
  "<#{name}#{attributes.to_xml_attributes}>#{@nil_element ? '' : inner_html}</#{name}>"
@@ -10,10 +10,13 @@ module Extlib
10
10
  #
11
11
  # @example
12
12
  # "egg_and_hams".classify #=> "EggAndHam"
13
+ # "enlarged_testes".classify #=> "EnlargedTestis"
13
14
  # "post".classify #=> "Post"
14
15
  #
15
16
  def classify(name)
16
- camelize(singularize(name.to_s.sub(/.*\./, '')))
17
+ words = name.to_s.sub(/.*\./, '').split('_')
18
+ words[-1] = singularize(words[-1])
19
+ words.collect { |word| word.capitalize }.join
17
20
  end
18
21
 
19
22
  # By default, camelize converts strings to UpperCamelCase.
@@ -48,7 +51,7 @@ module Extlib
48
51
  # "employee_salary" #=> "Employee salary"
49
52
  # "author_id" #=> "Author"
50
53
  def humanize(lower_case_and_underscored_word)
51
- lower_case_and_underscored_word.to_s.gsub(/_id$/, "").gsub(/_/, " ").capitalize
54
+ lower_case_and_underscored_word.to_s.gsub(/_id$/, '').tr('_', ' ').capitalize
52
55
  end
53
56
 
54
57
  # Removes the module part from the expression in the string
@@ -65,10 +68,13 @@ module Extlib
65
68
  #
66
69
  # @example
67
70
  # "RawScaledScorer".tableize #=> "raw_scaled_scorers"
71
+ # "EnlargedTestis".tableize #=> "enlarged_testes"
68
72
  # "egg_and_ham".tableize #=> "egg_and_hams"
69
73
  # "fancyCategory".tableize #=> "fancy_categories"
70
74
  def tableize(class_name)
71
- pluralize(class_name.to_const_path.gsub(/\//, '_'))
75
+ words = class_name.to_const_path.tr('/', '_').split('_')
76
+ words[-1] = pluralize(words[-1])
77
+ words.join('_')
72
78
  end
73
79
 
74
80
  # Creates a foreign key name from a class name.
@@ -253,7 +259,7 @@ module Extlib
253
259
 
254
260
  attr_reader :singular_of, :plural_of
255
261
 
256
- # Convert an English word from plurel to singular.
262
+ # Convert an English word from plural to singular.
257
263
  #
258
264
  # "boys".singular #=> boy
259
265
  # "tomatoes".singular #=> tomato
@@ -281,7 +287,7 @@ module Extlib
281
287
  #
282
288
  alias_method(:singularize, :singular)
283
289
 
284
- # Convert an English word from singular to plurel.
290
+ # Convert an English word from singular to plural.
285
291
  #
286
292
  # "boy".plural #=> boys
287
293
  # "tomato".plural #=> tomatoes
@@ -1,5 +1,5 @@
1
1
  class LazyArray # borrowed partially from StrokeDB
2
- instance_methods.each { |m| undef_method m unless %w[ __id__ __send__ send class dup object_id kind_of? respond_to? equal? assert_kind_of should should_not instance_variable_set instance_variable_get extend ].include?(m.to_s) }
2
+ include Enumerable
3
3
 
4
4
  attr_reader :head, :tail
5
5
 
@@ -82,7 +82,11 @@ class LazyArray # borrowed partially from StrokeDB
82
82
  end
83
83
 
84
84
  def empty?
85
- !any?
85
+ (@tail.nil? || @tail.empty?) &&
86
+ (@head.nil? || @head.empty?) && begin
87
+ lazy_load
88
+ @array.empty?
89
+ end
86
90
  end
87
91
 
88
92
  def any?(&block)
@@ -214,21 +218,21 @@ class LazyArray # borrowed partially from StrokeDB
214
218
  self
215
219
  end
216
220
 
217
- def pop
218
- if lazy_possible?(@tail)
219
- @tail.pop
221
+ def pop(*args)
222
+ if lazy_possible?(@tail, *args)
223
+ @tail.pop(*args)
220
224
  else
221
225
  lazy_load
222
- @array.pop
226
+ @array.pop(*args)
223
227
  end
224
228
  end
225
229
 
226
- def shift
227
- if lazy_possible?(@head)
228
- @head.shift
230
+ def shift(*args)
231
+ if lazy_possible?(@head, *args)
232
+ @head.shift(*args)
229
233
  else
230
234
  lazy_load
231
- @array.shift
235
+ @array.shift(*args)
232
236
  end
233
237
  end
234
238
 
@@ -401,6 +405,16 @@ class LazyArray # borrowed partially from StrokeDB
401
405
  raise ArgumentError, "arguments may be 1 or 2 Integers, or 1 Range object, was: #{args.inspect}", caller(1)
402
406
  end
403
407
 
408
+ def each
409
+ lazy_load
410
+ if block_given?
411
+ @array.each { |entry| yield entry }
412
+ self
413
+ else
414
+ @array.each
415
+ end
416
+ end
417
+
404
418
  # delegate any not-explicitly-handled methods to @array, if possible.
405
419
  # this is handy for handling methods mixed-into Array like group_by
406
420
  def method_missing(method, *args, &block)
@@ -419,14 +433,14 @@ class LazyArray # borrowed partially from StrokeDB
419
433
  # 0 and incrementally compare each entry. if other is a LazyArray
420
434
  # this has a lesser likelyhood of triggering a lazy load
421
435
  0.upto(@head.size - 1) do |i|
422
- return false unless @head[i].send(operator, other[i])
436
+ return false unless @head[i].__send__(operator, other[i])
423
437
  end
424
438
 
425
439
  # compare the tail against the end of other. start at index
426
440
  # -1 and decrementally compare each entry. if other is a LazyArray
427
441
  # this has a lesser likelyhood of triggering a lazy load
428
442
  -1.downto(@tail.size * -1) do |i|
429
- return false unless @tail[i].send(operator, other[i])
443
+ return false unless @tail[i].__send__(operator, other[i])
430
444
  end
431
445
 
432
446
  lazy_load
@@ -434,24 +448,4 @@ class LazyArray # borrowed partially from StrokeDB
434
448
 
435
449
  @array.send(operator, other.to_ary)
436
450
  end
437
-
438
- # add proxies for all remaining Array and Enumerable methods
439
- (Array.public_instance_methods(false) | Enumerable.public_instance_methods(false)).each do |method|
440
- next if public_method_defined?(method)
441
-
442
- target = if method.to_s[-1, 1] == '='
443
- "send(:#{method}, *args, &block)"
444
- else
445
- "#{method}(*args, &block)"
446
- end
447
-
448
- class_eval <<-RUBY, __FILE__, __LINE__ + 1
449
- public
450
- def #{method}(*args, &block) # def []=(*args, &block)
451
- lazy_load # lazy_load
452
- results = @array.#{target} # results = @array.send(:[]=, *args, &block)
453
- results.equal?(@array) ? self : results # results.equal?(@array) ? self : results
454
- end # end
455
- RUBY
456
- end
457
451
  end
@@ -47,7 +47,7 @@ class Mash < Hash
47
47
  # A hash to update values in the mash with. The keys and the values will be
48
48
  # converted to Mash format.
49
49
  #
50
- # @return <Mash> The updated mash.
50
+ # @return [Mash] The updated mash.
51
51
  def update(other_hash)
52
52
  other_hash.each_pair { |key, value| regular_writer(convert_key(key), convert_value(value)) }
53
53
  self
@@ -57,7 +57,7 @@ class Mash < Hash
57
57
 
58
58
  # @param key<Object> The key to check for. This will be run through convert_key.
59
59
  #
60
- # @return <TrueClass, FalseClass> True if the key exists in the mash.
60
+ # @return [Boolean] True if the key exists in the mash.
61
61
  def key?(key)
62
62
  super(convert_key(key))
63
63
  end
@@ -70,7 +70,7 @@ class Mash < Hash
70
70
  # @param key<Object> The key to fetch. This will be run through convert_key.
71
71
  # @param *extras<Array> Default value.
72
72
  #
73
- # @return <Object> The value at key or the default value.
73
+ # @return [Object] The value at key or the default value.
74
74
  def fetch(key, *extras)
75
75
  super(convert_key(key), *extras)
76
76
  end
@@ -78,14 +78,14 @@ class Mash < Hash
78
78
  # @param *indices<Array>
79
79
  # The keys to retrieve values for. These will be run through +convert_key+.
80
80
  #
81
- # @return <Array> The values at each of the provided keys
81
+ # @return [Array] The values at each of the provided keys
82
82
  def values_at(*indices)
83
83
  indices.collect {|key| self[convert_key(key)]}
84
84
  end
85
85
 
86
86
  # @param hash<Hash> The hash to merge with the mash.
87
87
  #
88
- # @return <Mash> A new mash with the hash values merged in.
88
+ # @return [Mash] A new mash with the hash values merged in.
89
89
  def merge(hash)
90
90
  self.dup.update(hash)
91
91
  end
@@ -98,7 +98,7 @@ class Mash < Hash
98
98
 
99
99
  # @param *rejected<Array[(String, Symbol)] The mash keys to exclude.
100
100
  #
101
- # @return <Mash> A new mash without the selected keys.
101
+ # @return [Mash] A new mash without the selected keys.
102
102
  #
103
103
  # @example
104
104
  # { :one => 1, :two => 2, :three => 3 }.except(:one)
@@ -109,17 +109,17 @@ class Mash < Hash
109
109
 
110
110
  # Used to provide the same interface as Hash.
111
111
  #
112
- # @return <Mash> This mash unchanged.
112
+ # @return [Mash] This mash unchanged.
113
113
  def stringify_keys!; self end
114
114
 
115
- # @return <Hash> The mash as a Hash with symbolized keys.
115
+ # @return [Hash] The mash as a Hash with symbolized keys.
116
116
  def symbolize_keys
117
117
  h = Hash.new(default)
118
118
  each { |key, val| h[key.to_sym] = val }
119
119
  h
120
120
  end
121
121
 
122
- # @return <Hash> The mash as a Hash with string keys.
122
+ # @return [Hash] The mash as a Hash with string keys.
123
123
  def to_hash
124
124
  Hash.new(default).merge(self)
125
125
  end
@@ -127,7 +127,7 @@ class Mash < Hash
127
127
  protected
128
128
  # @param key<Object> The key to convert.
129
129
  #
130
- # @param <Object>
130
+ # @param [Object]
131
131
  # The converted key. If the key was a symbol, it will be converted to a
132
132
  # string.
133
133
  #
@@ -138,7 +138,7 @@ class Mash < Hash
138
138
 
139
139
  # @param value<Object> The value to convert.
140
140
  #
141
- # @return <Object>
141
+ # @return [Object]
142
142
  # The converted value. A Hash or an Array of hashes, will be converted to
143
143
  # their Mash equivalents.
144
144
  #
@@ -1,7 +1,7 @@
1
1
  class Object
2
2
  # Extracts the singleton class, so that metaprogramming can be done on it.
3
3
  #
4
- # @return <Class> The meta class.
4
+ # @return [Class] The meta class.
5
5
  #
6
6
  # @example [Setup]
7
7
  # class MyString < String; end
@@ -60,7 +60,7 @@ class Object
60
60
 
61
61
  # @param name<String> The name of the constant to get, e.g. "Merb::Router".
62
62
  #
63
- # @return <Object> The constant corresponding to the name.
63
+ # @return [Object] The constant corresponding to the name.
64
64
  def full_const_get(name)
65
65
  list = name.split("::")
66
66
  list.shift if list.first.blank?
@@ -76,7 +76,7 @@ class Object
76
76
  # @param name<String> The name of the constant to get, e.g. "Merb::Router".
77
77
  # @param value<Object> The value to assign to the constant.
78
78
  #
79
- # @return <Object> The constant corresponding to the name.
79
+ # @return [Object] The constant corresponding to the name.
80
80
  def full_const_set(name, value)
81
81
  list = name.split("::")
82
82
  toplevel = list.first.blank?
@@ -91,7 +91,7 @@ class Object
91
91
  #
92
92
  # @param name<String> The name of the full module name to make
93
93
  #
94
- # @return <NilClass>
94
+ # @return [nil]
95
95
  def make_module(str)
96
96
  mod = str.split("::")
97
97
  current_module = self
@@ -114,7 +114,7 @@ class Object
114
114
  # Check whether the object quacks_like? at least one of the options in the
115
115
  # array.
116
116
  #
117
- # @return <TrueClass, FalseClass>
117
+ # @return [Boolean]
118
118
  # True if the object quacks like duck.
119
119
  def quacks_like?(duck)
120
120
  case duck
@@ -131,7 +131,7 @@ class Object
131
131
 
132
132
  # Override this in a child if it cannot be dup'ed
133
133
  #
134
- # @return <Object>
134
+ # @return [Object]
135
135
  def try_dup
136
136
  self.dup
137
137
  end
@@ -140,7 +140,7 @@ class Object
140
140
  # returns result. If not, just returns receiver
141
141
  # itself
142
142
  #
143
- # @return <Object>
143
+ # @return [Object]
144
144
  def try_call(*args)
145
145
  if self.respond_to?(:call)
146
146
  self.call(*args)
@@ -152,7 +152,7 @@ class Object
152
152
  # @param arrayish<#include?> Container to check, to see if it includes the object.
153
153
  # @param *more<Array>:: additional args, will be flattened into arrayish
154
154
  #
155
- # @return <TrueClass, FalseClass>
155
+ # @return [Boolean]
156
156
  # True if the object is included in arrayish (+ more)
157
157
  #
158
158
  # @example 1.in?([1,2,3]) #=> true
@@ -165,7 +165,7 @@ class Object
165
165
  # Add instance_variable_defined? for backward compatibility
166
166
  # @param variable<Symbol, String>
167
167
  #
168
- # @return <TrueClass, FalseClass>
168
+ # @return [Boolean]
169
169
  # True if the object has the given instance variable defined
170
170
  unless respond_to?(:instance_variable_defined?)
171
171
  def instance_variable_defined?(variable)
@@ -2,7 +2,7 @@ module ObjectSpace
2
2
 
3
3
  class << self
4
4
 
5
- # @return <Array[Class]> All the classes in the object space.
5
+ # @return [Array<Class>] All the classes in the object space.
6
6
  def classes
7
7
  klasses = []
8
8
  ObjectSpace.each_object(Class) {|o| klasses << o}
@@ -30,7 +30,7 @@ module Gem
30
30
  # from any other location. If there are two gems of different versions in
31
31
  # the gems directory, the later one will load as usual.
32
32
  #
33
- # @return <Array[Array]> The object used for sorting gem specs.
33
+ # @return [Array<Array>] The object used for sorting gem specs.
34
34
  def sort_obj
35
35
  [@name, installation_path == File.join(defined?(Merb) && Merb.respond_to?(:root) ? Merb.root : Dir.pwd,"gems") ? 1 : -1, @version.to_ints, @new_platform == Gem::Platform::RUBY ? -1 : 1]
36
36
  end
@@ -36,9 +36,10 @@ class String
36
36
  #
37
37
  # @api public
38
38
  def snake_case
39
- return self.downcase if self =~ /^[A-Z]+$/
40
- self.gsub(/([A-Z]+)(?=[A-Z][a-z]?)|\B[A-Z]/, '_\&') =~ /_*(.*)/
41
- return $+.downcase
39
+ return downcase if match(/\A[A-Z]+\z/)
40
+ gsub(/([A-Z]+)([A-Z][a-z])/, '\1_\2').
41
+ gsub(/([a-z])([A-Z])/, '\1_\2').
42
+ downcase
42
43
  end
43
44
 
44
45
  ##
@@ -2,10 +2,14 @@ require File.expand_path(File.join(File.dirname(__FILE__), 'spec_helper'))
2
2
 
3
3
  describe Extlib::Inflection do
4
4
  describe "#classify" do
5
- it 'classifies data_mapper as DataMaper' do
5
+ it 'classifies data_mapper as DataMapper' do
6
6
  Extlib::Inflection.classify('data_mapper').should == 'DataMapper'
7
7
  end
8
8
 
9
+ it "classifies enlarged_testes as EnlargedTestis" do
10
+ Extlib::Inflection.classify('enlarged_testes').should == 'EnlargedTestis'
11
+ end
12
+
9
13
  it "singularizes string first: classifies data_mappers as egg_and_hams as EggAndHam" do
10
14
  Extlib::Inflection.classify('egg_and_hams').should == 'EggAndHam'
11
15
  end
@@ -72,13 +76,26 @@ describe Extlib::Inflection do
72
76
  Extlib::Inflection.tableize('fancy_category').should == 'fancy_categories'
73
77
  end
74
78
 
79
+ it 'underscores CamelCase strings before pluralization: enlarged_testis => enlarged_testes' do
80
+ Extlib::Inflection.tableize('enlarged_testis').should == 'enlarged_testes'
81
+ end
82
+
75
83
  it 'underscores CamelCase strings before pluralization: FancyCategory => fancy_categories' do
76
84
  Extlib::Inflection.tableize('FancyCategory').should == 'fancy_categories'
77
85
  end
78
86
 
87
+ it 'underscores CamelCase strings before pluralization: EnlargedTestis => enlarged_testes' do
88
+ Extlib::Inflection.tableize('EnlargedTestis').should == 'enlarged_testes'
89
+ end
90
+
79
91
  it 'replaces :: with underscores: Fancy::Category => fancy_categories' do
80
92
  Extlib::Inflection.tableize('Fancy::Category').should == 'fancy_categories'
81
93
  end
94
+
95
+ it 'underscores CamelCase strings before pluralization: Enlarged::Testis => enlarged_testes' do
96
+ Extlib::Inflection.tableize('Enlarged::Testis').should == 'enlarged_testes'
97
+ end
98
+
82
99
  end
83
100
 
84
101
  describe "#foreign_key" do