Ecto hierarchical schema id does not exist

Hello,

I’m currently trying to make a schema that have a reference to a parent of the same type and a record of an other type.
Here is my schema :

defmodule Comment do
  use Ecto.Schema
  import Ecto.Changeset

  @primary_key {:id, :binary_id, autogenerate: true}
  schema "comments" do

    belongs_to :post, Post, type: :binary_id

    belongs_to :comment, Comment, type: :binary_id

    has_many :sub_comments, Comment, references: :id
  end

  def changeset(struct, params \\ %{}) do
    struct
    |> cast(params, [:id, :comment_id, :post_id])
    |> unique_constraint(:id, name: "pkey", match: :suffix)
    |> foreign_key_constraint(:id, name: "comments_post_id_fkey")
    |> cast_assoc(:post)
    |> cast_assoc(:comment)
    |> cast_assoc(:sub_comments)
  end

But when I want to insert I have the following error :

09:44:58.759 [warn]  when storing block, got changeset errors at pos={40000000,
 ♯78315364456255586b7766696846717a43315879444a6f4672416e39767a7a396b35583773376a72525256}e[0m: %{
  "posts[].comments[].sub_comments[].id" => %{
    "does not exist" => true
  }
}

And when I try to insert a whole post with comment and sub-comments here is how the changeset look like :

#Ecto.Changeset<
  action: nil,
  changes: %{
    hash: ♯78315364456255586b7766696846717a43315879444a6f4672416e39767a7a396b35583773376a72525256,
    posts: [
      #Ecto.Changeset<
        action: :insert,
        changes: %{
          id: "cd68c55c-26df-4341-a568-7f7e5ce56070"
          hash: ♯324374336e686638364a594a347369524334413348473876746b357a62795a536637564b463831506b56786e6361546236446f3274687a66336a364541694b794447376269436f33504d6438636a694d7344415578574139,
          comments: [
            #Ecto.Changeset<
              action: :insert,
              changes: %{
                id: "ff47883b-a104-4269-8b7b-add298bd77a0",
                post_id: "cd68c55c-26df-4341-a568-7f7e5ce56070"
              },
              errors: [],
              data: #Comment<>,
              valid?: true
            >
          ],
        },
        errors: [],
        data: #Post<>,
        valid?: true
      >,

I don’t have any child record in sub_comments on this one. I have tried to artificially add one etc but I don’t find how to get rid of this message. I just want to have an hierarchical table with a reference to his parent/childs and a reference to the upper object posts.

When I remove the post_id from the cast I don’t have the error anymore but the field post_id in the DB is NULL.
Is that because the post is created in the same insert ? But it works for the parent comment id which is inserted in the same time and well linked. Is that because sub_comments are nested in comment ? If yes how can I make it.

EDIT: I have sort my thought in my brain and my post can be resumed in one question: how can we link a sub object to a upper one (more than one level) that are inserted in the same changeset.

1 Like

I just discovered that my id field is not cast on the Post schema…

1 Like