CodedAttribute
Two of my favorite MySQL datatypes are ENUMs and SETs. Unfortunately, ActiveRecord doesn’t appear to support these fields well, or provide a good and simple alternative to the problem of coded values. In the past, I used to write getters and setters that looked something like this to solve my problem.
class Article
STATUS_CODES => {
:deleted => 0, 0 => :deleted
:pending => 1, 1 => :pending,
:completed => 2, 2 => :completed,
:published => 3, 3 => :published
}
def status=(value)
value = value.to_sym if value.is_a?(String)
status_code = STATUS_CODES[value]
end
def status
STATUS_CODES[status_code]
end
end
Doesn’t that code look horrible? Wouldn’t it be better if it looked like this?!
class Article
coded_attribute :status {
0 => :deleted
1 => :pending
2 => :completed
3 => :published
end
end
Or, if we want to get even lazier!
class MyClass
coded_attribute :status, [ :deleted, :active, :pending, :deleted ]
end
If so, then you’ve come to the right place.
This plugin makes doing all of the above super easy. And your code (and other programmers) will love you for using it! Like seriously love you!
Coded Attributes
Lets get down to it. Suppose we have a car, and it can be any one of a variety of colors. We can indicate this in the model with the following code:
class Car < ActiveRecord::Base
coded_attribute :color, [ :red, :orange, :yellow, :green, :blue, :indigo, :violet ]
end
But we aren’t finished just yet. We still need to create a column to store our attribute data in. There are two ways to go about this.
Storing the Coded Value
The easiest way to store the coded value is to create an integer column in the database by appending ‘_code’ to the name of the attribute. So in our ‘cars’ table, we could create a ‘color_code’ integer field. If you do not want to name the column in your database ‘color_code’, you can replace :color, with a :method => :column pair, for example:
class Car < ActiveRecord::Base
coded_attribute :color => :color_id, [ :red, orange, :yellow, :green, :blue, :indigo, :violet ]
end
Coded Attribute Sets
If you do not want to use a SET datatype, coded_attribute_set an make use of an integer bitmask to store the values.
class Car < ActiveRecord::Base
coded_attribute_set :color, [ :red, :orange, :yellow, :green, :blue, :indigo, :violet ]
end
Planned Features
Future versions should hopefully support auto-detecting and setup of enum and set types (so you don’t need to even define the coded_attribute, it will be done automatically on all classes).
I also plan on a method added to Migrations that allow you to easily recode data
Copyright © 2010 Jaden Carver, released under the MIT license