Module: Flexus

Defined in:
lib/flexus.rb,
lib/flexus/version.rb,
lib/flexus/inflections.rb,
lib/flexus/rules_collection.rb

Overview

The Flexus transforms words from singular to plural, class names to table names, modularized class names to ones without, and class names to foreign keys. The default inflections for pluralization, singularization, and uncountable words are kept in inflections.rb.

The Rails core team has stated patches for the inflections library will not be accepted in order to avoid breaking legacy applications which may be relying on errant inflections. If you discover an incorrect inflection and require it for your application, you’ll need to correct it yourself (explained below).

Defined Under Namespace

Classes: Inflections, RulesCollection

Constant Summary collapse

ORDINALIZE_TH =
(4..16).to_set.freeze
VERSION =
"1.0.0"

Class Method Summary collapse

Class Method Details

.camelize(input) ⇒ String

Convert input to UpperCamelCase

Will also convert ‘/’ to ‘::’ which is useful for converting paths to namespaces.

Examples:

Flexus.camelize("data_mapper")        # => "DataMapper"
Flexus.camelize("data_mapper/errors") # => "DataMapper::Errors"

Parameters:

  • input (String)

Returns:

  • (String)


27
28
29
# File 'lib/flexus.rb', line 27

def self.camelize(input)
  input.gsub(/\/(.?)/) { "::#{$1.upcase}" }.gsub(/(?:\A|_)(.)/) { $1.upcase }
end

.classify(table_name) ⇒ String

Classify input

Create a class name from a plural table name like Rails does for table names to models. Note that this returns a string and not a Class.

To convert to an actual class # follow classify with constantize.

@examples:

Flexus.classify("egg_and_hams") # => "EggAndHam"
Flexus.classify("posts")        # => "Post"

# Singular names are not handled correctly:
Flexus.classify("business")     # => "Busines"

Returns:

  • (String)


281
282
283
284
# File 'lib/flexus.rb', line 281

def self.classify(table_name)
  # strip out any leading schema name
  camelize(singularize(table_name.sub(/.*\./, '')))
end

.constantize(input) ⇒ Class, Module

Find a constant with the name specified in the argument string

The name is assumed to be the one of a top-level constant, constant scope of caller is ignored

Examples:


Flexus.constantize("Module")            # => Module
Flexus.constantize("DataMapper::Error") # => DataMapper::Error

Parameters:

  • input (String)

Returns:

  • (Class, Module)


113
114
115
116
117
118
119
120
121
122
123
124
# File 'lib/flexus.rb', line 113

def self.constantize(input)
  names = input.split('::')
  names.shift if names.first.empty?

  names.inject(Object) do |constant, name|
    if constant.const_defined?(name, false)
      constant.const_get(name)
    else
      constant.const_missing(name)
    end
  end
end

.dasherize(input) ⇒ String

Convert input underscores to dashes

Examples:

Flexus.dasherize("foo_bar") # => "foo-bar"

Parameters:

  • input (String)

Returns:

  • (String)


61
62
63
# File 'lib/flexus.rb', line 61

def self.dasherize(input)
  input.tr('_', '-')
end

.demodulize(input) ⇒ String

Return unscoped constant name

Examples:


Flexus.demodulize("DataMapper::Error") # => "Error"
Flexus.demodulize("DataMapper")        # => "DataMapper"

Parameters:

  • input (String)

Returns:

  • (String)


78
79
80
# File 'lib/flexus.rb', line 78

def self.demodulize(input)
  input.split('::').last
end

.foreign_key(input) ⇒ String

Creates a foreign key name

Examples:


Flexus.foreign_key("Message") => "message_id"

Parameters:

  • input (String)

Returns:

  • (String)


94
95
96
# File 'lib/flexus.rb', line 94

def self.foreign_key(input)
  "#{underscorize(demodulize(input))}_id"
end

.humanize(input) ⇒ String

Humanize string

capitalizes the first word and turns underscores into spaces and strips a # trailing “_id”, if any. Like titleize, this is meant for creating pretty output.

Examples:


Flexus.humanize("employee_salary") # => "Employee salary"
Flexus.humanize("author_id")       # => "Author"

Parameters:

  • input (String)

Returns:

  • (String)


232
233
234
235
236
237
238
# File 'lib/flexus.rb', line 232

def self.humanize(input)
  result = inflections.humans.apply_to(input)
  result.gsub!(/_id\z/, "")
  result.tr!('_', " ")
  result.capitalize!
  result
end

.inflectionsFlexus::Inflections

Yields a singleton instance of Flexus::Inflections

Examples:


Flexus.inflections do |inflect|
  inflect.uncountable "rails"
end

Returns:



169
170
171
172
# File 'lib/flexus.rb', line 169

def self.inflections
  instance = Inflections.instance
  block_given? ? yield(instance) : instance
end

.ordinalize(number) ⇒ String

Convert a number into an ordinal string

Examples:


ordinalize(1)     # => "1st"
ordinalize(2)     # => "2nd"
ordinalize(1002)  # => "1002nd"
ordinalize(1003)  # => "1003rd"

Parameters:

  • number (Fixnum)

Returns:

  • (String)


143
144
145
146
147
148
149
150
151
152
153
154
155
# File 'lib/flexus.rb', line 143

def self.ordinalize(number)
  abs_value = number.abs

  if ORDINALIZE_TH.include?(abs_value % 100)
    "#{number}th"
  else
    case abs_value % 10
      when 1; "#{number}st"
      when 2; "#{number}nd"
      when 3; "#{number}rd"
    end
  end
end

.pluralize(word) ⇒ String

Convert input word string to plural

Examples:


Flexus.pluralize("post")         # => "posts"
Flexus.pluralize("octopus")      # => "octopi"
Flexus.pluralize("sheep")        # => "sheep"
Flexus.pluralize("words")        # => "words"
Flexus.pluralize("CamelOctopus") # => "CamelOctopi"

Parameters:

  • word (String)

Returns:

  • (String)


190
191
192
193
# File 'lib/flexus.rb', line 190

def self.pluralize(word)
  return word if uncountable?(word)
  inflections.plurals.apply_to(word)
end

.singularize(word) ⇒ String

Convert word to singular

Examples:


Flexus.singularize("posts") # => "post"
Flexus.singularize("octopi") # => "octopus"
Flexus.singularize("sheep") # => "sheep"
Flexus.singularize("word") # => "word"
Flexus.singularize("CamelOctopi") # => "CamelOctopus"

Parameters:

  • word (String)

Returns:

  • (String)


211
212
213
214
# File 'lib/flexus.rb', line 211

def self.singularize(word)
  return word if uncountable?(word)
  inflections.singulars.apply_to(word)
end

.tableize(input) ⇒ String

Tabelize input string

Create the name of a table like Rails does for models to table names. This method # uses the pluralize method on the last word in the string.

Examples:


Flexus.tableize("RawScaledScorer") # => "raw_scaled_scorers"
Flexus.tableize("egg_and_ham")     # => "egg_and_hams"
Flexus.tableize("fancyCategory")   # => "fancy_categories"

Parameters:

  • input (String)

Returns:

  • (String)


257
258
259
260
# File 'lib/flexus.rb', line 257

def self.tableize(input)
  word = input.gsub(/::/, '_')
  pluralize(underscorize(word))
end

.uncountable?(word) ⇒ Boolean

Test if word is uncountable

Examples:


Flexus.uncountable?('rice') #=> true
Flexus.uncountable?('apple') #=> false

Parameters:

  • word (String)

Returns:

  • (Boolean)

    true, if word is uncountable



300
301
302
# File 'lib/flexus.rb', line 300

def self.uncountable?(word)
  word.empty? || inflections.uncountables.include?(word.downcase)
end

.underscore(input) ⇒ String

Convert input to underscored, lowercase string

Changes ‘::’ to ‘/’ to convert namespaces to paths.

Examples:

Flexus.underscore("DataMapper")         # => "data_mapper"
Flexus.underscore("DataMapper::Errors") # => "data_mapper/errors"

Parameters:

  • input (String)

Returns:

  • (String)


45
46
47
48
# File 'lib/flexus.rb', line 45

def self.underscore(input)
  word = input.gsub(/::/, '/')
  underscorize(word)
end