I am new to entity framework, and I've been working on a project lately that I used clean architecture in and found myself in a bit of hassle. should I introduce further abstraction to the already abstracted entity framework in the form of repositories that have single responsibility crud methods or is it better to use services that encapsulate business logic and use ef core straight in there for example (db context or for the case of identity user manager)?
For example, this is my implementation of a service:
public async Task<Result> ChangeEmailAsync(string userId, string confirmationToken, string newEmail)
{
try
{
var user = await userManager.FindByIdAsync(userId);
if (user == null) return Result.Failure(["user Not Found"], StatusCodes.Status404NotFound);
var changeEmailResult = userManager.ChangeEmailAsync(user, newEmail, confirmationToken);
if (!changeEmailResult.Result.Succeeded)
return Result.Failure(changeEmailResult.Result.Errors.Select(error => error.Description).ToArray(),
StatusCodes.Status400BadRequest);
return Result.Success("Email Changed Successfully !");
}
catch (Exception e)
{
logger.LogError("error in method {method} , stackTrace : {stack}", nameof(ChangeEmailAsync), e.StackTrace);
return Result.Failure(["Unexpected error occured"], StatusCodes.Status400BadRequest);
}
}
1 Answer 1
should I introduce further abstraction to the already abstracted entity framework in the form of repositories that have single responsibility crud methods or is it better to use services that encapsulate business logic and use ef core straight in there for example (db context or for the case of identity user manager)?
I'm not sure if I get that correctly, but you seem aware that EF is using Unit Of Work
and Repositories
design patterns. So, wrapping a repository inside another repository would do nothing except adding more code complexity.
So, stick with the Service
design pattern for DbContext
. However, for Services
that already implemented such as UserManager
. You can use Extension methods
, this would keep your code consistence and maintainable.
Lastly, your ChangeEmailAsync
is fine, however, you should be aware of security leaks such as User Not Found
. The system should not tell the user wither the email or user exists or not. As this would open to enumeration vulnerabilities. So, try to conceal the actual error from the user, and just return a success message to the user, but log that in your system. This would make it harder to guess. Always keep your sensitive data concealed, do not let your system messages leak any sensitive information that could be used to attack your system.