Is it ok for a Repository to return boolean values based on objects it (virtually) contains?
For example:
if (userRepository.checkCredentials(username, password))
{
// ...
Or is it a better approach to do it the verbose way:
user = userRepository.findByUsername(username);
if (user != null && user.checkPassword(password)) {
{
// ...
Sounds more like a specification doesn't it?
if (canAuthenticateSpec.isSatisfiedBy(username, password))
In the past, I have done this with a specification, so I can clearly and simply have that check around for my code to use.
But, recently, I did this with a service that does the work, and builds a result based on why they didn't authenticate. So, something, like this:
AuthenticateResult result = slAuthenticator.Authenticate(username, password)
if (result.authenticated) {
user = result.user
} else {
String message = result.failureReason;
A Repository is a mechanism for encapsulating storage, retrieval, and search behavior which emulates a collection of objects.
I think it is OK to return boolean from a repository but only if the method involves all the objects in this repository. Repository usually exposes collection-like interface. For example users.IsEmpty()
or users.IsNameUnique("jdoe")
seem logical because they need access to the whole collection.
In your scenario, only finding user by name is the responsibility that can be assigned to the repository. Checking whether password is valid or not does not seem like a good fit for repository. So the second, more verbose, approach seems better to me.
Alternatively you can have a dedicated Authenticator interface in your domain and implementation in data access layer (similarly to how repositories are implemented). Or Authenticator can become a domain service that uses repository internally. Authenticator can also tell between 'user not found' or 'password invalid' which would probably have different business meaning.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With