DI with Entity Framework Entity - c#

I want to add a validation class to an Entity, so it can check it is valid before being entered into the database. (The check is for business requirements, not db constraints).
I have the class
public class MyEntity
{
private readonly IValidatorFactory _validatorFactory;
public MyEntity(IValidatorFactory validatorFactory)
{
_validatorFactory = validatorFactory;
}
//Entity Properties Removed For Clarity
public void Validate()
{
if(_validatorFactory == null)
{
throw new ArgumentNullException("Validator Factory was null, cannot validate this item");
}
var validator = _validatorFactory.GetValidator(this.ItemTypeId);
valid = validator.Validate();
}
}
Using dependency injection, I am struggling to see how I can cleanly resolve the dependency when the project uses EF6. If I return a DbSet, it will of course not know about the requirement for the validator. A parameterless constructor is required.

Firstly, I don't think you should be trying to use DI with your entities. Validation should probably also occur within your entity itself rather than using an external validator (passed into the Validate method or created with a ValidatorFactory).
Entity Framework has multiple ways to do validation built in. Have you tried any of those?
The simplest form would be adding attributes to properties, such as Required and StringLength. For more complex validation you could have your entities implement IValidateObject or override DbContext.ValidateEntity.
Using any of those methods a DbEntityValidationException will be raised when validation fails when you call DbContext.SaveChanges. You can also trigger validation without throwing exceptions by calling DbContext.GetValidationErrors.

The need for an external validator feels like a smell to me - not to mention the convoluted ValidatorFactory.
If you want to avoid the anemic domain antipattern as you rightly said, you might as well include validation in the entities themselves and keep them valid at all times.
Another thing that doesn't make sense to me is that you identified 4 entities with "different business requirements and validation rules". IMO this is precisely where you need the specificity of ad hoc entities each enforcing its own rules internally, as opposed to the genericity of an external Validator abstraction.
Regarding the similar part of your 4 entities, i.e. the data, I would try to extract it to meaningful Value Objects and compose your entities of these objects.

Related

Implementing a domain service with DDD in C#

I'm working on a domain model writing my software all DDD and stuff doing a great job, when I suddenly bump into the same problem I have been facing over and over again and now it's time to share some insights. The root of the problem lies in the uniqueness of data.
For example, let's say we're writing this awesome domain model for a user. Obviously the username is unique and just to be as flexible as possible we want the user to be able to change his name, so I implemented the following method:
public void SetUsername(string value)
{
if (string.IsNullOrWhiteSpace(value))
{
throw new UserException(UserErrorCode.UsernameNullOrEmpty,
"The username cannot be null or empty");
}
if (!Regex.IsMatch(value, RegularExpressions.Username))
{
throw new UserException(UserErrorCode.InvalidUsername,
"The username {value} does not meet the required ");
}
if (!Equals(Username, value))
{
Username = value;
SetState(TrackingState.Modified);
}
}
Again, this is all fine and fancy, but this function lacks the ability to check if the username is unique or not. So writing all these nice articles about DDD, this would be a nice use-case for a Domain Service. Ideally, I would inject that service using dependency injection but this ruins the constructor of my domain model. Alternatively, I can demand an instance of a domain service as a function argument like so: public void SetUsername(string value, IUsersDomainService service) and to be honest I don't see any solid alternatives.
Who has faced this problem and maybe came up with a nice rock-solid solution?
I agree with #TomTom. But as most times with software decisions, it depends, there is almost always a tradeoff. As a rule of thumb, you gain more by not injecting a domain service into an entity. This is a common question when one is starting with DDD and CQRS+ES. And has been thoroughly discussed in the CQRS mailing list here
However, there are some cases where the approach you suggested (known as method injection) might be beneficial it depends on the scenario. I’ll try and drive some analysis points next.
Consider the case where you want to make some validation before creating an entity. Let's think of a hypothetical and way oversimplified international banking context, with the following entity:
public class BankNote
{
private BankNote() {}
public static FromCurrency(
Currency currency,
ISupportedCurrencyService currencyService)
{
currencyService.IsAvailable(currency);
}
}
I am using the factory method pattern FromCurrency inside your entity to abstract the entity creation process and add some validation so that the entity is always created in the correct state.
Since the supported currencies might change overtime, and the logic of which currencies are supported is a different responsibility than the bank note issuing logic, injecting the ISupportedCurrencyService in the factory method gives us the following benefits:
By the way, the method dependency injection for domain services is suggested in the book: Hands-On Domain-Driven Design with .NET Core
By Alexey Zimarev. Chapter 5 "Implementing the Model" page 120
Pros
The BankNote is always created with a supported Currency, even if the currencies supported change overtime.
Since we are depending on an interface instead of a concrete implementation, we can easily swap and change the implementation without changing the entity.
The service is never stored as an instance variable of the class, so no risk of depending on it more than we need.
Cons
If we keep going this way we might add a lot of dependencies injected into the entity and it will become hard to maintain overtime.
We still are adding a loosely coupled dependency to the entity and hence the entity now needs to know about that interface. We are violating the Single Responsibility Principle, and now you would need to mock the ISupportedCurrencyService to test the factory method.
We can’t instantiate the entity without depending on a service implemented externally from the domain. This can cause serious memory leak and performance issues depending on the scenario.
Another approach
You can avoid all the cons if you call the service before trying to instantiate the entity. Say having a different class for the factory instead of a factory method, and make that separate factory use the ISupportedCurrencyService and only then call the entity constructor.
public class BankNoteFactory
{
private readonly ISupportedCurrencyService _currencyService;
private BankNoteFactory(
ISupportedCurrencyService currencyService)
=> _currencyService = currencyService;
public BankNote FromCurrency(
Currency currency)
{
if(_currencyService.IsAvailable(currency))
return new BanckNote(currency);
// To call the constructor here you would also need
// to change the constructor visibility to internal.
}
}
Using this approach you would end with one extra class and an entity that could be instantiated with unsupported currencies, but with better SRP compliance.

In a repository pattern, how can I integrate domain object factories

I have a project structured like this :
WebSite --> Services --> Repositories --> Domain Objects
I use Entity Framework 6 and Autofac.
I've been told I should remove all construction logic from my domain objects so they remain as POCO as possible. The thing is, I have properties that should be initialized when a new object is created such as CreationDate and UserIdCreatedBy
As an example, if I have a Client object, I would use the following logic in the Client class constructor :
public class Client
{
public Client()
{
this.CreationDate = DateTime.UtcNow;
if (Thread.CurrentPrincipal is CustomPrincipal
&& ((CustomPrincipal)Thread.CurrentPrincipal).CustomIdentity != null
&& ((CustomPrincipal)Thread.CurrentPrincipal).CustomIdentity.User != null)
{
this.UserIdCreatedBy = ((CustomPrincipal)Thread.CurrentPrincipal).CustomIdentity.User.UserId;
}
}
... Properties and such
}
So now, I would like to take this constructor logic out of the domain object into a factory for that object. How can I do it gracefully so that Entity Framework uses it when I call MyContext.Clients.Create()? Is that even possible? I know calling the Thread's CurrentPrincipal is not all that good either, but it's for the example to show the logic could be more complex than a plain default value.
Thanks a lot
Assuming that you use DB storage to store the items (not for manipulations with them) I think you could use separate class for instantiating objects. (Some kind of factory as you described.)
For example, in my apps I often have UserManager class. This class does all work relating to the users creation depending on the login method (email+password, social ID etc). Also this class might contain methods for changing password etc.
UPD:
I use data layer as something that knows how to create/update/read/delete objects from/to database. In addition, class that works with db can has methods like selectByThis, selectByThat etc. So you never need to write something db-specific somewhere in your code, except db layer. (I mean that you never need to write something like .Where(a => a.SomeProp == true), you just use special method for this, so if you change the db you will just have to change your db layer, now whole the project.)
So yes, when I need some special logic for initializing object I use separate class. (Like some kind of manager.) That class does all the work and then just tells the db layer: “hey, I did all the work, so just save this object for me!”
It simplifies the maintenance for you. Also, this is how to follow the rule of single responsibility. One class initialize, do some work and the other class saves.

CommandHandler decorators dependency

I have an issue where I would like my handler to use data generated from the handlers:
UpdateUserProfileImageCommandHandlerAuthorizeDecorator
UpdateUserProfileImageCommandHandlerUploadDecorator
UpdateUserProfileImageCommandHandler
My problem is both architectural and performance.
UpdateUserCommandHandlerAuthorizeDecorator makes a call to the repository (entityframework) to authorize the user. I have other decorators similar to this that should use and modify entities and send it up the chain.
UpdateUserCommandHandler should just save the user to the database. I currently have to make another repository call and update the entity while I could have worked on the entity from the previous decorator.
My issue is that the command only accepts the user Id and some properties to update. In the case where I get the user entity from the Authorize decorator, how can I still work on that entity up the chain? Is it Ok to add that User property to the command and work on that?
Code:
public class UpdateUserProfileImageCommand : Command
{
public UpdateUserProfileImageCommand(Guid id, Stream image)
{
this.Id = id;
this.Image = image;
}
public Stream Image { get; set; }
public Uri ImageUri { get; set; }
}
public class UpdateUserProfileImageCommandHandlerAuthorizeDecorator : ICommandHandler<UpdateUserProfileImageCommand>
{
public void Handle(UpdateUserProfileImageCommand command)
{
// I would like to use this entity in `UpdateUserProfileImageCommandHandlerUploadDecorator`
var user = userRespository.Find(u => u.UserId == command.Id);
if(userCanModify(user, currentPrincipal))
{
decoratedHandler(command);
}
}
}
public class UpdateUserProfileImageCommandHandlerUploadDecorator : ICommandHandler<UpdateUserProfileImageCommand>
{
public void Handle(UpdateUserProfileImageCommand command)
{
// Instead of asking for this from the repository again, I'd like to reuse the entity from the previous decorator
var user = userRespository.Find(u => u.UserId == command.Id);
fileService.DeleteFile(user.ProfileImageUri);
var command.ImageUri = fileService.Upload(generatedUri, command.Image);
decoratedHandler(command);
}
}
public class UpdateUserProfileImageCommandHandler : ICommandHandler<UpdateUserProfileImageCommand>
{
public void Handle(UpdateUserProfileImageCommand command)
{
// Again I'm asking for the user...
var user = userRespository.Find(u => u.UserId == command.Id);
user.ProfileImageUri = command.ImageUri;
// I actually have this in a PostCommit Decorator.
unitOfWork.Save();
}
}
You should not try to pass on any extra data just for the sake of performance. Besides, usng decorators, you can't change the contract. Instead you should allow that user entity to be cached and this should typically be the responsibility of the repository implementation. With Entity Framework this is actually rather straightforward. You can call DbSet.Find(id) and EF will first look up the entity in the cache. This prevents unneeded round trips to the database. I do this all the time.
So the only thing you have to do is add a Find(key) or GetById method to your repository that maps to EF's Find(key) method and you're done.
Furthermore, I agree with Pete. Decorators should be primarily for cross-cutting concerns. Adding other things in decorators can be okay sometimes, but you seem to split up the core business logic over both the handler and its decorators. Writing the file to disk be longs to the core logic. You might be conserned about adhering to the Single Responsibility, but it seems to me that your splitting a single responsibility out over multiple classes. That doesn't mean that your command handlers should be big. As Pete said, you probably want to extract this to a service and inject this service into the handler.
Validating the authorization is a cross-cutting concern, so having this in a decorator seems okay, but there are a few problems with your current implementation. First of all, doing it like this will cause you to have many non-generic decorators, which leads to a lot of maintenance. Besides, you silently skip the execution if the user is unauthorized which is typically not what you want.
Instead of silently skipping, consider throwing an exception and prevent the user from being able to call this functionality under normal circumstances. This means that if an exception is thrown, there's either a bug in your code, or the user is hacking your system. Silently skipping without throwing an exception can make it much harder to find bugs.
Another thing is that you might want to consider is trying to implement this authorization logic as generic decorator. For instance have a generc authorization decorator or validation decorator. This might not always be possible, but you might be able to mark commands with an attribute. For instance, in the system I'm currently working on we mark our commands like this:
[PermittedRole(Role.LabManagement)]
We have a AuthorizationVerifierCommandHandlerDecorator<TCommand> that checks the attributes of the command being executed and verifies whether the current user is allowed to execute that command.
UPDATE
Here's an example of what I think your UpdateUserProfileImageCommandHandler could look like:
public class UpdateUserProfileImageCommandHandler
: ICommandHandler<UpdateUserProfileImageCommand>
{
private readonly IFileService fileService;
public UpdateUserProfileImageCommandHandler(IFileService fileService)
{
this.fileService = fileService;
}
public void Handle(UpdateUserProfileImageCommand command)
{
var user = userRespository.GetById(command.Id);
this.fileService.DeleteFile(user.ProfileImageUri);
command.ImageUri = this.fileService.Upload(generatedUri, command.Image);
user.ProfileImageUri = command.ImageUri;
}
}
Why do this via decorators in the first place?
Validation
The normal approach is to have clients do any and all validation required before submitting the command. Any command that is created/published/executed should have all (reasonable) validation performed before submitting. I include 'reasonable' because there are some things, like uniqueness, that can't be 100% validated beforehand. Certainly, authorization to perform a command can be done before submitting it.
Split Command Handlers
Having a decorator that handles just a portion of the command handling logic, and then enriches the command object seems like over-engineering to me. IMHO, decorators should be use to extend a given operation with additional functionality, e.g. logging, transactions, or authentication (although like I said, I don't think that applies for decorating command handlers).
It seems that uploading the image, and then assigning the new image URL in the database are the responsibility of one command handler. If you want the details of those two different operations to be abstracted, then inject your handlers with classes that do so, like IUserimageUploader.
Generally
Normally, commands are considered immutable, and should not be changed once created. This is to help enforce that commands should contain up front all the necessary information to complete the operation.
I'm a little late here, but what I do is define a IUserContext class that you can IoC inject. That way you can load the important user data once and then cache it and all other dependencies can use the same instance. You can then have that data expire after so long and it'll take care of itself.

Validation strategies

I have a business model with many classes in, some logical entities within this model consist of many different classes (Parent-child-grandchild.) On these various classes I define constraints which are invariant, for example that the root of the composite should have a value for Code.
I currently have each class implement an interface like so...
public interface IValidatable
{
IEnumerable<ValidationError> GetErrors(string path);
}
The parent would add a validation error if Code is not set, and then execute GetErrors on each child, which in turn would call GetErrors on each grandchild.
Now I need to validate different constraints for different operations, for example
Some constraints should always be checked because they are invariant
Some constraints should be checked when I want to perform operation X on the root.
Some additional constraints might be checked when performing operation Y.
I have considered adding a "Reason" parameter to the GetErrors method but for a reason I can't quite put my finger on this doesn't feel right. I have also considered creating a visitor and having a concrete implementation to validate for OperationX and another for OperationY but dislike this because some of the constraint checks would be required for multiple operations but not all of them (e.g. a Date is required for OperationX+OperationY but not OperationZ) and I wouldn't like to have to duplicate the code which checks.
Any suggestions would be appreciated.
You have an insulation problem here, as your classes are in charge of doing their own validation, yet the nature of that validation depends on the type of operation you're doing. This means the classes need to know about the kinds of operations that can be performed on them, which creates a fairly tight coupling between the classes and the operations that use them.
One possible design is to create a parallel set of classes like this:
public interface IValidate<T>
{
IEnumerable<ValidationError> GetErrors(T instance, string path);
}
public sealed class InvariantEntityValidator : IValidate<Entity>
{
public IEnumerable<ValidationError> GetErrors(Entity entity, string path)
{
//Do simple (invariant) validation...
}
}
public sealed class ComplexEntityValidator : IValidate<Entity>
{
public IEnumerable<ValidationError> GetErrors(Entity entity, string path)
{
var validator = new InvariantEntityValidator();
foreach (var error in validator.GetErrors(entity, path))
yield return error;
//Do additional validation for this complex case
}
}
You'll still need to resolve how you want to associate the validation classes with the various classes being validated. It sounds like this should occur at the level of the operations somehow, as this is where you know what type of validation needs to occur. It's difficult to say without a better understanding of your architecture.
I would do a kind of attribute-based validation:
public class Entity
{
[Required, MaxStringLength(50)]
public string Property1 { get; set; }
[Between(5, 20)]
public int Property2 { get; set; }
[ValidateAlways, Between(0, 5)]
public int SomeOtherProperty { get; set; }
[Requires("Property1, Property2")]
public void OperationX()
{
}
}
Each property which is passed to the Requires-attribute needs to be valid to perform the operation.
The properties which have the ValidateAlways-attribute, must be valid always - no matter what operation.
In my pseudo-code Property1, Property2 and SomeOtherProperty must be valid to execute OperationX.
Of course you have to add an option to the Requires-attribute to check validation attributes on a child, too. But I'm not able to suggest how to do that without seeing some example code.
Maybe something like that:
[Requires("Property1, Property2, Child2: Property3")]
If needed you can also reach strongly typed property pointers with lambda expressions instead of strings (Example).
I would suggest using the Fluent Validation For .Net library. This library allows you to setup validators pretty easily and flexibly, and if you need different validations for different operations you can use the one that applies for that specific operation (and change them out) very easily.
I've used Sptring.NET's validation engine for exactly the same reason - It allows you to use Conditional Validators. You just define rules - what validation to apply and under what conditions and Spring does the rest. The good thing is that your business logic is no longer polluted by interfaces for validation
You can find more information in documentation at springframework.net I will just copy the sample for the their doc to show how it looks like:
<v:condition test="StartingFrom.Date >= DateTime.Today" when="StartingFrom.Date != DateTime.MinValue">
<v:message id="error.departureDate.inThePast" providers="departureDateErrors, validationSummary"/>
</v:condition>
In this example the StartingFrom property of the Trip object is compared to see if it is later than the current date, i.e. DateTime but only when the date has been set (the initial value of StartingFrom.Date was set to DateTime.MinValue).
The condition validator could be considered "the mother of all validators". You can use it to achieve almost anything that can be achieved by using other validator types, but in some cases the test expression might be very complex, which is why you should use more specific validator type if possible. However, condition validator is still your best bet if you need to check whether particular value belongs to a particular range, or perform a similar test, as those conditions are fairly easy to write.
If you're using .Net 4.0, you can use Code Contracts to control some of this.
Try to read this article from top to bottom, I've gained quite a few ideas from this.
http://codebetter.com/jeremymiller/2007/06/13/build-your-own-cab-part-9-domain-centric-validation-with-the-notification-pattern/
It is attribute based domain validation with a Notification that wraps those validations up to higher layers.
I would separate the variant validation logic out, perhaps with a Visitor as you mentioned. By separating the validation from the classes, you will be keeping your operations separate from your data, and that can really help to keep things clean.
Think about it this way too -- if you mix-in your validation and operations with your data classes, think of what are things going to look like a year from now, when you are doing an enhancement and you need to add a new operation. If each operation's validation rules and operation logic are separate, it's largely just an "add" -- you create a new operation, and a new validation visitor to go with it. On the other hand, if you have to go back and touch alot of "if operation == x" logic in each of your data classes, then you have some added risk for regression bugs/etc.
I rely on proven validation strategy which has implemented in .net framework in 'System.ComponentModel.DataAnnotations Namespace' and for example used in ASP.NET MVC.
This one provides unobtrusive way to apply validation rules (using attributes or implementing IValidatableObject) and facilities to validate rules.
Scott Allen described this way in great article 'Manual Validation with Data Annotations'.
if you want to apply validation attributes on interface then look at MetadataTypeAttribute
to get better understanding how it works look at MS source code

Where should I put a unique check in DDD?

I'm working on my first DDD project, and I think I understand the basic roles of entities, data access objects, and their relationship. I have a basic validation implementation that stores each validation rule with it's associated entity. This works fine for rules that apply to only the current entity, but falls apart when other data is needed. For example, if I have the restriction that a username must be unique, I would like the IsValid() call to return false when there is an existing user with the current name.
However, I'm not finding any clean way to keep this validation rule on the entity itself. I'd like to have an IsNameUnique function on the entity, but most of the solutions to do this would require me to inject a user data access object. Should this logic be in an external service? If so, how do I still keep the logic with the entity itself? Or is this something that should be outside of the user entity?
Thanks!
I like Samuel's response, but for the sake of simplicity, I would recommend implementing a Specification. You create a Specification that returns a boolean to see if an object meets certain criteria. Inject an IUserRepository into the Specification, check if a user already exists with that name, and return a boolean result.
public interface ISpecification<T>
{
bool IsSatisfiedBy(TEntity entity);
}
public class UniqueUsernameSpecification : ISpecification<User>
{
private readonly IUserRepository _userRepository;
public UniqueUsernameSpecification(IUserRepository userRepository)
{
_userRepository = userRepository;
}
public bool IsSatisfiedBy(User user)
{
User foundUser = _userRepository.FindUserByUsername(user.Username);
return foundUser == null;
}
}
//App code
User newUser;
// ... registration stuff...
var userRepository = new UserRepository();
var uniqueUserSpec = new UniqueUsernameSpecification(userRepository);
if (uniqueUserSpec.IsSatisfiedBy(newUser))
{
// proceed
}
In DDD, there ia a concept called aggregate. It is basically responsible for consistency within the application.
IMHO, in this case specifically, I guess the CustomerRepository would be inside something like the "Customer aggregate", being the Customer class the aggregate root.
The root would then be responsible for doing all this stuff, and no one else could access the CustomerRepository options. And there are some possibilities:
The CustomerRepository could throw an exception if the name is not unique (and the Customer would catch and return the error, or something like that)
The CustomerRepository could have an IsValidUserName(), that the Customer would call before doing anything else
Any other option you can think of
I'm going to say that this is simply beyond the scope of DDD.
What you have with DDD is an aggregation of events that produce a useful model. However, data relationships between such models are not necessarily possible.
What consistency model are you using?
If you can commit multiple events in an ACID transaction you can ensure that changes to a group of aggregates happen atomically.
If you use an eventual consistency model you might not be able to actually validate these things until later. And when you do, you might need to compensate for things that have supposedly happened but are no longer valid.
Uniqueness must be answered within a context. If you model is small (in the thousands) you can have an aggregate represent the set of values that you want to be unique. Assuming a group aggregate transaction is possible.
If not, well, then you simply project your model to a database that support an uniqueness constraint. If this projection fails you have to go back to your aggregate and somehow mark it as invalid. All the while you need to consider failure. This is where a distributed long running process, like the saga pattern can be useful but also require that you think about additional things.
In summary, if you cannot use a storage model with a strong consistency guarantee everything becomes a lot more complicated. That said, there are good, well through out patterns for managing failures in a distributed environment but it turns the problem on it's head a bit because now you need to consider failure, at every point along the way, which is a good thing but it will require a bigger time investment.

Categories

Resources