I am not sure if this situation would more be related to generics than DTOs, but here it goes:
I have a DTO that represents a Person. A Person can have as children other Person(s) or just ResourceLink to those Person(s). This means that the child can be of either of the 2 types: Person (the DTO) or the ResourceLink. What type it would be, is determined through a queryParam and consequently logically through the flow follwed. I want to represent them using just ONE collection object and am not aware of the best way to do so.
Here is what I have so far:
public class PersonDTO<T> {
#XmlElementWrapper(name = "children")
#XmlElement(name = "child")
List<T> children;
// other stuff
}
With this approach, I need to define the translated type based on an if...else condition.
Earlier I had 2 different collections, one of which remained NULL. I also thought of extracting the relationship thing out in a new DTO as ChildrenDTO (not sure if that's a great idea)
I would like to know if there is a best practice for this situation, otherwise, if it is possible to declare a PersonDTO<PersonDTO> or PersonDTO<ResourceLink> depending on a condition.
Thanks in advance!
I'd suggest instead, using a third type for the elements of List children:
public interface PersonResolver () {
Person resolvePerson ();
}
public class Person implements PersonResolver {
Person resolvePerson () { return this; }
}
public class ResourceLink implements PersonResolver {
Person resolvePerson () {
if (myLinkTargetType == TARGET_TYPE_PERSON)
{ return (Person) myTarget; }
return null;
}
}
Related
I use this code in my application and I find it very ugly.
Is there a smart way of doing this?
for (final ApplicationCategories applicationCategorie : applicationCategories) {
if (applicationCategorie == ApplicationCategories.PROJECTS) {
// invoke right method
} else if (applicationCategorie == ApplicationCategories.CALENDAR) {
// ...
} else if (applicationCategorie == ApplicationCategories.COMMUNICATION) {
} else if (applicationCategorie == ApplicationCategories.CONTACTS) {
} else if (applicationCategorie == ApplicationCategories.DOCUMENTS) {
} else if (applicationCategorie == ApplicationCategories.WORKINGBOOK) {
}
}
My aim is to handle all application categorie enums which contained into the enum list.
The least you can do is to declare the method that handles the behaviour dependent to the enum inside ApplicationCategories. In this way, if you will add a new value to the enum, you will only to change the code relative to enum.
In this way, your code adheres to the Open Closed Principle, and so it is easier to maintain.
enum ApplicationCategories {
PROJECTS,
CALENDAR,
// And so on...
WORKINGBOOK;
public static void handle(ApplicationCategories category) {
switch (category) {
case PROJECTS:
// Code to handle projects
break;
case CALENDAR:
// Code to handle calendar
break;
// And so on
}
}
}
This solution is only feasable if you do not need any external information to handle the enum value.
Remember you can also add fields to enum values.
EDIT
You can also implement a Strategy design pattern if you need. First of all, define a strategy interface and some concrete implementations.
interface CategoryStrategy {
void handle(/* Some useful input*/);
}
class ProjectStrategy implements Strategy {
public void handle(/* Some useful input*/) {
// Do something related to projects...
}
}
class CalendarStrategy implements Strategy {
public void handle(/* Some useful input*/) {
// Do something related to calendars...
}
}
//...
Then, you can modify your enum in order to use the above strategy.
enum ApplicationCategories {
PROJECTS(new ProjectStrategy()),
CALENDAR(new CalendarStrategy()),
// And so on...
WORKINGBOOK(new WorkingBookStrategy());
private CategoryStrategy strategy;
ApplicationCategories(CategoryStrategy strategy) {
this.strategy = strategy;
}
public static void handle(ApplicationCategories category) {
category.strategy.handle(/* Some inputs */);
}
}
Clearly, the above code is only a sketch.
The design pattern you need is the Strategy.
Enums and violation of the Open/Closed Principle
The use of enums when you have to perform a different action for each defined value is a bad practice. As the software evolves, it is likely that you have to spread the if chain around different places. If you add a new enum value, you'll have to add a new if for that value in all these places. Since you may not even be able to find all the places where you have to include the new if, that is a source for bugs.
Such approach also violates the Open/Closed Principle (OCP). Just creating a method to handle each enum value doesn't make your code conformant to OCP. It will make the code more organised but doesn't change anything about the "if" issue.
Java 7 solution with Strategy Pattern
Using Java 7 or prior, you can define a ApplicationCategory interface that all categories will implement. This interface will provide a common method that each category will implement to perform the required actions for that category:
public interface ApplicationCategory {
boolean handle();
}
Usually your method should return something. Since I don't know what is your exact goal, I'm making the method to return just a boolean. It would indicate if the category was handled or not, just as an example.
Then you have to define a class implementing such an interface for each category you have. For instance:
public class CalendarCategory implements ApplicationCategory {
boolean handle(){
//the code to handle the Calendar category
return true;
}
}
public class CommunicationCategory implements ApplicationCategory {
boolean handle(){
//the code to handle the Communication category
return true;
}
}
Now you don't need the enum class and the handle method that was inside it needs to be moved elsewhere, that completely depends on your project. That handle method will be changed to:
public static void handle(ApplicationCategory category) {
//Insert here any code that may be executed,
//regardless of what category it is.
category.handle();
}
You don't need an enum anymore because any variable declared as ApplicationCategory just accepts an object that implements such an interface. If you use the enum together with the Strategy implementation, it will be yet required to change the enum class any time you add a new ApplicationCategory implementation, violating the OCP again.
If you use the Strategy pattern, you don't even need the enum anymore in this case.
Java 8 solution with functional programming and Strategy Pattern
You can more easily implement the Strategy pattern using functional programming and lambda expressions, and avoid the proliferation of class just to provide different implementations of a single method (the handle method in this case).
Since the handle method is not receiving any parameter and is retuning something, this description conforms to the Supplier functional interface. An excellent way to identify what kind of functional interface a method you are defining conforms to, it is studying the java.util.function package.
Once the type of functional interface is identified, we can create just a ApplicationCategory class (that in the Java 7 example was an interface) in a functional way, defining the previous handle method as an attribute of the Supplier type. You must define a setter for this handle attribute to enable changing the handle implementation. Defining a method as an attribute, you are enabling such a method implementation to be changed in runtime, providing a different but far simpler, easier and more maintainable implementation of the Strategy pattern.
If you need to use the category name somewhere, for instance to display it in a user interface, you could define an enum inside the ApplicationCategory class. However, there is no direct relation between the enum value and the handle provided. The enum works just as a tag for the category. It is like a "name" attribute in a Person class, that we usually just use to "tag" and print a person.
public class ApplicationCategory {
//insert all categories here
enum Type {CALENDAR, COMMUNNICATION}
/**
* The Supplier object that will handle this category object.
* It will supply (return) a boolean to indicate if the category
* was processed or not.
*/
private Supplier<Boolean> handler;
private Type type;
/**
* A constructor that will receive a Supplier defining how to
* handle the category that is being created.
*/
public ApplicationCategory(Type type, Supplier<Boolean> handler){
Objects.requireNonNull(type);
this.handler = handler;
setType(type);
}
/**
* Handle the category by calling the {#link Supplier#get()} method,
* that in turn returns a boolean.
*/
public boolean handle(){
return supplier.get();
}
public Type getType(){ return type; }
public final void setHandler(Supplier<Boolean> handler){
Objects.requiredNonNull(handler);
this.handler = handler;
}
}
If you give the behaviour that will handle the enum value at the enum constructor call, as suggested by the other answer provided here, then you don't have how to change the behaviour in runtime and it in fact doesn't conform to the Strategy pattern. Unless you really don't need that, you might implement in that way, but remember it violates the OCP.
How to use the Java 8 functional ApplicationCategory class
To instantiate a ApplicationCategory you have to provide the Type (an enum value) and the handler (that is a Supplier and can be given as a lambda expression). See the example below:
import static ApplicationCategory.CALENDAR;
public class Test {
public static void main(String args[]){
new Test();
}
public Test(){
ApplicationCategory cat = new ApplicationCategory(CALENDAR, this::calendarHandler);
System.out.println("Was " + cat + " handled? " + cat.handle());
}
private boolean calendarHandler(){
//the code required to handle the CALENDAR goes here
return true;
}
}
The this::calendarHandler instruction is a method reference to pass a "pointer" to the calendarHandler method. It is not calling the method (you can see that due to the use of :: instead of . and the lack of parenthesis), it is just defining what method has to be in fact called when the handle() method is called, as can be seen in System.out.println("Was " + cat + " handled? " + cat.handle());
By using this approach, it is possible to define different handlers for different instances of the same category or to use the same handler for a subset of categories.
Unlike other languages, Java provides facilities that specifically allow this sort of thing to be done in a safe object-oriented way.
Declare an abstract method on the enum, and then specific implementations for each enum constant. The compiler will then ensure that every constant has an implementation and nobody has to worry about missing a case somewhere as new values are added:
enum ApplicationCategories {
PROJECTS {
void handle() {
...
}
},
...
public abstract void handle();
}
Then, instead of calling some static handle(category), you just call category.handle()
The website that I'm working on is heavily depending on ajax/json and knockout.js.
I would like to have a lot of my Controllers return view-tailored 'json objects', without wrapping them in a JsonResult when returning the method.
This would mean I could easily composite multiple calls into one parent object, but still be able to call the Actions separately too.
Simplified example:
public object Main(int groupId)
{
var viewModel = new
{
Persons = Employees(groupId),
Messages = AllMessages()
};
return viewModel;
}
public object Employees(int groupId)
{
return DatabaseContext.Employees.Where(e => e.GroupId == groupId).ToList();
}
public object AllMessages()
{
return DatabaseContext.Messages.ToList();
}
I was hoping I could capture the returned object in OnActionExecuted and at that point wrap the whole result up in a final JsonResult.
The result is already converted to a string and captured in a ContentResult though.
Any ideas? :) Thanks,
A good approach on this is to create helper methods for your entity calls. Or if you have those methods already somewhere, they can actually serve as the helper methods. In that manner you can return a list of strongly-typed Messages and Employees as well as returning your desired parent object. You can then have individual controller methods that returns json objects. In addition, you can extend the parent viewmodel to return additional fields.
The Parent ViewModel
public class ParentModel {
public Employee Persons {get;set;}
public Message Messages {get;set;}
}
The Helper Methods
The beauty of using helper methods similar to what is defined here is that you can apply a few more logic to your query, and more, and you don't have to change anything in your controller methods.
public ParentModel GetMain(int groupId)
{
var viewModel = new ParentModel
{
Persons = Employees(groupId),
Messages = AllMessages()
};
return viewModel;
}
public IEnumerable<Employee> Employees(int groupId)
{
return DatabaseContext.Employees.Where(e => e.GroupId == groupId).ToList();
}
public IEnumerable<Message> AllMessages()
{
return DatabaseContext.Messages.ToList();
}
The Controller Methods
public ActionResult GetParent(int groupId){
return Json(helperinstance.GetMain());
}
public ActionResult GetEmployees(int groupId){
return Json(helperinstance.Employees());
}
public ActionResult GetMessages(int groupId){
return Json(helperinstance.AllMessages());
}
Thanks for the answer. I'm not going for the solution of von v. because I like to keep the boilerplate as small as possible.
In the end I am trying out the following approach. It seems to work pretty well for now, but I still have to test it in real production.
If anyone has some (security) concerns with this, I'm happy to hear them in the comments.
// BaseController
protected override void OnActionExecuting(ActionExecutingContext filterContext)
{
var returnType = ((ReflectedActionDescriptor)filterContext.ActionDescriptor).MethodInfo.ReturnType;
// is the returnType not deriving from ActionResult? Automatically wrap it in a JsonResult
if ( !typeof(ActionResult).IsAssignableFrom(returnType) )
{
var result = filterContext.ActionDescriptor.Execute(filterContext, filterContext.ActionParameters);
filterContext.Result = Json( result );
}
}
In MVC3 Code First EF how do you associate one entity with another without creating a new one (many-to-many)?
So I have a many-to-many relationship between class1 and class2. I need class1 to hold many class2 and vice versa. However, class2 is independent; I have a list of them that I want to edit separately and then associate with a new class1.
When I pass my class2List to the controller( via AJAX and JSON), I checked and all the Ids of the class2s correspond to existing ids in the db, i.e. new class2s are not created.
Model
class
{
[key]
public int Id {set; get;}
}
class1 : class
{
private ICollection<class2> _class2s;
public virtual ICollection<class2> class2s
{
get { return _class2s ?? ( _class2s = new HashSet<class2>()); }
set { _class2s = value; }
}
}
class2 : class
{
private ICollection<class1> _class1s;
public virtual ICollection<class1> class1s
{
get { return _class1s ?? ( _class1s = new HashSet<class1>()); }
set { _class1s = value; }
}
}
Controller
public ActionResult SaveChanges(List<class2> class2List)
{
createNewClass2AndAssociateExistingClass2s(class2List);
SaveChangesToDb();
return View("ProductDetail", Model);
}
createNewClass2AndAssociateExistingClass2s(List<class2> class2List)
{
var newClass1 = newClass1()
{
class2s = class2List;
}
////UnitOfWork allows me to access several DbSets in one transaction
unitOfWork.Create(newClass1)
}
SaveChangesToDb()
{
unitOfWork.Commit();
}
What this does is create a new class1 (as it should) but instead of associating the existing class2s with it, it makes new class2s with new Ids and adds them to the database.
My question:
Does this have to do with how EF is reading my Id property from base class?
How would I be able to associate several existing class2s as a list with a new class1, without creating new class2s in the database?
Cheers
Ok so two things I learned from figuring this out:
I was inheriting from an abstract class when I should have been implementing an interface. This is a great idea if you have several entities that have a similar property such as "Id" and you want to do something like
T FindById<T>(int id) where T : IEntity
When making associations in EF, even if the Id matches an existing entry, it will not update that entry, unless EF is tracking that entry in the context, as it says here. What I needed to do was:
Add a method in the mapping layer that gets the entry by id that I
want from the repository
Copy the attributes of the new entry into that context entry
Return the context entry
Hope this helps someone
I'm using EF 4.1 to build a domain model. I have a Task class with a Validate(string userCode) method and in it I want to ensure the user code maps to a valid user in the database, so:
public static bool Validate(string userCode)
{
IDbSet<User> users = db.Set<User>();
var results = from u in users
where u.UserCode.Equals(userCode)
select u;
return results.FirstOrDefault() != null;
}
I can use Moq to mock IDbSet no problem. But ran into trouble with the Where call:
User user = new User { UserCode = "abc" };
IList<User> list = new List<User> { user };
var users = new Mock<IDbSet<User>>();
users.Setup(x => x.Where(It.IsAny<Expression<Func<User, bool>>>())).Returns(list.AsQueryable);
Initialization method JLTi.iRIS3.Tests.TaskTest.SetUp threw exception.
System.NotSupportedException: System.NotSupportedException: Expression
references a method that does not belong to the mocked object:
x => x.Where<User>(It.IsAny<Expression`1>()).
Other than creating a level of indirection (eg, using a ServiceLocator to get an object that runs the LINQ and then mock that method) I can't think of how else to test this, but I want to make sure there is no way before I introduce another layer. And I can see this kind of LINQ queries will be needed quite often so the service objects can quickly spiral out of control.
Could some kind soul help? Thanks!
There is an article on MSDN highlighting how to mock using moq:
The gist of it is to represent linq to entities operations with linq to objects.
var mockSet = new Mock<DbSet<Blog>>();
mockSet.As<IQueryable<Blog>>().Setup(m => m.Provider).Returns(data.Provider);
mockSet.As<IQueryable<Blog>>().Setup(m => m.Expression).Returns(data.Expression);
mockSet.As<IQueryable<Blog>>().Setup(m => m.ElementType).Returns(data.ElementType);
mockSet.As<IQueryable<Blog>>().Setup(m => m.GetEnumerator()).Returns(data.GetEnumerator());
As Ladislav points out there are disadvantages to this as Linq To Objects is simply different to Linq to Entities so it may result in false positives. But it now being an MSDN article it does point that it is at least possible and perhaps recommended in some cases?
One thing that may of changed since the original answers to this post is that the Entity Framework team have opened up areas of Entity Framework in EF 6.0 to make it easier to mock it's inners.
Although I have not tried this, because IDBSet implements IEnumerable you might have to mock the enumerator method so the linq statements will pick up your list of users. You don't actually want to mock linq but by the looks of your code you want to test whether you are finding the right user based on the UserCode which I think is a valid unit test.
var user = new User { UserCode = "abc" };
var list = new List<User> { user };
var users = new Mock<IDbSet<User>>();
users.Setup(x => x.GetEnumerator()).Returns(list.GetEnumerator());
You might get a conflict with the non-generic version of the GetEnumerator but it this might help you on the right track.
Then you have to then place the mocked object on the data context which depends on other code that we don't see.
As I know Moq is able to set up only virtual methods of mocked object itself but you are trying to set up extensions (static) method - no way! These methods are absolutely outside of your mock scope.
Moreover that code is hard to test and requires too much initialization to be able to test it. Use this instead:
internal virtual IQueryable<User> GetUserSet()
{
return db.Set<User>();
}
public bool Validate(string userCode)
{
IQueryable<User> users = GetUserSet();
var results = from u in users
where u.UserCode.Equals(userCode)
select u;
return results.FirstOrDefault() != null;
}
You will just need to set up GetUserSet to return your list. Such testing has some major issues:
You are not testing the real implementation - in case of EF mocking sets is stupid approach because once you do it you change linq-to-entities to linq-to-objects. Those two are totally different and linq-to-entities is only small subset of linq-to-objects = your unit tests can pass with linq-to-objects but your code will fail at runtime.
Once you use this approach you cannot use Include because include is dependent on DbQuery / DbSet. Again you need integration test to use it.
This doesn't test that your lazy loading works
The better approach is removing your linq queries from Validate method - just call them as another virtual method of the object. Unit test your Validate method with mocked query methods and use integration tests to test queries themselves.
I found it easier just to write the stub:
internal class FakeDbSet<T> : IDbSet<T>where T : class
{
readonly HashSet<T> _data;
readonly IQueryable _query;
public FakeDbSet()
{
_data = new HashSet<T>();
_query = _data.AsQueryable();
}
public virtual T Find(params object[] keyValues)
{
throw new NotImplementedException("Derive from FakeDbSet<T> and override Find");
}
public T Add(T item)
{
_data.Add(item);
return item;
}
public T Remove(T item)
{
_data.Remove(item);
return item;
}
public T Attach(T item)
{
_data.Add(item);
return item;
}
public void Detach(T item)
{
_data.Remove(item);
}
Type IQueryable.ElementType
{
get { return _query.ElementType; }
}
Expression IQueryable.Expression
{
get { return _query.Expression; }
}
IQueryProvider IQueryable.Provider
{
get { return _query.Provider; }
}
IEnumerator IEnumerable.GetEnumerator()
{
return _data.GetEnumerator();
}
IEnumerator<T> IEnumerable<T>.GetEnumerator()
{
return _data.GetEnumerator();
}
public TDerivedEntity Create<TDerivedEntity>() where TDerivedEntity : class, T
{
return Activator.CreateInstance<TDerivedEntity>();
}
public T Create()
{
return Activator.CreateInstance<T>();
}
public ObservableCollection<T> Local
{
get
{
return new ObservableCollection<T>(_data);
}
}
I'm trying to write a generic method parameter validation functionality that can be chained (fluent interface) to attach more and more validations/checks like:
public void SomeMethod(User user, string description)
{
ParameterHelper
.Create(() => user)
.RejectNull();
ParameterHelper
.Create(() => description)
.RejectNull()
.RejectEmptyString();
// now this would be luxurious
ParameterHelper
.Create(() => new { user = user, desc = description })
.RejectNull(o => o.user)
.RejectNull(o => o.desc)
.RejectEmptyString(o => o.desc);
}
I would like to use this helper class to test method parameters for certain values before using them (most of the time null will be tested).
Current state of affairs
I first started writing static helper class without the Create() method like:
public static class ParameterHelper
{
public static void RejectNull(Expression<Func<T>> expr)
{
if (expr.Compile()().Equals(default(T)))
{
MemberExpression param = (MemberExpression)expr.Body;
throw new ArgumentNullException(param.Member.Name);
}
}
}
But this doesn't allow chaining. That's why I created the Create() method that would return something that can be used by chained extension methods.
The problem
I would like to avoid multiple Compile() calls, so basically my Create() method should return Func<T> and reject methods should be extension methods of Func<T>.
If my Create() does return Func<T> I don't get the chance to read parameter names that should be supplied to various exceptions (using MemberExpression).
If I return Expression<Func<T>> instead I will have to call Compile() in each Reject extension method.
Questions
Is there a C# library that already does this kind of chaining?
If not, what do you suggest how this should be done? Any examples from the web would be warmly welcome.
Additional note
I should point out that complex/long validation invocation code is not an option here, because my current validation is done like:
if (user == null)
{
throw new ArgumentNullException("user");
}
or
if (string.IsNullOrEmpty(description))
{
throw new ArgumentNullException("description");
}
Which has two major drawbacks:
I repeat the same lines of code over and over
it uses magic strings
So validation should be done with a one liner per check as described above in the desired scenario.
There is a simple way to implement such a fluent interface. Your 'ParameterHelper.Create' method should return an instance of some class (this class is named Requirements below). This instance should hold the expression which was passed to Create. Also this class should have Require... instance methods which will validate expression and return this. Requirements class can be a private class inside ParameterHelper. I would also introduce an interface for this requirements chain (this interface is named IRequirements below. Sample:
public static class ParameterHelper
{
public static IRequirements Create<T>(Expression<Func<T>> expression)
{
return new Requirements{ Expression = expression };
}
private class Requirements<T> : IRequirements
{
public readonly Expression<Func<T>> Expression { get; set; }
public IRequirements RejectNull()
{
if (Expression .Compile()().Equals(default(T)))
{
MemberExpression param = (MemberExpression)Expression.Body;
throw new ArgumentNullException(param.Member.Name);
}
return this;
}
// other Require... methods implemented in the same way
}
}
public interface IRequirements
{
IRequirements RejectNull();
}
This approach will allow you implementing your luxurious solution - you just need to add a corresponding parameters to Reject... methods. Also you will probably need to make IRequirements interface generic.
Robert,
I have a library that solves this problem. It is called Bytes2you.Validation (Project). It is fast, extensible, intuitive and easy-to-use C# library providing fluent APIs for argument validation.
It focuses exactly on the problem that you want to solve, but does not use expressions. This is so, because they are a lot slower than just passing the argument name. For a library like that, that is designed to be used everywhere the performance is one of the most critical features.
For example:
Guard.WhenArgument(stringArgument,"stringArgument").IsNullOrEmpty().IsEqual("xxx").Throw();
// Which means - when stringArgument is null or empty OR is equal to "xxx" we will throw exception. If it is null, we will throw ArgumentNullException. If it is equal to "xxx", we will throw ArgumentException.