@jodosha Another question came up regarding uniqueness validations. I’m handling them on the database level with an unique index. When this rule is violated an Sequel::UniqueConstraintViolation
error is raised.
How would you handle this in an action? (Taking into consideration that the client should get an response with the errors.)
As far as I can tell handle_exception
doesn’t work in this case since it only takes an HTTP status code. Then I tried to add the error to the errors but could not find an appropriate public API within lotus/validation
. My current solution looks like the following, I’m hoping it can be DRY’ed up a little bit.
module Datsu::Controllers::Identities
class Create
include Datsu::Action
expose :identity
params do
param :identity do
param :email, presence: true
param :password, presence: true
end
end
def initialize(repository = IdentityRepository)
@repository = repository
end
def call(params)
@identity = Identity.new params[:identity]
@repository.create @identity
rescue Sequel::UniqueConstraintViolation
halt_with_error 'identity.email', :uniqueness
end
end
end
module ParameterValidation
private
def validate!
halt_with_errors(error_map) unless params.valid?
end
def error_map
errors.to_h.inject({}) { |hash, (key, value)| hash.merge({ key.to_sym => value.map(&:validation) }) }.to_h
end
def halt_with_errors(errors)
halt 422, JSON.generate({ errors: errors })
end
def halt_with_error(attribute, error)
halt_with_errors({ attribute => [ error ] })
end
end