Does Ecto.Changeset.cast provide a global configuration for empty_strings_to_nil?
0 reputation · 22 Jan 2024, 11:44 UTC
0 reputation · 22 Jan 2024, 11:44 UTC
When processing form data or API requests, Ecto.Changeset.cast/4 allows developers to convert empty strings to nil using the empty_strings_to_nil option. This prevents blank strings from being persisted in database columns where NULL is the preferred representation of missing data.
Currently, this behavior is typically managed on a per-changeset basis. In large applications with numerous schemas, applying this option to every individual changeset increases the risk of inconsistency, where some fields store empty strings and others store nil for the same logical state.
What is the recommended approach for enforcing a project-wide policy on empty string conversion without manually adding the option to every changeset? Is there a supported global configuration within Ecto to standardize this behavior across all casts?
31275 reputation · 22 Jan 2024, 19:42 UTC
There is no global configuration in Ecto that automatically sets empty_strings_to_nil: true for every Ecto.Changeset.cast/4 call. The option must be supplied explicitly on each cast, or you must provide your own helper that injects it.
The cast/4 implementation only accepts an opts keyword list. Internally it looks for the :empty_strings_to_nil flag and applies it to the fields it processes. There is no place in the Ecto source that reads a global configuration value, so the behavior cannot be changed without touching the library itself.
Wrap cast/4 in a helper function
defmodule MyApp.Casts do
def cast(changeset, schema, params, required, optional) do
Ecto.Changeset.cast(changeset, schema, params, required, optional, empty_strings_to_nil: true)
end
end
# Usage
changeset = MyApp.Casts.cast(%MyApp.User{}, params, [:name], [:age])
Define a macro that injects the option
defmacro cast_with_nil(changeset, schema, params, required, optional) do
quote do
Ecto.Changeset.cast(unquote(changeset), unquote(schema), unquote(params),
unquote(required), unquote(optional), empty_strings_to_nil: true)
end
end
Use Phoenix LiveView’s form handling
When you use form_for or live_form in a LiveView, Phoenix automatically sets empty_strings_to_nil: true on the underlying changeset. This covers the majority of web‑form use cases, but it does not affect API endpoints or other contexts.
cast/4 call.nil.NULL is persisted.Are you using Phoenix LiveView for form submissions, or are all casts occurring in plain Elixir modules? Knowing this will help decide whether the LiveView automatic conversion suffices or a custom wrapper is required.
Use comments to ask for clarification. Post a solution as an answer.
No question comments on this page.