luckyframework / luckyframework/avram
Unable to query a model where 2 associations use the same model
Nobody has claimed this yet.
- Dominant language
- Crystal
- Stars
- 183
- Forks
- 67
- PR merge metrics
- No merged PRs in 30d
Description
Related: #1007
Say you have a model where it has 2 `belongs_to` and both of those associations are the same model (e.g. User), any query you do that requires both will only use 1 join and override any where clauses set.
```crystal
class Interview < BaseModel
table do
belongs_to interviewer : User
belongs_to interviewee : User
end
end
# I want to query for all interviews where the Interviewer isn't available for hire, but the Interviewee is
InterviewQuery.new
.where_interviewer(UserQuery.new.available_for_hire(false))
.where_interviewee(UserQuery.new.available_for_hire(true))
```
In this case, we end up getting this SQL which is not what I want
```sql
SELECT interviews.*
FROM interviews
INNER JOIN users ON interviews.interviewer_id = users.id
WHERE users.available_for_hire = 'false'
AND users.available_for_hire = 'true'
```
My initial thought is if we just always alias the joins to your association method name, then maybe it'll fix this. However, I think that may also be a breaking change for anyone using `where(raw_query : String)`.
So `where_interviewer` would go from
```
INNER JOIN users ON interviews.interviewer_id = users.id
```
to
```
INNER JOIN users AS interviewers ON interviews.interviewer_id = interviewers.id
```
But then anyone that was doing `where("users.something @> ?", ...)` would now get runtime errors since they would need to change it to `where("interviewers.something @> ?", ...)`.
Maybe we can use some annotation to turn on this change at compile time and give people time to swap over? I'm not sure how that would work. :thinking:
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Start with the where_interviewer and where_interviewee query methods and reproduce the SQL shown in the issue using two belongs_to associations targeting User. Investigate how joins and raw where clauses are named; done means both associations can be queried independently without conflicting conditions while the compatibility impact of existing users[something] clauses is addressed.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- crystal, sql
- Domain
- backend, databases
- Issue type
- Bug
- Difficulty
- 4/5
- Estimated time
- 3-5 days
- Activity status
- Stale
- Clarity
- Mostly clear
- Newbie friendliness
- 35/100