I am Serializing an object which has a deep hierarchy of objects.
After deserialization, i am able to access only those fields which were available in object before serialization. For rest, i get LazyInitializationException.
class A {
List<B> objs
}
class B {
C c
}
class C {
D d
}
Initially, i used to get LazyInitializationException while accessing a.objs*.c
Then i executed a loop before serialization: a.objs.each{it.c}
Now I get LazyInitializationException at a.objs*.c.d and not a.objs*.c
How do I make sure that object fetches each reference from DB before serialization?
The only way I can think of is to walk through the object graph initializing any lazy collections you find.
The only other way is to use the mapping closure in each domain class to disable lazy loading.
Could you not refresh the object from the database after deserialization using the refresh() method?
Related
Is it allowed to call components' components according to the Law of Demeter?
By component I mean an object
which was "exclusively" injected into the container or was created in
the container
which has the same life cycle with it's container
For example, Brain is a component of a Dog:
partial class Dog
{
private readonly IBrain brain;
public Dog(IBrain brain)
{
this.brain = brain;
}
}
Here is some information I found:
http://c2.com/cgi/wiki?LawOfDemeter
Your method can call methods on its own fields directly (but not on
the fields' fields)
message target can only be one of the following objects:
... an object referred to by the object's attribute
http://www.ccs.neu.edu/research/demeter/demeter-method/LawOfDemeter/paper-boy/demeter.pdf
A method of an object should invoke only the methods of the following
kinds of objects:
...
any objects it creates/instantiates
its direct component objects
And here is a case:
partial class Dog
{
public void Command(string cmd)
{
var movement = brain.GetMemory().GetMovement(cmd);
skeleton.ExecuteMovement(movement);
}
}
Is it allowed to call components' components according to the Law of Demeter?
By definition this is not allowed since you should Only talk to your immediate friends.
In other words, the IBrain service should not expose its internal services through its interface (assuming that GetMemory() returns an IMemory service of some kind). Instead, the IBrain interface should either provide provide a method that allows retrieving the movement -or- the IMemory should be injected directly intoDog`.
I have a groovy class that looks up a method reference and then invokes it. The method being invoked is a private method. When the actual class is an instance of the child class, it throws an error that it cannot find the private method, even though it is the public method in the parent that actually calls it.
In this case, I could obviously just call pMethod2() directly and that works, but I'm trying to understand why this doesn't work as written and if there's a way to correct it so it works.
class Parent {
def pMethod1() {
def m = this.&pMethod2
m() // this call fails if the calling class is of type Child
}
private def pMethod2() {}
public static void main(String[] args) {
new Child().pMethod1();
}
}
class Child extends Parent {}
It is a bit confusing, especially if you're used to C / C++. What you get when using the ".&" operator in Groovy is not an address, but an instance of MethodClosure.
The MethodClosure object contains an owner and a delegate object, which is used when resolving the method to call. In your example, the owner and delegate object will be "this", which is an instance of Child. The method to call is simply stored as a string.
So, the assignment
m = this.&pMethod2
is just a shorthand way of writing
m = new MethodClosure(this, "pMethod2")
When you invoke the m() closure, it will try to resolve (at runtime) the method by looking for methods named "pMethod2" in the owner and the delegate objects respectively. Since the owner and delegate is an instance of Child, it will not find private methods located in Parent.
To make your example work you must make sure that the method is visible to the owner and/or delegate of the closure.
This can be done several ways, for instance by changing the access modifier of pMethod2 to protected, or by creating the closure with an instance of Parent; something like this:
m = new Parent().&pMethod2
Note that is is irrelevant that you created the MethodClosure instance in a method where pMethod2 is actually visible. It is also irrelevant that you invoke the closure in a method where it is visible. The method is not visible to the owner or delegate of the MethodClosure, which is what is being used when resolving the method.
To best describe what I want to happen, i'll show what i'm doing, as to me it makes sense that this would work ...
public class foo()
{
public foo()
{
MyContext db = new MyContext();
foobar = db.foobar.first();
this = Mapper.Map<bar, foo>(foobar);
}
}
Basically, I want to use automapper within the destination class to map from the source class within the destination classes constructor.
Is there a way to do this?
You cannot do this because this is read only in C#. You cannot assign this a value in the constructor. Not cool to try to change the reference of an object in its constructor. You will have to do the mapping manually and assign each individual property. I would also question if it as a good practice to assign an object values from a database or service in a default constructor. It is not very transparent to the user of the object what is going on and you can get an exception in your constructor.
I'm doing things considered horrible by some lately, but I personally enjoy this kind of experiment. Here's a telegraph style description:
Use NH to fetch data objects
Each DataObject is wrapped by a CastleDynamicProxy
When Properties decorated with Custom Attributes are queried, redirect to own code instead of NHibernate to get Returnvalue.
Object creation / data fetch code
Objects=GetAll().Select(x=>ProxyFactory.CreateProxy<T>(x)).ToList();
public IList<Person> GetAll()
{
ISession session = SessionService.GetSession();
IList<Person> personen = session.CreateCriteria(typeof(Person))
.List<Person>();
return personen;
}
The Proxy generation Code:
public T CreateProxy<T>(T inputObject)
{
T proxy = (T)_proxyGenerator.CreateClassProxy(typeof(T), new ObjectRelationInterceptor<T>(inputObject));
return proxy;
}
The Interceptor used is defined like so:
public class MyInterceptor<T> : IInterceptor
{
private readonly T _wrappedObject;
public MyInterceptor(T wrappedObject)
{
_wrappedObject = wrappedObject;
}
public void Intercept(IInvocation invocation)
{
if (ShouldIntercept(invocation)) { /* Fetch Data from other source*/ }
else
{
invocation.ReturnValue = invocation.Method.Invoke(_wrappedObject, invocation.Arguments);
}
}
public bool ShouldIntercept(IInvocation invocation)
{
// true if Getter / Setter and Property
// has a certain custom attribute
}
}
This works fine in an environment without NHibernate (creating objects in code, where the Object holds its own data).
Unfortunately, the else part in the Intercept method seems to leave NHibernate unfunctional, it seems the _wrappedObject is reduced to it's base type functionality (instead of being proxied by NHibernate), so all mapped Child collections remain empty.
I tried switching from lazy to eager loading (and confirmed that all SQL gets executed), but that doesn't change anything at all.
Does anybody have an idea what I could do to get this back to work?
Thanks a lot in advance!
I found out that what I do is partially wrong and partially incomplete. Instead of deleting this question, I chose to answer it myself, so that others can benefit from it as well.
First of all, I have misunderstood the class proxy to be an instance proxy, which is why i stored the _wrappedObject. I needed the Object to perform invocation.Method.Invoke(_wrappedObject, invocation.Arguments), which is the next mistake. Instead of doing so, I should have passed the call on to the next interceptor by making use of invocation.Proceed().
Now, where was that Incomplete? NH seems to need to know Metadata about it's instances, so I missed one important line to make NH aware that the proxy is one of its kin:
SessionFactory.GetClassMetadata(entityName).SetIdentifier(instance, id, entityMode);
This only works in an NHibernate Interceptor, so the final product differs a bit from my initial one...Enough gibberish, you can see a very very comprehensible example on this on Ayende's website. Big props for his great tutorial!
This question is about OOP in any statically typed language. Suppose I have two classes whose instances maintain pointers/references to each other. In my case, one class is a container, and the other a wrapper around a contained object which maintains a pointer to the container in which it lives.
class Container {
Element[] elements;
}
class Element {
// ... data...
Container holds_me;
}
The constructor of Container creates an Element object to wrap each contained object, and sets their holds_me pointers to itself.
Now I want to inherit from these classes. I want a DerivedContainer class, which inherits from Container and contains DerivedElement objects, where DerivedElement inherits from Element and refers to the containing DerivedContainer object. What is the right way to do this (or is it the wrong thing to do)?
The most straightforward thing is for the constructor of DerivedContainer to create DerivedElements and store them in elements and set their holds_me pointer to itself. Then all the methods of Container and Element will work, but any new methods defined in DerivedContainer and DerivedElement will have to downcast the objects held in elements and holds_me in order to invoke any new methods on them that weren't defined in the base classes. This doesn't seem pretty; so I wonder, is there a better solution?
Yep, this is the right way to do it, without any more information, IMHO. It makes sense if you think that all of the methods in Element can apply to every Element, but the only classes that should know anything about the Derived set of functionality are (ideally only) DerivedElement and (if necessary) DerivedContainer. In other words, to anyone else, Elements and Containers are only Elements and Containers.
You can sometimes do a little better with templates(C++) or generics(Java), since the thought behind these features is that a Container<Element> knows that it holds Elements and a Container<DerivedElement> knows that it holds DerivedElements, but if you have a heterogeneous Container, you really have to have each subclass handle the derived functionality by trying to downcast.
If your language supports it, you could use Generics/Templates. The Container class could have the Elements class as a parameterized type. That way, you can forget about downcasting the Elements.
In case anyone is interested, I've realized that it's possible to do more or less what I originally wanted here using abstract types. Here is some Scala code:
abstract class Container { ctnr =>
type E <: Element
class Element { this : E =>
// data
def holds_me = ctnr
}
var elements : Array[E]
}
The original container is an abstract class containing both a nested class of elements and an abstract type of elements. The subtyping assertion E <: Element requires E to always be a subclass of Element, while the self reference this : E => forces any instantiation of Element to belong to the type E (as instantiated by some implementation of Container).
class ContainerImpl extends Container {
type E = Element
// initialize 'elements' using 'new Element()'
}
abstract class DerivedContainer extends Container {
override type E <: DerivedElement
class DerivedElement extends Element { this : E =>
// more data
}
}
class DerivedContainerImpl extends DerivedContainer {
type E = DerivedElement
// initialize 'elements' using 'new DerivedElement()'
}