Rails STI Subclasses get loaded when querying parent class

278 views Asked by At

I'm using STI pattern with Rails 6.0.3.3 and Ruby 2.6.6 which looks something like below:

class User end;

class User::Donor < User end;

class User::Legal < User::Donor end;

where donor and legal represents two types themselves.

I've inherited User::Legal with User::Donor due to the shared functionalities.

I've a User::Legal type record in my database.

In rails console when I try

1)  User::Donor.first # returns nil
2)  User::Legal.first # returns user_legal_obj
3)  User::Donor.first # returns user_legal_obj

// Query

1) SELECT "users".* FROM "users" WHERE "users"."type" = $1 LIMIT $2  [["type", "User::Donor"], ["LIMIT", 1]]

2) SELECT "users".* FROM "users" WHERE "users"."type" = $1 LIMIT $2  [["type", "User::Legal"], ["LIMIT", 1]]

3) SELECT "users".* FROM "users" WHERE "users"."type" IN ($1, $2) LIMIT $3  [["type", "User::Donor"], ["type", "User::Legal"], ["LIMIT", 1]]

Does anyone know why Rails is doing this weird behaviour that effects my output?

1

There are 1 answers

2
Qiu Chaofan On

Actually I did not reproduce the inconsistent behavior in the description (two User::Donor.first prints different results). Were your files or database modified during your rails console session?

If you mean that getting User::Donor result when querying User::Legal is weird, the answer is: it's expected behavior, and that's why it's called 'inheritance'.

The concept is from object-oriented programming, which means 'is a'. Here your User::Legal inherits from User::Donor, so User::Legal is a User::Donor. When querying User::Donor records, User::Legal should also be presented.

See 'Single table inheritance' in rails documents: https://api.rubyonrails.org/classes/ActiveRecord/Inheritance.html