
A few hours into Fluent nHibernate. I decided to log some of these errors. As time permits I’ll update this one post. Eventually once I’m running smoothly I may do a post on Fluent nHibernate and my findings. This is assuming I stick with it, but so far, so good.
I will also add that the docs for Fluent nHibernate have been very good so far which is why I’m able to ge so far in such a short time. Shout out to Fluent nHibernate team… they need a shorter name though…
Errors
“The element ‘class’ in namespace ‘urn:nhibernate-mapping-2.2′ has invalid child element ‘property’ in namespace ‘urn:nhibernate-mapping-2.2′. List of possible elements expected: ‘meta, jcs-cache, cache, id, composite-id’ in namespace ‘urn:nhibernate-mapping-2.2′.”
Fix: In your mapping class, make sure you have an Id
namespace Store.Domain.Mappings
{
public class Product: ClassMap
{
public Product()
{
Id(c => c.ProductId);
}
}
}
“input string not correct format.”
Although the error shows you the Fluently.Configure… line, it’s probably not your connection string or settings.Fix: make sure ALL properties are virtual, remove any extra parameter settings and continue testing.
Could not initialize proxy – no Session. NHibernate.HibernateException {NHibernate.LazyInitializationException}
I am using Fluent nHibernate with AutoMappings. AutoMapping now implements Lazy Load as a convention. You can either override this everywhere in your application but that would cause a hit to performance and perhaps unecessary loading of date.
The Dilemma
I have a model similar to this:Member.Login.Username
Member is a base class for different types of members.Login object is lazy loaded. Username is self explanatory.
Suppose you’re attempting to Map from this complex object (Member) into a simple Member Edit View or Partial View in your MVC application. I am currently doing something like this:
namespace Store.Web.Controllers
{
MemberProcessingService _service = new MemberProcessingService();
public ActionResult EditMember(long id)
{
Domain.Entities.Member data = _service.GetMember(id);
EditMemberViewDataMapper mapper = new EditMemberViewDataMapper ();
EditMemberViewDataviewdata = mapper.MapFrom(data);
return PartialView("EditMember", viewdata);
}
}
There are a few things in here that could be refactored but for the sake of simplicity, the main issue here is that we’re allowing the _service to handle the ISession. BUT, because we do not know what type of member to expect nor do we want to violate SRP, we do not want the service to do the mapping as this is the job of the controller, to provide the view with data. Any number of actions could be calling the _service.GetMember method, we definitely do not want to be mapping the view data in that method. So how do we get around this error with the session…?
The Fix(?)
Simply put, we need to take the ISession “up” a level so that it reigns from the start of a request through to the end.
This has probably become obvious to you by now as well. We can’t call the Member.Login.Username without loading the Login object and we need a session to do this.
There are a few ways to achieve this, I am now in the process of doing this when I though I’d blog. I will be back later to set out a defined approach.
So far here are some options and reading:
Sharp WebSessionStorage
(scroll down to the /NHibernate/WebSessionStorage.cs: An ISessionStorage
Jeffery Palermo’s ISessionBuilder
ISession builder to maintain a session through the entire WebRequest.
At this point, all my Actions represent an entire request ( or unit of work ). By the time it sends the view/partial view, everything should be complete. I’m not sure what scenario would be outside this understanding but for now that works.
Long story short, I’m going to refactor to better handle the session without necessarily adding that concern directly to the action method.
















Be The First To Comment
Related Post
Please Leave Your Comments Below