Rails 3 convert superclass to subclass
In a recent rails 3.0 project I was working on I had an interesting dilemma. I have two models, User and Member. Member is a subclass of User.
Now when a user logs into the system the system checks what roles and permissions each user has and then redirects them accordingly. e.g. if the user record has a role of ‘Member’ then we redirect them to the member section.
Now since Member is a subclass of User, we are using STI ( Single table inheritance ) within rails whereby all the member attributes are stored as columns within the single user table. Member has an additional method called active? which determines if the membership level is active or not. However, in the logic which checks where to redirect signins because only User objects are returned, each call to active? is made on the superclass of User and not Member. To fix this I could redefine active? within the User model but it means duplication of the active? method inside Members class.
Another alternative would be to convert the User model into a Member object. ActiveRecord instances have a method called becomes(klass) which takes the name of the class to convert to. The definition of becomes from the API docs as follows:
Returns an instance of the specified klass with the attributes of the current record. This is mostly useful in relation to single-table inheritance structures where you want a subclass to appear as the superclass.
Full link of the api can be found here: http://api.rubyonrails.org/classes/ActiveRecord/Persistence.html#method-i-becomes
Now we are going the other way round from superclass to subclass which is unorthodox but works in my case here. An example of what I ended up with: