Does SaveChanges violate Restful conventions? - breeze

I just finished watching John Pappa's pluralsight training video and was just blown away with how all of the pieces came together.
As I am digesting what I learned I am left with one serious after thought.
As incredibly easy breeze makes the queryable part and the CUD part of data services, the CUD part seems to have too much of a proprietary webapi method signature. It's easy to use and brilliant in how functional it is for its simplicity but we are used to Post, Put and Delete for the CUD part of things. These individual WepApi methods are more to code but they allow explicitly stated logic for saving things. I, for example, only do soft deletes, so an explicitly declared Delete webapi function would allow me to insert a deleted record in to my audit table, mark the record deleted by setting the DeletedDate and then actually not delete the record. Sometimes, based on the role of the person, you want to do overposting protections. For example CreatedDate might be a property in the entity but a client side forced/invalid change in that property should not auto-update the column on the server side. Or, while part of a ServiceTicket entity, the assigned service technician should never be able to be updated by the client unless the user has certain roles.
Where and how can these server side interventions be coded in the SaveChanges method in breeze? And what happens when people expect a fully Post/Put/Delete like "api" and breeze only provides a single method like SaveChanges?
And finally I am assuming that breeze uses the proprietary ContextProvider only because the odata implementation doesn't yet do the expand and select, right? Are there any plans to do away with that extra layer if and once wepapi odata fully implements all the odata verbs? How, if at all, has the 2012 Update 2 changed things in this regard?
Thanks

Related

John Pappa Partials and BreezeJS using direct support in Entity Framework for this versus doing projections in breezejs

Having run into this issue:
Collection navigation properties may NOT be set
myself for exactly the same reason
and posting this suggestion on uservoice
https://breezejs.uservoice.com/forums/173093-breeze-feature-suggestions/suggestions/3796779-repository-sample-that-serves-view-models-
After seeing the great new compact meta-data feature and reviewing the edmunds sample I am trying to put it all together and come up a solution that allows me to serve DTO's/View models versus full domain objects from a ef-codefirst web api back end and I have come up with two scenerios.
1)Use web api to return the DTO's/create the metadata in JS and use the where parameters to do filtering as required) thus as I understand it the entities can be tracked by breeze. The problem with this is that I will have to override save changes and convert dtos/viewmodels back to EF domain objects and save them. I am not certain that this is either as simple/ or as complex as I can see it being. Basically my proposed algorithm for this is to remove root objects and related children from the change set as DTOs and map them back to Domain objects which can then be added to the context and saved (seems like a lot of work and I am not totaly sure that the order this has to be done in is always knowable)
2) Follow Julie Lermans lead from the Pluralsight Enterprise EF couurse and create the partials directly in EF using code first and just let breeze work as designed. (in the course Julie creates stripped down models of Customer which have attributes placed on them that tells EF to map it to the customer table)
I would love to hear anyones thoughts on this. I am personally leaning towards #2 but I may yet be persuaded to choose #1 if there is a chance of a tool to generate the metadata from my C# clases or if the implementation of SaveChanges can be shown to be manageable and not turn into rewriting half of what EF is supposed to be doing for me)
I was looking into the same issue myself and I ended up going with option 2. For my situation, I felt that I had more control going with option 2 and that I was better able to map my data the way I wanted without feeling that I had more layers than my personal project needed. Julie Lermans "Shrink EF Models with DDD Bounded Contexts" (http://msdn.microsoft.com/en-us/magazine/jj883952.aspx) was a very helpful article for me as well.

How do I inspect change-set data on the server before saving it?

A friend asks "Do you have examples or docs on how to inspect the Breeze change-set data on the server and perform server side validation and security checks before committing the data to the database?" My answer follows.
See the "Custom EFContextProvider" topic in the documentation which describes the Breeze.NET facilities for this purpose.
Although this topic targets the EFContextProvider<T> specifically, most of the points apply to the base class, ContextProvider<T>, which is helpful when saving to any kind of data store (see the "NoDb" sample for example).
The app produced by the BreezeMvcSpa template offers a taste of save validation (understood in the broadest sense to include security checks).
The BreezeMvcSpa template will be released Feb 2013 in conjunction with the "ASP.NET and Web Tools 2012.2")
Look at Models/TodoRepository.cs which inherits from EFContextProvider<T>. It overrides BeforeSaveEntity(entityInfo) to confirm that you are always updating/deleting a TodoList/TodoItem that belongs to the current user. It also assigns the current user to a new TodoList. In a real app, this would be a dispatcher to some helper classes dedicated to validating specific entity types, a point I slightly elaborate below.
There are two other important overrides:
BeforeSaveEntities(saveMap) gives you a chance to examine the entire change-set at once. This is a great way to make validate the entire change-set as a whole perhaps to ensure that this save request makes sense as a single transaction. It's also a good place to do some cross-entity checking. BeforeSaveEntities(saveMap) is called after calling BeforeSaveEntity(entityInfo) for each entity individually.
BeforeSaveEntities(saveMap) might be a good dispatch point for delegating validation to dedicated helper classes. I doubt that I would put all of my validation logic in one big ContextProvider class. I don’t mind that all save activity funnels through the ContextProvider.SaveChanges gate but I don’t want to do all the work in the ContextProvider itself.
SaveChangesCore is the other important override. That’s where you do any final pre-save preparation and hand the change-set to something that actually performs the database save (e.g., the DbContext.SaveChanges method). You could intercept the result of the save operation before returning control to the ContextProvider.
Note also that, when using the DbContext, EF applies the validations you prescribe in model attributes, both the standard set and your custom validation attributes.
I have more save advice but this is probably enough to digest right now.

Can a pure DDD approach be used with NHibernate?

I've been reading up on DDD a little bit, and I am confused how this would fit in when using an ORM like NHibernate.
Right now I have a .NET MVC application with fairly "fat" controllers, and I'm trying to figure out how best to fix that. Moving this business logic into the model layer would be the best way to do this, but I am unsure how one would do that.
My application is set up so that NHibernate's session is managed by an HttpModule (gets session / transaction out of my way), which is used by repositories that return the entity objects (Think S#arp arch... turns out a really duplicated a lot of their functionality in this). These repositories are used by DataServices, which right now are just wrappers around the Repositories (one-to-one mapping between them, e.g. UserDataService takes a UserRepository, or actually a Repository). These DataServices right now only ensure that data annotations decorating the entity classes are checked when saving / updating.
In this way, my entities are really just data objects, but do not contain any real logic. While I could put some things in the entity classes (e.g. an "Approve" method), when that action needs to do something like sending an e-mail, or touching other non-related objects, or, for instance, checking to see if there are any users that have the same e-mail before approving, etc., then the entity would need access to other repositories, etc. Injecting these with an IoC wouldn't work with NHibernate, so you'd have to use a factory pattern I'm assuming to get these. I don't see how you would mock those in tests though.
So the next most logical way to do it, I would think, would be to essentially have a service per controller, and extract all of the work being done in the controller currently into methods in each service. I would think that this is breaking with the DDD idea though, as the logic is now no longer contained in the actual model objects.
The other way of looking at that I guess is that each of those services forms a single model with the data object that it works against (Separation of data storage fields and the logic that operates on it), but I just wanted to see what others are doing to solve the "fat controller" issue with DDD while using an ORM like NHibernate that works by returning populated data objects, and the repository model.
Updated
I guess my problem is how I'm looking at this: NHibernate seems to put business objects (entities) at the bottom of the stack, which repositories then act on. The repositories are used by services which may use multiple repositories and other services (email, file access) to do things. I.e: App > Services > Repositories > Business Objects
The pure DDD approach I'm reading about seems to reflect an Active Record bias, where the CRUD functions exist in the business objects (This I call User.Delete directly instead of Repository.Delete from a service), and the actual business object handles the logic of things that need to be done in this instance (Like emailing the user, and deleting files belonging to the user, etc.). I.e. App > (Services) > Business Objects > Repositories
With NHibernate, it seems I would be better off using the first approach given the way NHibernate functions, and I am looking for confirmation on my logic. Or if I'm just confused, some clarification on how this layered approach is supposed to work. My understanding is that if I have an "Approve" method that updates the User model, persists it, and lets say, emails a few people, that this method should go on the User entity object, but to allow for proper IoC so I can inject the messagingService, I need to do this in my service layer instead of on the User object.
From a "multiple UI" point of view this makes sense, as the logic to do things is taken out of my UI layer (MVC), and put into these services... but I'm essentially just factoring the logic out to another class instead of doing it directly in the controller, and if I am not ever going to have any other UI's involved, then I've just traded a "fat controller" for a "fat service", since the service is essentially going to encapsulate a method per controller action to do it's work.
DDD does not have an Active Record slant. Delete is not a method that should be on an Entity (like User) in DDD.
NHibernate does support a DDD approach very well, because of how completely divorced it remains from your entity classes.
when that action needs to do something
like sending an e-mail, or touching
other non-related objects
One piece of the puzzle it seems you are missing is Domain Events. A domain entity shouldn't send an email directly. It should raise an event in the Domain that some significant event has happened. Implement a class whose purpose is to send the email when the event occurs, and register it to listen for the Domain Event.
or, for instance, checking to see if
there are any users that have the same
e-mail before approving
This should probably be checked before submitting the call to "approve," rather than in the function that does the approving. Push the decision up a level in calling code.
So the next most logical way to do it,
I would think, would be to essentially
have a service per controller
This can work, if it's done with the understanding that the service is an entry point for the client. The service's purpose here is to take in parameters in a DTO from the front end/client and translate that into method calls against an entity in order to perform the desired funcitonality.
The only limitations NHibernate creates for classes is all methods/properties must be virtual and a class must have a default constructor (can be internal or protected). Otherwise, it does not [edit] interfere with object structure and can map to pretty complex models.
The short answer to you question is yes, in fact, I find NHibernate enhances DDD - you can focus on developing (and altering) your domain model with a code first approach, then easily retro-fit persistence later using NHibernate.
As you build out your domain model following DDD, I would expect that much of the business logic that's found you way into you MVC controllers should probably reside in your domain objects. In my first attempt at using ASP.NET MVC I quickly found myself in the same position as yourself - fat controllers and an anemic domain model.
To avoid this, I'm now following the approach of keeping a rich domain model that implements the business logic and using MVC's model as essentially simple data objects used by my views. This simplifies my controllers - they interact with my domain model and provide simple data objects (from the MVC model) to the views.
Updated
The pure DDD approach I'm reading about seems to reflect an Active Record bias...
To me the active record pattern means entities are aware of their persistance mechanism and an entity maps directly to a database table record. This is one way of using NHibernate e.g. see Castle Active Record, however, I find this pollutes domain enitities with knowledge of their persistence mechanism. Instead, typically, I'll have a repository per aggregate root in my domain model which implements an abstract repository. The abstract repository provides basic CRUD methods such as:
public IList<TEntity> GetAll()
public TEntity GetById(int id)
public void SaveOrUpdate(TEntity entity)
public void Delete(TEntity entity)
.. which my concrete repositories can supplement/extend.
See this post on The NHibernate FAQ which I've based a lot of my stuff on. Also remember, NHibernate (depending on how you set up your mappings) will allow you to de-persist a complete object graph, i.e. your aggregate root plus all the objects hanging off it and once you've finished working with it, can cascade saves through you entire object graph, this certainly isn't active record.
...since the service is essentially going to encapsulate a method per controller action to do it's work...
I still think you should consider what functionality that you currently have in your controllers should, more logically, be implemented within your domain objects. e.g. in your approval example, I think it would be sensible for an entity to expose an approve method which does whatever it needs to do to within the entity and if, as in your example, needs to send emails, delegate this to a service. Services should be reserved for cross-cutting concerns. Then, once you've finished working with your domain objects, pass them back to your repository to persist changes.
A couple of books I've found useful on these topics are:
Domain-Driven Design by Eric Evans
Applying Domain-Driven Design and Patterns by Jimmy Nilsson

ASP.NET MVC (MVC2) Best practices when Inserting/Updating Data using Linq to SQL and Repository layers

I'm in a bit of a conundrum here and I'm hoping for some of you Guru's to help fill in the blanks.
The situation I'm currently facing is with regards to my "Users" table and my "OpenID" table. My app allows for a user to have multiple OpenID's, so I keep track of them in a separate table.
Users
ID
Username
OpenID
ID
UserID
Claimedidentifier
I have a CRUD repository for each table, and I also have a Service that interfaces with the Repository (one service per repo).
The question I have is with regards to inserting a new user (since updating will follow the same principal). Here are the options that I have in my head.
Have the UserService insert a new user, retrieve the user's ID and then insert a new OpenID using the UserID
Have the UserService send the new user along with the ClaimedIdentifier to the UserRepository, and have the repository insert both the User and the OpenID (this doesn't fit the CRUD methodology very well)
Create a View of both the User table an the OpenID table, create a UsersOpenIDRepository and a UsersOpenIDService, and then insert to the View.
Any other thoughts or suggestions beyond what I can think of will be greatly appreciated.
Please note, I am not using NHibernate whereby I can model my domain however I see fit. I am sticking to Linq to SQL on this project,
In my experience Linq2SQL does not fit the CRUD methodology very well anyway. Making it fit means jumping through too many hoops to be really worth it. The problem you are describing isn't even the one only one - it gets even worse when updating entities.
Therefore I opted for solution 2 (inserting both entities in the usersrepostory) in my current project.
I also gave up on update methods for the repositories. Unstead my repositories simply have a SubmitChanges method which must be called after all updates are performed on loaded entities. All repositories created in the same web request share the same DataContext, so it doesn't really matter which repository I call Submitchanges on. It's not CRUD, but it lends itself much better to the LINQ2SQL way of performing database updates.
If you really absolutely want pure CRUD, you might want to check out EF with the POCO entity generation template.

Where to put auditing or logging?

I'm currently working on an ASP.NET MVC project using NHibernate and I need to keep track of changes on some entities in order to be able to make some reports and queries over the data. For this reason I wanted to have the data in a table, but I'm trying to decide where to "hook" the auditing code.
On the NHibernate layer:
PRO: Powerful event system to track any change
PRO: Nothing can be changed in the application without notice (unless someone uses raw SQL...)
CON: As I have a generic repository... then I have to filter out the useful entities (I don't need to track everything).
CON: I don't have easy access to the controller and the action so I can only track basic operations (update, delete...). I can get the HttpContext at least to get some info.
On an Action Filter at Controller level:
PRO: Full information on the request and web application status. This way I can distinguish an "edit" from a "status change" and be more descriptive in the audit information.
CON: Someone can forget a filter and an important action can be taken without notice which is a big con.
Any clue?
Update: See how to Create an Audit Log using NHibernate Events.
I think doing this at the repository level is a much better fit. Mostly because you may, in the future, decide to add some method of access to your repository which does not go through MVC (e.g., a WCF interface to the data).
So the question becomes, how do you address the cons you've listed about doing it on the NHibernate layer?
Filtering out the useful entities is simple enough. I would probably do this via a custom attribute on the entity type. You can tag the entities you want to track, or the ones you don't; whichever is easier.
Figuring out what the controller really intended is harder. I'm going to dispute that you can "get the HttpContext"; I don't think it is a good idea to do this in a repository, because the separation of concerns. The repository should not be dependent on the web. One method would be to create custom methods on the repository for actions you'd like to track differently; this is especially attractive if there are other aspects of these edits which behave differently, such as different security. Another method is to examine the changes by comparing the old and new versions of the objects and derive the actual nature of the change. A third method is to make no attempt to derive the nature of the change, but just store the before and after versions in the log so that the person who reads the log can figure it out for themselves.
I'd rather put it in the data (NHibernate in your case) layer. Putting it in the controller and asking other people (or yourself, in the future) to implement controllers accordingly conflicts with object-oriented design principles.
I do this with NHibernate. Objects that require auditing implement an IAudtable interface and I use an Interceptor do the auditing on any object that implements IAuditable by intercepting OnFlushDirty, OnDelete, and OnSave.

Resources