I am learning elixir with the phoenix framework version 1.7. and it comes with the core_components.
inside you will find
# All other inputs text, datetime-local, url, password, etc. are handled here...
def input(assigns) do
~H"""
<div phx-feedback-for={@name}>
<.label for={@id}><%= @label %></.label>
<input
type={@type}
name={@name}
id={@id}
value={Phoenix.HTML.Form.normalize_value(@type, @value)}
class={[
"mt-2 block w-full rounded-lg text-neutral-50 bg-neutral-800 focus:ring-0 sm: sm:leading-6 border-2",
"phx-no-feedback:border-008B8B phx-no-feedback:focus:border-amber-600",
@errors == [] && "border-008B8B focus:border-amber-600",
@errors != [] && "border-rose-400 focus:border-rose-400"
]}
{@rest}
/>
<.error :for={msg <- @errors}><%= msg %></.error>
</div>
"""
end
However i noticed a small bug. if you say type=“date” and directly pass in the database value of :utc_datetime the field stays empty.
I tried to resolve this by adding my own input type
def input(%{type: "date"} = assigns) do
~H"""
<div phx-feedback-for={@name}>
<.label for={@id}><%= @label %></.label>
<input
type={@type}
name={@name}
id={@id}
value={Phoenix.HTML.Form.normalize_value(@type, if @value do Date.to_iso8601(@value) else @value end)}
class={[
"mt-2 block w-full rounded-lg text-neutral-50 bg-neutral-800 focus:ring-0 sm: sm:leading-6 border-2",
"phx-no-feedback:border-008B8B phx-no-feedback:focus:border-amber-600",
@errors == [] && "border-008B8B focus:border-amber-600",
@errors != [] && "border-rose-400 focus:border-rose-400"
]}
{@rest}
/>
<.error :for={msg <- @errors}><%= msg %></.error>
</div>
"""
end
this works almost like expected as in i can send a date using type=“date” as long as i do this in the controller
def create(conn, %{"task" => task_params}) do
#modify the user input slighly to morph it into the database schema better.
task_params = Map.put(task_params, "creator_id", conn.assigns.current_user.id)
task_params if task_params["due_date"] do
corrected_date = task_params["due_date"] <> " 00:00"
Map.put(task_params, "due_date", corrected_date)
else
task_params
end
#proceed to save task without issue
however the issue that i encounter now is when i start adding validation. For that i am using a <.simple_form> with an ecto changeset.
When anything is invalid i get
“no function clause matching in Date.to_iso8601/2”
the value it gets back is of string “2024-01-01” after trying debug this for a while, but from the database i get back ~U[2024-06-25 00:00:00Z].
The value ~U[2024-06-25 00:00:00Z] seems to work just fine. but “2024-01-01” does not.
Without the Date.to_iso8601(@value)
part the date ~U[2024-06-25 00:00:00Z] will not pass correctly to Phoenix.HTML.Form.normalize_value(“date”, value)
i have tried to write functions that parse dates and strings but i cannot seem to know the difference between the 2 inputs.
I assume i am doing something simply wrong in my approach and welcome any insight in my troubles.
Thanks in advance!