In a rails application, I have a base model like this :
class User < ActiveRecord::Base
attr_accessible :email, :name
end
And an inheritance from this model, like this :
class Provider < User
belongs_to :user
attr_accessible :business_name, :contact_name, :business_phone_number,
:business_email, :website, :user_id
end
When I do :
Provider.new.user_id
It say NoMethodError: undefined method 'user_id' for #<Provider:0x007f63ec8b3790>
.
When I just do Provider.new
I have this:
#<Provider id: nil, name: nil, email: nil, created_at: nil, updated_at: nil, type: "Provider">
This is a part of my schema.rb :
create_table "providers", :force => true do |t|
t.string "business_name", :null => false
t.string "contact_name", :null => false
t.string "business_phone_number", :null => false
t.string "business_email", :null => false
t.string "website"
t.integer "user_id"
end
create_table "users", :force => true do |t|
t.string "name"
t.string "email"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
end
As you can see, the attributes accessibles for Provider are not accessible. Do you have a solution?
Thanks!
As discussed in the answer to Single Table Inheritance to refer to a child class with its own fields , ActiveRecord
's implementation of Single Table Inheritance does not involve additional tables. All subclasses share the same table and rely on a type
field to identify subclasses. That explains why your Provider
instances only contain the fields available in your users
table, including the type
field that Rails adds for the subclassing support. Your providers
table is unused.
The same table is used at the database level. STI is achieved by adding a new column to the existing table. The new column usually named 'type' is used to hold the information whether it is a 'Provider' or 'User'
Here is how the the model queries translate to a sql query
When the User model is queried, as per your example, it searches 'users' table and includes all available type values in the condition
> User.first
SELECT `users`.* FROM `users` WHERE `users`.`type` IN ('User', 'Provider') ORDER BY `users`.`id` ASC LIMIT 1
When the Provider model is queried, type is set as 'Provider' in the condition and so the results get filtered. The underlying database table remains the same ie 'users'
> Provider.first
SELECT `users`.* FROM `users` WHERE `users`.`type` IN ('Provider') ORDER BY `users`.`id` ASC LIMIT 1
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.