mack-facets 0.6.0

Sign up to get free protection for your applications and to get access to all the features.
data/README ADDED
@@ -0,0 +1,3 @@
1
+ README
2
+ ========================================================================
3
+ mack-facets was developed by: markbates
@@ -0,0 +1,50 @@
1
+ module English # :nodoc:
2
+
3
+ # = English Nouns Number Inflection.
4
+ #
5
+ # This module provides english singular <-> plural noun inflections.
6
+ module Inflect # :nodoc:
7
+
8
+ class << self
9
+
10
+ # Convert an English word from plurel to singular.
11
+ #
12
+ # "boys".singular #=> boy
13
+ # "tomatoes".singular #=> tomato
14
+ #
15
+ def singular(word)
16
+ if result = singular_of[word]
17
+ return result.dup
18
+ end
19
+ result = word.dup
20
+ singularization_rules.each do |(match, replacement)|
21
+ break if result.gsub!(match, replacement)
22
+ end
23
+ # Mack: cache the result of the translation:
24
+ singular_of[word] = result unless word == result
25
+ return result
26
+ end
27
+
28
+ # Convert an English word from singular to plurel.
29
+ #
30
+ # "boy".plural #=> boys
31
+ # "tomato".plural #=> tomatoes
32
+ #
33
+ def plural(word)
34
+ if result = plural_of[word]
35
+ return result.dup
36
+ end
37
+ #return self.dup if /s$/ =~ self # ???
38
+ result = word.dup
39
+ pluralization_rules.each do |(match, replacement)|
40
+ break if result.gsub!(match, replacement)
41
+ end
42
+ # Mack: cache the result of the translation:
43
+ plural_of[word] = result unless word == result
44
+ return result
45
+ end
46
+
47
+ end
48
+
49
+ end
50
+ end
@@ -0,0 +1,12 @@
1
+ class Integer #:nodoc:
2
+
3
+ #
4
+ # 10.english #=> 'ten'
5
+
6
+ include English::Numerals
7
+
8
+ def english
9
+ self.name(self)
10
+ end
11
+
12
+ end
@@ -0,0 +1,90 @@
1
+ class Array
2
+
3
+ # This method is useful when you have a method that looks like this:
4
+ # def foo(*args)
5
+ # do something
6
+ # end
7
+ # The problem is when you use the * like that everything that comes in is
8
+ # an array. Here are a few problems with this:
9
+ # foo([1,2,3])
10
+ # When you pass an array into this type of method you get the following nested array:
11
+ # [[1,2,3]]
12
+ # The parse_splat_args method, if called, would do this:
13
+ # args.parse_splat_args # => [1,2,3]
14
+ # Now say you called this method like such:
15
+ # foo(1)
16
+ # args would be [1]
17
+ # args.parse_splat_args # => 1
18
+ # Finally
19
+ # foo
20
+ # args.parse_splat_args # => nil
21
+ def parse_splat_args
22
+ unless self.empty?
23
+ args = self#.flatten
24
+ case args.size
25
+ when 1
26
+ return args.first # if there was only one arg passed, return just that, without the array
27
+ when 0
28
+ return nil # if no args were passed return nil
29
+ else
30
+ return args # else return the array back, cause chances are that's what they passed you!
31
+ end
32
+ end
33
+ end
34
+
35
+ # This will return a new instance of the array sorted randomly.
36
+ def randomize(&block)
37
+ if block_given?
38
+ self.sort {|x,y| yield x, y}
39
+ else
40
+ self.sort_by { rand }
41
+ end
42
+ end
43
+
44
+ # This calls the randomize method, but will permantly replace the existing array.
45
+ def randomize!(&block)
46
+ if block_given?
47
+ self.replace(self.randomize(&block))
48
+ else
49
+ self.replace(self.randomize)
50
+ end
51
+ end
52
+
53
+ # This will pick a random value from the array
54
+ def pick_random
55
+ self[rand(self.length)]
56
+ end
57
+
58
+ # This allows you to easily recurse of the array randomly.
59
+ def random_each
60
+ self.randomize.each {|x| yield x}
61
+ end
62
+
63
+ def subset?(other)
64
+ self.each do |x|
65
+ return false if !(other.include? x)
66
+ end
67
+ true
68
+ end
69
+
70
+ def superset?(other)
71
+ other.subset?(self)
72
+ end
73
+
74
+ # This will give you a count, as a Hash, of all the values in the Array.
75
+ # %w{spam spam eggs ham eggs spam}.count # => {"eggs" => 2, "ham" => 1, "spam" => 3}
76
+ def count
77
+ k = Hash.new(0)
78
+ self.each{|x| k[x] += 1}
79
+ k
80
+ end
81
+
82
+ # This will invert the index and the values and return a Hash of the results.
83
+ # %w{red yellow orange}.invert # => {"red" => 0, "orange" => 2, "yellow" => 1}
84
+ def invert
85
+ h = {}
86
+ self.each_with_index{|x,i| h[x] = i}
87
+ h
88
+ end
89
+
90
+ end
@@ -0,0 +1,38 @@
1
+ class Class
2
+
3
+ # Returns a new Object instance of the class name specified.
4
+ #
5
+ # Examples:
6
+ # Class.new_instance_of("Orange") => #<Orange:0x376c0c>
7
+ # Class.new_instance_of("Animals::Dog") => #<Animals::Dog:0x376a2c>
8
+ def self.new_instance_of(klass_name)
9
+ klass_name.constantize.new
10
+ end
11
+
12
+ # This will through the ancestor tree of object and tell you if
13
+ # that object is of the specified type.
14
+ def class_is_a?(klass_name)
15
+ self.ancestors.each do |an|
16
+ if an == klass_name
17
+ return true
18
+ end
19
+ end
20
+ return false
21
+ end
22
+
23
+ # Returns an array of the classes parent classes.
24
+ #
25
+ # Examples:
26
+ # Orange.parents # => [Citrus, Fruit, Object]
27
+ # Citrus.parents # => [Fruit, Object]
28
+ # Fruit.parents # => [Object]
29
+ def parents
30
+ ans = [self.superclass]
31
+ until ans.last.superclass.nil?
32
+ ans << ans.last.superclass
33
+ end
34
+ ans
35
+ end
36
+
37
+ end
38
+
@@ -0,0 +1,49 @@
1
+ require 'uri'
2
+ class Hash
3
+
4
+ def join(pair_string, join_string)
5
+ output = []
6
+ sorted = self.sort {|a,b| a[0].to_s <=> b[0].to_s}
7
+ sorted.each do |ar|
8
+ output << sprintf(pair_string, ar[0], ar[1])
9
+ end
10
+ output.join(join_string)
11
+ end
12
+
13
+ # Deletes the key(s) passed in from the hash.
14
+ def -(ars)
15
+ [ars].flatten.each {|a| self.delete(a)}
16
+ self
17
+ end
18
+
19
+ # Converts a hash to query string parameters.
20
+ # An optional boolean escapes the values if true, which is the default.
21
+ def to_params(escape = true)
22
+ params = ''
23
+ stack = []
24
+
25
+ each do |k, v|
26
+ if v.is_a?(Hash)
27
+ stack << [k,v]
28
+ else
29
+ v = v.to_s.uri_escape if escape
30
+ params << "#{k}=#{v}&"
31
+ end
32
+ end
33
+
34
+ stack.each do |parent, hash|
35
+ hash.each do |k, v|
36
+ if v.is_a?(Hash)
37
+ stack << ["#{parent}[#{k}]", v]
38
+ else
39
+ v = v.to_s.uri_escape if escape
40
+ params << "#{parent}[#{k}]=#{v}&"
41
+ end
42
+ end
43
+ end
44
+
45
+ params.chop! # trailing &
46
+ params.split("&").sort.join("&")
47
+ end
48
+
49
+ end
@@ -0,0 +1,34 @@
1
+ require 'pp'
2
+ require 'stringio'
3
+
4
+ module Kernel
5
+
6
+ def pp_to_s(object)
7
+ pp_out = StringIO.new
8
+ PP.pp(object,pp_out)
9
+ return pp_out.string
10
+ end
11
+
12
+ def retryable(options = {}, &block)
13
+ opts = { :tries => 1, :on => Exception }.merge(options)
14
+
15
+ retries = opts[:tries]
16
+ retry_exceptions = [opts[:on]].flatten
17
+
18
+ x = %{
19
+ begin
20
+ return yield
21
+ rescue #{retry_exceptions.join(", ")} => e
22
+ retries -= 1
23
+ if retries > 0
24
+ retry
25
+ else
26
+ raise e
27
+ end
28
+ end
29
+ }
30
+
31
+ eval(x, &block)
32
+ end
33
+
34
+ end
@@ -0,0 +1,15 @@
1
+ module Math
2
+
3
+ def self.log2(x)
4
+ self.log(x)/self.log(2.0)
5
+ end
6
+
7
+ def self.min(a, b)
8
+ a < b ? a : b
9
+ end
10
+
11
+ def self.max(a, b)
12
+ a > b ? a : b
13
+ end
14
+
15
+ end
@@ -0,0 +1,29 @@
1
+ class Module
2
+
3
+ # Bulk converts the security level of methods in this Module from one level to another.
4
+ def convert_security_of_methods(old_level = :public, new_level = :protected)
5
+ eval("#{old_level}_instance_methods").each{ |meth| self.send(new_level, meth) }
6
+ self
7
+ end
8
+
9
+ # Includes this module into a Class, and changes all public methods to protected.
10
+ #
11
+ # Examples:
12
+ # module MyCoolUtils
13
+ # def some_meth
14
+ # "hi"
15
+ # end
16
+ # self.include_safely_into(FooController)
17
+ # end
18
+ # or:
19
+ # MyCoolUtils.include_safely_into(FooController, SomeOtherClass)
20
+ def include_safely_into(*args)
21
+ [args].flatten.each do |a|
22
+ if a.is_a?(String) || a.is_a?(Symbol)
23
+ a = a.to_s.constantize
24
+ end
25
+ a.send(:include, self.convert_security_of_methods)
26
+ end
27
+ end
28
+
29
+ end
@@ -0,0 +1,164 @@
1
+ class Object
2
+
3
+ # Includes a module into the current Class, and changes all the module's public methods to protected.
4
+ #
5
+ # Example:
6
+ # class FooController
7
+ # safely_include_module(MyCoolUtils, MyOtherModule)
8
+ # end
9
+ def safely_include_module(*modules)
10
+ [modules].flatten.each do |mod|
11
+ mod.include_safely_into(self)
12
+ end
13
+ end
14
+
15
+ # Prints out the methods associated with this object in alphabetical order.
16
+ def print_methods
17
+ m = "----- #{self} (methods) -----\n"
18
+ m << methods.sort.join("\n")
19
+ puts m
20
+ m
21
+ end
22
+
23
+ # An elegant way to refactor out common options
24
+ #
25
+ # with_options :order => 'created_at', :class_name => 'Comment' do |post|
26
+ # post.has_many :comments, :conditions => ['approved = ?', true], :dependent => :delete_all
27
+ # post.has_many :unapproved_comments, :conditions => ['approved = ?', false]
28
+ # post.has_many :all_comments
29
+ # end
30
+ #
31
+ # Can also be used with an explicit receiver:
32
+ #
33
+ # map.with_options :controller => "people" do |people|
34
+ # people.connect "/people", :action => "index"
35
+ # people.connect "/people/:id", :action => "show"
36
+ # end
37
+ #
38
+ def with_options(options)
39
+ yield Mack::Utils::OptionMerger.new(self, options)
40
+ end
41
+
42
+ # See Class parents for more information.
43
+ def class_parents
44
+ self.class.parents
45
+ end
46
+
47
+ # This method gets called when a parameter is passed into a named route.
48
+ # This can be overridden in an Object to provlde custom handling of parameters.
49
+ def to_param
50
+ self.to_s
51
+ end
52
+
53
+ # Uses <code>define_method</code> to create an empty for the method parameter defined.
54
+ # That method will then raise MethodNotImplemented. This is useful for creating interfaces
55
+ # and you want to stub out methods that others need to implement.
56
+ def self.needs_method(meth)
57
+ define_method(meth) do
58
+ raise NoMethodError.new("The interface you are using requires you define the following method '#{meth}'")
59
+ end
60
+ end
61
+
62
+ # This prints out running time for the block provided. This is great for things
63
+ # like Rake tasks, etc... where you would like to know how long it, or a section of
64
+ # it took to run.
65
+ def running_time(message = "", logger = nil)
66
+ s_time = Time.now
67
+ s = "---Starting at #{s_time}---"
68
+ puts s
69
+ logger.info s unless logger.nil?
70
+ yield if block_given?
71
+ e_time = Time.now
72
+ e = "---Ending at #{e_time}---"
73
+ puts e
74
+ logger.info e unless logger.nil?
75
+ secs = e_time - s_time
76
+ if secs < 60
77
+ x = "Running time #{secs} seconds."
78
+ else
79
+ x = "Running time roughly #{secs/60} minutes [#{secs} seconds]"
80
+ end
81
+ x += " [MESSAGE]: #{message}" unless message.blank?
82
+ puts x
83
+ logger.info x unless logger.nil?
84
+ end
85
+
86
+ # This method will call send to all the methods defined on the previous method.
87
+ #
88
+ # Example:
89
+ # Fruit.send_with_chain([:new, :get_citrus, :get_orange, :class]) # => Orange
90
+ #
91
+ # This would be the equivalent:
92
+ # Fruit.new.get_citrus.get_orange.class
93
+ def send_with_chain(methods, *args)
94
+ obj = self
95
+ [methods].flatten.each {|m| obj = obj.send(m, *args)}
96
+ obj
97
+ end
98
+
99
+ # ivar_cache allows you to cache the results of the block into an instance variable in a class,
100
+ # and then will serve up that instance variable the next time you call that method again.
101
+ #
102
+ # old way:
103
+ # def show_page_link
104
+ # unless @show_page_link # check if instance variable exists
105
+ # # if the instance variable doesn't exist let's do some work and assign it to the instance variable.
106
+ # @show_page_link = link_to("show", some_url(:id => self.id, :foo => bar, etc... => etc))
107
+ # end
108
+ # @show_page_link # now return the instance variable
109
+ # end
110
+ #
111
+ # new way:
112
+ # def show_page_link
113
+ # ivar_cache do
114
+ # link_to("show", some_url(:id => self.id, :foo => bar, etc... => etc))
115
+ # end
116
+ # end
117
+ #
118
+ # this does everything the old way did, but it is much cleaner, and a lot less code!
119
+ # in case you're wondering it caches the result, by default, to an instance variable named after the method,
120
+ # so in our above example the instance variable would be name, <code>@show_page_link</code>. this can be overridden like such:
121
+ #
122
+ # def show_page_link
123
+ # ivar_cache("foo_var") do
124
+ # link_to("show", some_url(:id => self.id, :foo => bar, etc... => etc))
125
+ # end
126
+ # end
127
+ #
128
+ # now it will cache it to <code>@foo_var</code>
129
+ def ivar_cache(var_name = nil, &block)
130
+ if var_name.nil?
131
+ call = caller[0]
132
+ var_name = call[(call.index('`')+1)...call.index("'")]
133
+ end
134
+ var = instance_variable_get("@#{var_name}")
135
+ unless var
136
+ return instance_variable_set("@#{var_name}", yield) if block_given?
137
+ end
138
+ instance_variable_get("@#{var_name}")
139
+ end
140
+
141
+ def ivar_cache_clear(var_name = nil, &block)
142
+ if var_name.nil?
143
+ call = caller[0]
144
+ var_name = call[(call.index('`')+1)...call.index("'")]
145
+ end
146
+ remove_instance_variable("@#{var_name}") #rescue
147
+ yield if block_given?
148
+ end
149
+
150
+ # Returns the namespaces for a particular object.
151
+ #
152
+ # Examples:
153
+ # Animals::Dog::Poodle.new.namespaces # => ["Animals", "Dog"]
154
+ def namespaces
155
+ ivar_cache("object_namespaces") do
156
+ nss = []
157
+ full_name = self.class.name.to_s
158
+ nss = full_name.split("::")
159
+ nss.pop
160
+ nss
161
+ end
162
+ end
163
+
164
+ end
@@ -0,0 +1,218 @@
1
+ class String
2
+ include Style
3
+
4
+ def methodize
5
+ x = self
6
+
7
+ # if we get down to a nil or an empty string raise an exception!
8
+ raise NameError.new("#{self} cannot be converted to a valid method name!") if x.nil? || x == ''
9
+
10
+ # get rid of the big stuff in the front/back
11
+ x.strip!
12
+
13
+ # if we get down to a nil or an empty string raise an exception!
14
+ raise NameError.new("#{self} cannot be converted to a valid method name!") if x.nil? || x == ''
15
+
16
+ x = x.underscore
17
+
18
+ # get rid of spaces and make the _
19
+ x.gsub!(' ', '_')
20
+ # get rid of everything that isn't 'safe' a-z, 0-9, ?, !, =, _
21
+ x.gsub!(/([^ a-zA-Z0-9\_\?\!\=]+)/n, '_')
22
+
23
+ # if we get down to a nil or an empty string raise an exception!
24
+ raise NameError.new("#{self} cannot be converted to a valid method name!") if x.nil? || x == ''
25
+
26
+ # condense multiple 'safe' non a-z chars to just one.
27
+ # ie. ___ becomes _ !!!! becomes ! etc...
28
+ [' ', '_', '?', '!', "="].each do |c|
29
+ x.squeeze!(c)
30
+ end
31
+
32
+ # if we get down to a nil or an empty string raise an exception!
33
+ raise NameError.new("#{self} cannot be converted to a valid method name!") if x.nil? || x == ''
34
+
35
+ #down case the whole thing
36
+ x.downcase!
37
+
38
+ # get rid of any characters at the beginning that aren't a-z
39
+ while !x.match(/^[a-z]/)
40
+ x.slice!(0)
41
+
42
+ # if we get down to a nil or an empty string raise an exception!
43
+ raise NameError.new("#{self} cannot be converted to a valid method name!") if x.nil? || x == ''
44
+ end
45
+
46
+ # let's trim this bad boy down a bit now that we've cleaned it up, somewhat.
47
+ # we should do this before cleaning up the end character, because it's possible to end up with a
48
+ # bad char at the end if you trim too late.
49
+ x = x[0..100] if x.length > 100
50
+
51
+ # get rid of any characters at the end that aren't safe
52
+ while !x.match(/[a-z0-9\?\!\=]$/)
53
+ x.slice!(x.length - 1)
54
+ # if we get down to a nil or an empty string raise an exception!
55
+ raise NameError.new("#{self} cannot be converted to a valid method name!") if x.nil? || x == ''
56
+ end
57
+
58
+ # if we get down to a nil or an empty string raise an exception!
59
+ raise NameError.new("#{self} cannot be converted to a valid method name!") if x.nil? || x == ''
60
+
61
+ # let's get rid of characters that don't belong in the 'middle' of the method.
62
+ orig_middle = x[1..(x.length - 2)]
63
+ n_middle = orig_middle.dup
64
+
65
+ ['?', '!', "="].each do |c|
66
+ n_middle.gsub!(c, "_")
67
+ end
68
+
69
+ # the previous gsub can leave us with multiple underscores that need cleaning up.
70
+ n_middle.squeeze!("_")
71
+
72
+ x.gsub!(orig_middle, n_middle)
73
+ x.gsub!("_=", "=")
74
+ x
75
+ end
76
+
77
+ # Returns a constant of the string.
78
+ #
79
+ # Examples:
80
+ # "User".constantize # => User
81
+ # "HomeController".constantize # => HomeController
82
+ # "Mack::Configuration" # => Mack::Configuration
83
+ def constantize
84
+ Module.instance_eval("::#{self}")
85
+ end
86
+
87
+ def hexdigest
88
+ Digest::SHA1.hexdigest(self)
89
+ end
90
+
91
+ def hexdigest!
92
+ self.replace(self.hexdigest)
93
+ end
94
+
95
+ def self.randomize(length = 10)
96
+ chars = ("A".."H").to_a + ("J".."N").to_a + ("P".."T").to_a + ("W".."Z").to_a + ("3".."9").to_a
97
+ newpass = ""
98
+ 1.upto(length) { |i| newpass << chars[rand(chars.size-1)] }
99
+ return newpass.upcase
100
+ end
101
+
102
+ # Performs URI escaping so that you can construct proper
103
+ # query strings faster. Use this rather than the cgi.rb
104
+ # version since it's faster. (Stolen from Camping).
105
+ def uri_escape
106
+ self.gsub(/([^ a-zA-Z0-9_.-]+)/n) {
107
+ '%'+$1.unpack('H2'*$1.size).join('%').upcase
108
+ }.tr(' ', '+')
109
+ end
110
+
111
+ # Unescapes a URI escaped string. (Stolen from Camping).
112
+ def uri_unescape
113
+ self.tr('+', ' ').gsub(/((?:%[0-9a-fA-F]{2})+)/n){
114
+ [$1.delete('%')].pack('H*')
115
+ }
116
+ end
117
+
118
+ def truncate(length = 30, truncate_string = "...")
119
+ if self.nil? then return end
120
+ l = length - truncate_string.length
121
+ if $KCODE == "NONE"
122
+ self.length > length ? self[0...l] + truncate_string : self
123
+ else
124
+ chars = self.split(//)
125
+ chars.length > length ? chars[0...l].join + truncate_string : self
126
+ end
127
+ end
128
+
129
+ def truncate!(length = 30, truncate_string = "...")
130
+ self.replace(self.truncate(length, truncate_string))
131
+ end
132
+
133
+ end
134
+ # require 'digest'
135
+ # class String
136
+ #
137
+ # # Maps to Mack::Utils::Inflector.instance.pluralize
138
+ # def plural
139
+ # Mack::Utils::Inflector.instance.pluralize(self)
140
+ # end
141
+ #
142
+ # # Maps to Mack::Utils::Inflector.instance.singularize
143
+ # def singular
144
+ # Mack::Utils::Inflector.instance.singularize(self)
145
+ # end
146
+ #
147
+
148
+ #
149
+ #
150
+ # def underscore
151
+ # camel_cased_word = self.dup
152
+ # camel_cased_word.to_s.gsub(/::/, '/').
153
+ # gsub(/([A-Z]+)([A-Z][a-z])/,'\1_\2').
154
+ # gsub(/([a-z\d])([A-Z])/,'\1_\2').
155
+ # tr("-", "_").
156
+ # downcase
157
+ # end
158
+ #
159
+ # def starts_with?(x)
160
+ # self.match(/^#{x}/) ? true : false
161
+ # end
162
+ #
163
+ # def ends_with?(x)
164
+ # self.match(/#{x}$/) ? true : false
165
+ # end
166
+ #
167
+ # # Returns "is" or "are" based on the number, i.e. "i=6; There #{isare(i)} #{i} topics here."
168
+ # def self.pluralize_word(num, vals = ["is", "are"])
169
+ # return vals[0] if num.to_i==1
170
+ # return vals[1]
171
+ # end
172
+ #
173
+ # def remove(val)
174
+ # gsub(val, '')
175
+ # end
176
+ #
177
+ # def remove!(val)
178
+ # gsub!(val, '')
179
+ # end
180
+ #
181
+
182
+ #
183
+ # def truncate(length = 30, truncate_string = "...")
184
+ # if self.nil? then return end
185
+ # l = length - truncate_string.length
186
+ # if $KCODE == "NONE"
187
+ # self.length > length ? self[0...l] + truncate_string : self
188
+ # else
189
+ # chars = self.split(//)
190
+ # chars.length > length ? chars[0...l].join + truncate_string : self
191
+ # end
192
+ # end
193
+ #
194
+ # def truncate!(length = 30, truncate_string = "...")
195
+ # self.replace(self.truncate(length, truncate_string))
196
+ # end
197
+ #
198
+ # def capitalize_all_words
199
+ # self.gsub(/\b\w/) {|s| s.upcase}
200
+ # end
201
+ #
202
+ # def capitalize_all_words!
203
+ # self.replace(self.capitalize_all_words)
204
+ # end
205
+ #
206
+ # # keep adding on to this whenever it becomes apparent that unsafe strings
207
+ # # could get passed through into the database
208
+ # def sql_safe_str
209
+ # if !self.nil?
210
+ # self.gsub(/[\']/, "\'\'")
211
+ # end
212
+ # end
213
+ #
214
+ # def sql_safe_str!
215
+ # self.replace(self.sql_safe_str)
216
+ # end
217
+ #
218
+ # end
@@ -0,0 +1,7 @@
1
+ class Symbol
2
+
3
+ def methodize
4
+ self.to_s.methodize
5
+ end
6
+
7
+ end
@@ -0,0 +1,31 @@
1
+ require 'rubygems'
2
+ require 'digest'
3
+ require 'facets'
4
+ require 'facets/ruby'
5
+ require 'facets/style'
6
+ require 'facets/blank'
7
+ require 'facets/hash'
8
+ require 'facets/hash/symbolize_keys'
9
+ require 'facets/hash/stringify_keys'
10
+ require 'facets/module'
11
+ require 'facets/infinity'
12
+ require 'english/inflect'
13
+ require 'english/numerals'
14
+ [:inflector, :inflections, :options_merger].each do |k|
15
+ path = File.join File.dirname(__FILE__), "utils", "#{k}"
16
+ #puts "requiring #{path}"
17
+ require path
18
+ end
19
+
20
+ [:array, :class, :hash, :kernel, :math, :module, :object, :string, :symbol].each do |k|
21
+ path = File.join File.dirname(__FILE__), "extensions", "#{k}"
22
+ #puts "requiring #{path}"
23
+ require path
24
+ end
25
+
26
+ [:numerals, :inflect].each do |k|
27
+ path = File.join File.dirname(__FILE__), "english_extensions", "#{k}"
28
+ #puts "requiring #{path}"
29
+ require path
30
+ end
31
+
@@ -0,0 +1,63 @@
1
+ require File.join(File.dirname(__FILE__), "inflector")
2
+ # Default inflections. This is taken from Jeremy McAnally's great Rails plugin, acts_as_good_speeler. Thanks Jeremy! http://www.jeremymcanally.com/
3
+ Mack::Utils::Inflector.inflections do |inflect|
4
+ # inflect.plural(/$/, 's')
5
+ inflect.plural(/s$/i, 's')
6
+ inflect.plural(/(bu)s$/i, '\1ses')
7
+ inflect.plural(/(stimul|hippopotam|octop|vir|syllab|foc|alumn|fung|radi)us$/i, '\1i')
8
+ inflect.plural(/(ax|test)is$/i, '\1es')
9
+ inflect.plural(/(alias|status)$/i, '\1es')
10
+ inflect.plural(/(buffal|tomat|torped)o$/i, '\1oes')
11
+ inflect.plural(/([dti])um$/i, '\1a')
12
+ inflect.plural(/sis$/i, 'ses')
13
+ inflect.plural(/(?:([^f])fe|([lr])f)$/i, '\1\2ves')
14
+ inflect.plural(/(hive)$/i, '\1s')
15
+ inflect.plural(/([^aeiouy]|qu)y$/i, '\1ies')
16
+ inflect.plural(/(x|ch|ss|sh)$/i, '\1es')
17
+ inflect.plural(/(matr|append|vert|ind)ix|ex$/i, '\1ices')
18
+ inflect.plural(/([m|l])ouse$/i, '\1ice')
19
+ inflect.plural(/^(ox)$/i, '\1en')
20
+ inflect.plural(/(quiz)$/i, '\1zes')
21
+ inflect.plural(/(phenomen|criteri)on$/i, '\1a')
22
+ inflect.plural(/^(?!(.*hu|.*ger|.*sha))(.*)(wom|m)an$/i, '\2\3en')
23
+ inflect.plural(/(curricul|bacteri|medi)um$/i, '\1a')
24
+ inflect.plural(/(nebul|formul|vit|vertebr|alg|alumn)a$/i, '\1ae')
25
+
26
+ # inflect.singular(/s$/i, '')
27
+ inflect.singular(/(n)ews$/i, '\1ews')
28
+ inflect.singular(/([dti])a$/i, '\1um')
29
+ inflect.singular(/((a)naly|(b)a|(d)iagno|(p)arenthe|(p)rogno|(s)ynop|(t)he)ses$/i, '\1\2sis')
30
+ inflect.singular(/(^analy|cri|empha)ses$/i, '\1sis')
31
+ inflect.singular(/([^f])ves$/i, '\1fe')
32
+ inflect.singular(/(hive)s$/i, '\1')
33
+ inflect.singular(/(tive)s$/i, '\1')
34
+ inflect.singular(/(bus)es$/i, '\1')
35
+ inflect.singular(/(o)es$/i, '\1')
36
+ inflect.singular(/(shoe)s$/i, '\1')
37
+ inflect.singular(/(test|ax)es$/i, '\1is')
38
+ inflect.singular(/(stimul|hippopotam|octop|vir|syllab|foc|alumn|fung|radi)i$/i, '\1us')
39
+ inflect.singular(/(alias|status)es$/i, '\1')
40
+ inflect.singular(/^(ox)en$/i, '\1')
41
+ inflect.singular(/(vert|ind)ices$/i, '\1ex')
42
+ inflect.singular(/(matr|append)ices$/i, '\1ix')
43
+ inflect.singular(/(quiz)zes$/i, '\1')
44
+ inflect.singular(/(phenomen|criteri)a$/i, '\1on')
45
+ inflect.singular(/(.*)(wo|m)en$/i, '\1\2an')
46
+ inflect.singular(/(medi|curricul|bacteri)a$/i, '\1um')
47
+ inflect.singular(/(nebula|formula|vita|vertebra|alga|alumna)e$/i, '\1')
48
+ inflect.singular(/^(.*)ookies$/, '\1ookie')
49
+ inflect.singular(/(.*)ss$/, '\1ss')
50
+ inflect.singular(/(.*)ies$/, '\1y')
51
+
52
+ inflect.irregular('person', 'people')
53
+ inflect.irregular('child', 'children')
54
+ inflect.irregular('sex', 'sexes')
55
+ inflect.irregular('move', 'moves')
56
+ inflect.irregular('tooth', 'teeth')
57
+ inflect.irregular('die', 'dice')
58
+ inflect.irregular('talisman', 'talismans')
59
+ inflect.irregular('penis', 'penises')
60
+ inflect.irregular('christmas', 'christmases')
61
+ inflect.irregular('knowledge', 'knowledge')
62
+ inflect.irregular('quiz', 'quizzes')
63
+ end
@@ -0,0 +1,99 @@
1
+ require 'singleton'
2
+ require File.join(File.dirname(__FILE__), "..", "english_extensions", 'inflect')
3
+ module Mack # :nodoc:
4
+ module Utils # :nodoc:
5
+ # This class is used to deal with inflection strings. This means taken a string and make it plural, or singular, etc...
6
+ # Inflection rules can be added very easy, and are checked from the bottom up. This means that the last rule is the first
7
+ # rule to be matched. The exception to this, kind of, is 'irregular' and 'uncountable' rules. The 'uncountable' rules are
8
+ # always checked first, then the 'irregular' rules, and finally either the 'singular' or 'plural' rules, depending on what
9
+ # you're trying to do. Within each of these sets of rules, the last rule in is the first rule matched.
10
+ #
11
+ # Example:
12
+ # Mack::Utils::Inflector.inflections do |inflect|
13
+ # inflect.plural(/$/, 's')
14
+ # inflect.plural(/^(ox)$/i, '\1en')
15
+ # inflect.plural(/(phenomen|criteri)on$/i, '\1a')
16
+ #
17
+ # inflect.singular(/s$/i, '')
18
+ # inflect.singular(/(n)ews$/i, '\1ews')
19
+ # inflect.singular(/^(.*)ookies$/, '\1ookie')
20
+ #
21
+ # inflect.irregular('person', 'people')
22
+ # inflect.irregular('child', 'children')
23
+ # end
24
+ class Inflector
25
+ include Singleton
26
+
27
+ # Adds a plural rule to the system.
28
+ #
29
+ # Example:
30
+ # Mack::Utils::Inflector.inflections do |inflect|
31
+ # inflect.plural(/$/, 's')
32
+ # inflect.plural(/^(ox)$/i, '\1en')
33
+ # inflect.plural(/(phenomen|criteri)on$/i, '\1a')
34
+ # end
35
+ def plural(rule, replacement)
36
+ English::Inflect.plural_rule(rule, replacement)
37
+ end
38
+
39
+ # Adds a singular rule to the system.
40
+ #
41
+ # Example:
42
+ # Mack::Utils::Inflector.inflections do |inflect|
43
+ # inflect.singular(/s$/i, '')
44
+ # inflect.singular(/(n)ews$/i, '\1ews')
45
+ # inflect.singular(/^(.*)ookies$/, '\1ookie')
46
+ # end
47
+ def singular(rule, replacement)
48
+ English::Inflect.singular_rule(rule, replacement)
49
+ end
50
+
51
+ # Adds a irregular rule to the system.
52
+ #
53
+ # Example:
54
+ # Mack::Utils::Inflector.inflections do |inflect|
55
+ # inflect.irregular('person', 'people')
56
+ # inflect.irregular('child', 'children')
57
+ # end
58
+ def irregular(rule, replacement)
59
+ English::Inflect.rule(rule, replacement)
60
+ English::Inflect.word(rule, replacement)
61
+ end
62
+
63
+ # Returns the singular version of the word, if possible.
64
+ #
65
+ # Examples:
66
+ # Mack::Utils::Inflector.instance.singularize("armies") # => "army"
67
+ # Mack::Utils::Inflector.instance.singularize("people") # => "person"
68
+ # Mack::Utils::Inflector.instance.singularize("boats") # => "boat"
69
+ def singularize(word)
70
+ English::Inflect.singular(word)
71
+ end
72
+
73
+ # Returns the singular version of the word, if possible.
74
+ #
75
+ # Examples:
76
+ # Mack::Utils::Inflector.instance.pluralize("army") # => "armies"
77
+ # Mack::Utils::Inflector.instance.pluralize("person") # => "people"
78
+ # Mack::Utils::Inflector.instance.pluralize("boat") # => "boats"
79
+ def pluralize(word)
80
+ English::Inflect.plural(word)
81
+ end
82
+
83
+ public
84
+ class << self
85
+
86
+ # Yields up Mack::Utils::Inflector.instance
87
+ def inflections
88
+ if block_given?
89
+ yield Mack::Utils::Inflector.instance
90
+ else
91
+ Mack::Utils::Inflector.instance
92
+ end
93
+ end
94
+
95
+ end
96
+
97
+ end # Inflection
98
+ end # Utils
99
+ end # Mack
@@ -0,0 +1,27 @@
1
+ module Mack
2
+ module Utils
3
+ class OptionMerger #:nodoc:
4
+ instance_methods.each do |method|
5
+ undef_method(method) if method !~ /^(__|instance_eval|class|object_id)/
6
+ end
7
+
8
+ def initialize(context, options)
9
+ @context, @options = context, options
10
+ end
11
+
12
+ private
13
+ def method_missing(method, *arguments, &block)
14
+ merge_argument_options! arguments
15
+ @context.send(method, *arguments, &block)
16
+ end
17
+
18
+ def merge_argument_options!(arguments)
19
+ arguments << if arguments.last.respond_to? :to_hash
20
+ @options.merge(arguments.pop)
21
+ else
22
+ @options.dup
23
+ end
24
+ end
25
+ end # OptionMerger
26
+ end # Utils
27
+ end # Mack
metadata ADDED
@@ -0,0 +1,86 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: mack-facets
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.6.0
5
+ platform: ruby
6
+ authors:
7
+ - markbates
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+
12
+ date: 2008-07-16 00:00:00 -04:00
13
+ default_executable:
14
+ dependencies:
15
+ - !ruby/object:Gem::Dependency
16
+ name: facets
17
+ version_requirement:
18
+ version_requirements: !ruby/object:Gem::Requirement
19
+ requirements:
20
+ - - "="
21
+ - !ruby/object:Gem::Version
22
+ version: 2.4.1
23
+ version:
24
+ - !ruby/object:Gem::Dependency
25
+ name: english
26
+ version_requirement:
27
+ version_requirements: !ruby/object:Gem::Requirement
28
+ requirements:
29
+ - - "="
30
+ - !ruby/object:Gem::Version
31
+ version: 0.2.0
32
+ version:
33
+ description: "mack-facets was developed by: markbates"
34
+ email: mark@mackframework.com
35
+ executables: []
36
+
37
+ extensions: []
38
+
39
+ extra_rdoc_files:
40
+ - README
41
+ files:
42
+ - lib/english_extensions/inflect.rb
43
+ - lib/english_extensions/numerals.rb
44
+ - lib/extensions/array.rb
45
+ - lib/extensions/class.rb
46
+ - lib/extensions/hash.rb
47
+ - lib/extensions/kernel.rb
48
+ - lib/extensions/math.rb
49
+ - lib/extensions/module.rb
50
+ - lib/extensions/object.rb
51
+ - lib/extensions/string.rb
52
+ - lib/extensions/symbol.rb
53
+ - lib/mack-facets.rb
54
+ - lib/utils/inflections.rb
55
+ - lib/utils/inflector.rb
56
+ - lib/utils/options_merger.rb
57
+ - README
58
+ has_rdoc: true
59
+ homepage: http://www.mackframework.com
60
+ post_install_message:
61
+ rdoc_options: []
62
+
63
+ require_paths:
64
+ - lib
65
+ - lib
66
+ required_ruby_version: !ruby/object:Gem::Requirement
67
+ requirements:
68
+ - - ">="
69
+ - !ruby/object:Gem::Version
70
+ version: 1.8.6
71
+ version:
72
+ required_rubygems_version: !ruby/object:Gem::Requirement
73
+ requirements:
74
+ - - ">="
75
+ - !ruby/object:Gem::Version
76
+ version: "0"
77
+ version:
78
+ requirements: []
79
+
80
+ rubyforge_project: magrathea
81
+ rubygems_version: 1.1.1
82
+ signing_key:
83
+ specification_version: 2
84
+ summary: Ruby language extensions for Mack
85
+ test_files: []
86
+