函数 Ecto.ChangeSet.cast_assoc/3 未定义(模块 Ecto.ChangeSet 不可用)

function Ecto.ChangeSet.cast_assoc/3 is undefined (module Ecto.ChangeSet is not available)

我是 Elixir、Phoenix 和 Ecto 的新手,所以我正在观看视频教程。本教程通过模式为用户设置凭据,每个用户都有一个唯一的凭据。所以我有一个用户:

defmodule Foo.Accounts.User do
  use Ecto.Schema
  import Ecto.Changeset

  alias Foo.Accounts.Credential


  schema "users" do
    field :name, :string
    field :username, :string
    has_one :credential, Credential

    timestamps()
  end

  @doc false
  def changeset(user, attrs) do
    user
    |> cast(attrs, [:name, :username])
    |> validate_required([:name, :username])
    |> unique_constraint(:username)
  end
end

和凭证:

defmodule Foo.Accounts.Credential do
  use Ecto.Schema
  import Ecto.Changeset

  alias Foo.Accounts.User

  schema "credentials" do
    field :email, :string
    belongs_to :user, User

    timestamps()
  end

  def changeset(credential, attrs) do
    credential
    |> cast(attrs, [:email])
    |> validate_required([:email])
    |> unique_constraint(:email)

  end

end

create_user代码是:

  def create_user(attrs \ %{}) do
    %User{}
    |> User.changeset(attrs)
    |> Ecto.ChangeSet.cast_assoc(:credential, with: &Credential.changeset/2)
    |> Repo.insert()
  end

创建凭据代码是

 def create_credential(attrs \ %{}) do
    %Credential{}
    |> Credential.changeset(attrs)
    |> Repo.insert()
  end

当我尝试插入具有完整有效数据的用户时,出现错误

POST/用户未定义函数错误 函数 Ecto.ChangeSet.cast_assoc/3 未定义(模块 Ecto.ChangeSet 不可用)

我也不知道为什么。

错误屏幕显示 Ecto.ChangeSet.cast_assoc/3 使用 3 个参数调用 #Ecto.Changeset, valid?: true> :凭据 [与:&Foo.Accounts.Credential.changeset/2]

用户 %{"email" => "jimmyjobber@emailaddress.com", "name" => "jimmyjobber", "username" => "jimmyjobber"}

来自 Ecto 文档 cast_assoc/3 在处理外部数据时使用。

广泛搜索找到了接近我的问题的文章,但没有任何帮助。

请告诉我我遗漏了什么,以便我可以继续学习本教程。

正如之前的评论所指出的,模块的正确名称是 Ecto.Changeset——大小写很重要!虽然 Elixir 是编译的,但它仍然具有一些 运行 时间灵活性,允许动态模块名称之类的东西:在其他语言中,拼写错误的模块名称将是 compile-time 错误,但在 Elixir 中,这些是 运行-time 错误(!)。 (这是设计使然:它是 Erlang/Elixir 可热插拔并能够更新 运行ning 系统的一部分。

这里的要点是非常注意模块和函数名称的大写。每当您收到“未定义”错误时,请仔细检查您是否正确拼写了模块名称。