2
votes

I have quite a several level relationship of models in my project. In a controller I have this:

var1 = Repo.get!(Model1, 123) |> Repo.preload([child_items1:  :child_items2])

This works fine but I have to go one level deeper.

Namely each child_items2 many child_items3. Now, how can I preload child_items3 for each child_items2?

2
Try Repo.get!(Model1, 123) |> Repo.preload([child_items1: [child_items2: :child_items3]), let's see what happens. - NoDisplayName
Worked for me! This should be an answer rather than a comment - Jonathan de M.

2 Answers

0
votes

I usually use scopes. For example in my Model(1) I will have a with_model2 function that preloads the Model2. So to load 3 associations in a row, I'd have something like:

def with_model2(query \\ __MODULE__) do
  from query, preload: [model2: ^Model2.with_model3]
end

for my Model(1). And then you get the idea, the Model2 would have

def with_model3(query \\ __MODULE__) do
  from query, preload: :model3
end

I actually never went 3 level deep, but I just assume that would work.

0
votes

For others: The documentation actually says: Nested associations can also be preloaded in both formats:

Repo.all from p in Post,
       preload: [comments: :likes]

or in one query

Repo.all from p in Post,
       join: c in assoc(p, :comments),
       join: l in assoc(c, :likes),
       where: l.inserted_at > c.updated_at,
       preload: [comments: {c, likes: l}]