我使用以下内容:
架构:
defmodule App.Form.ContactForm do
use Ecto.Schema
import Ecto.Changeset
schema "" do
field :name, :string, virtual: true
field :email, :string, virtual: true
field :phone, :string, virtual: true
field :body, :binary, virtual: true
end
def changeset(model, params) do
model
|> cast(params, [:name, :email, :phone, :body])
|> validate_required([:name, :phone])
end
end
上下文:
defmodule App.Form do
alias App.Form.ContactForm
def change_contact(%ContactForm{} = contact \\ %ContactForm{}) do
ContactForm.changeset(contact, %{})
end
def create_contact(attrs \\ %{}) do
contact = ContactForm.changeset(%ContactForm{}, attrs)
contact = Map.merge(contact, %{action: :create}) # because we don't have a Repo call, we need to manually set the action.
if contact.valid? do
# send email or whatever here.
end
contact
end
end
在html中:
<%= form_for @contact, Routes.contact_path(@conn, :contact), [as: "contact"], fn f -> %>
# the form. I leave styling up to you. Errors should be working because we set the action.
在路由器中:
post "/contact", PageController, :contact, as: :contact
以及控制器中两个必要的功能:
def index(conn, _params) do
render(conn, "index.html", contact: App.Form.change_contact())
end
def contact(conn, %{"contact" => contact_params}) do
with changeset <- App.Form.create_contact(contact_params),
true <- changeset.valid?
do
conn
|> put_flash(:success, gettext("We will get back to you shortly."))
|> render("index.html", contact: changeset)
else
_ ->
conn
|> put_flash(:error, gettext("Please check the errors in the form."))
|> render("index.html", contact: App.Form.create_contact(contact_params))
end
end
联系表单的代码很多,这就是我想发布此内容的原因,这样您就不必重写此内容。希望对你有帮助。