【问题标题】:Foreign key not inserted into ecto table外键未插入 ecto 表
【发布时间】:2017-07-12 12:47:08
【问题描述】:

我正在学习 Elixir,现在创建一个包含 users 表和 user_informations 表的应用程序。我试图在user_informations 中查询user_id 但它没有被插入,我不明白为什么,因为所有其他字段都被插入了。

这是 user_informations 表:

def change do
  create table(:user_informations, primary_key: false) do
    add :user_information_id, :uuid, primary_key: true
    add :user_id, references(:users, [column: :user_id, type: :uuid])
    add :full_name, :string
    add :job_title, :string
    add :address, :string
    add :city, :string
    add :country, :string
    add :phone_number, :integer
    add :bio, :string

    timestamps()
  end

  create unique_index(:user_informations, [:user_information_id])
end

UserInformation 模型:

defmodule MyApp.Accounts.UserInformation do
  use Ecto.Schema
  alias MyApp.Accounts
  import Ecto.Changeset

  @primary_key {:user_information_id, Ecto.UUID, autogenerate: true}
  @foreign_key_type Ecto.UUID
  schema "user_informations" do
    field :full_name, :string
    field :job_title, :string
    field :address, :string
    field :city, :string
    field :country, :string
    field :phone_number, :integer
    field :bio, :string

    belongs_to :users, Accounts.User, foreign_key: :user_id

    timestamps()
  end

  @doc """
  Builds a changeset based on the `struct` and `params`.
  """
  def user_details_changeset(struct, params \\ %{}) do
    struct
      |> cast(params, [:full_name, :job_title, :address, :city, :country, :phone_number, :bio])
      |> validate_required([:full_name])
      |> validate_length(:full_name, min: 2)
  end
end

插入user_informations的变更集的函数:

  def update(conn, %{"user_information" => user_information_params}) do
    current_user = Guardian.Plug.current_resource(conn)
    user_information_changeset = Ecto.build_assoc(current_user, :user_informations,
        full_name: user_information_params["full_name"],
        job_title: user_information_params["job_title"],
        address: user_information_params["address"],
        city: user_information_params["city"],
        country: user_information_params["country"],
        phone_number: user_information_params[:phone_number],
        bio: user_information_params["bio"])

    Repo.insert(user_information_changeset)
        conn
        |> put_flash(:info, "Success!")
        |> redirect(to: page_path(conn, :index))
  end

【问题讨论】:

    标签: elixir phoenix-framework ecto


    【解决方案1】:

    我想通了:user_id 参数必须作为额外参数提供给变更集。

    user_information_changeset = Ecto.build_assoc(current_user, :user_informations,
            full_name: user_information_params["full_name"],
            ...
            user_id: current_user.user_id)
    

    【讨论】:

    • 我认为 build_assoc 应该自动为您处理,可能您遗漏了一些东西。
    • 你是对的,显然current_user = Guardian.Plug.current_resource(conn) 不会像 Ecto 期望的那样返回 user_id。因此,我删除了build_assoc 并将变更集实现为%UserInformation{user_id: current_user.user_id, ....}。现在它以正确的方式工作。
    猜你喜欢
    • 2016-12-17
    • 1970-01-01
    • 2016-10-26
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-10-09
    • 1970-01-01
    • 2011-02-06
    相关资源
    最近更新 更多