I have several backend applications that use their own changesets. In the frontend web application, I want to tie the interaction with these backends together to provide a better user experience. In other words, I want to merge changeset errors that the backend applications return and display those to the user.
The idea would be to use the changeset functions for each backend concern:
def enroll(params) do
enrollment = Portal.Enrollment.changeset(%Portal.Enrollment{}, params) # used for rendering the form
user_changeset = Identity.User.changeset(%Identity.User{}, params)
contact_changeset = Accounts.Contact.changeset(%Accounts.Contact{}, params)
contact_point_changeset = Account.ContactPoint.changeset(%Accounts.ContactPoint, params)
enrollment_changeset =
Enum.reduce([user_changeset, contact_changeset, contact_point_changeset],
enrollment,
fn changeset, acc ->
case Ecto.Changeset.apply_action(changeset, :insert) do
{:ok, _data} ->
acc
{:error, changeset} ->
%{acc | errors: acc.errors ++ changeset.errors}
end
end)
...
end
%Portal.Enrollment{}
is an embedded ecto schema used for rendering the forms on the web frontend.
What do you think of this approach? I guess one criticism would be that I should be more defensive and that these validations would be a better fit closer to the user. However, my concern is incongruity between the backend’s validations and the frontend’s. Do you a different way of managing this?