Skip to main content


Eclipse Community Forums
Forum Search:

Search      Help    Register    Login    Home
Home » Modeling » EMF » Teneo Parent/Child fetching
Teneo Parent/Child fetching [message #427178] Thu, 05 February 2009 08:10 Go to next message
Flavio Donze is currently offline Flavio DonzeFriend
Messages: 211
Registered: July 2009
Location: Switzerland
Senior Member
Hello Martin

I modeled a Parent/Child relationship in an object called TreeNode.
In my Server/Client application (using Riena to transfer objects) I want
to read the child TreeNodes by my self.
Right now if I read a TreeNode some where in the tree, the whole tree is
loaded.

Well I can not use PersistenceOptions, because this needs to apply only
for this Entity and PersistenceOptions.SET_PROXY wouldn't work anyway
since the objects on the client wouldn't know how to resolve the proxy.

As far as I know using the "FetchType Lazy" also creates proxies.

So what would be the best way to block Teneo/Hibernate to load the childs?

Here the ecore declaration of TreeNode:

<eClassifiers xsi:type="ecore:EClass" name="TreeNode"
eSuperTypes="#//BasicObject">
<eOperations name="addChild">
<eParameters name="node" eType="#//TreeNode"/>
</eOperations>
<eOperations name="getChild" eType="#//TreeNode">
<eParameters name="id" eType="ecore:EDataType
http://www.eclipse.org/emf/2002/Ecore#//EString"/>
</eOperations>
<eOperations name="hasChilds" eType="ecore:EDataType
http://www.eclipse.org/emf/2002/Ecore#//EBoolean"/>
<eStructuralFeatures xsi:type="ecore:EAttribute" name="name"
eType="ecore:EDataType http://www.eclipse.org/emf/2002/Ecore#//EString"/>
<eStructuralFeatures xsi:type="ecore:EReference" name="childs"
upperBound="-1"
eType="#//TreeNode" containment="true"/>
<eStructuralFeatures xsi:type="ecore:EReference" name="object"
eType="#//ObjectRef"
containment="true"/>
<eStructuralFeatures xsi:type="ecore:EReference" name="parent"
eType="#//TreeNode"/>
<eStructuralFeatures xsi:type="ecore:EAttribute" name="type"
eType="ecore:EDataType http://www.eclipse.org/emf/2002/Ecore#//EString"/>
</eClassifiers>


I appreciate any help, I searched the web but couldn't find a fitting
solution.


Prozessmanagement und Qualitätsmanagement Software QMS/IMS
https://www.scodi.ch
Re: Teneo Parent/Child fetching [message #427179 is a reply to message #427178] Thu, 05 February 2009 08:35 Go to previous messageGo to next message
Martin Taal is currently offline Martin TaalFriend
Messages: 5468
Registered: July 2009
Senior Member
Hi Flavio,
Is also the parent of the treenode read? Or 'only' the children?

gr. Martin

Flavio Donzé wrote:
> Hello Martin
>
> I modeled a Parent/Child relationship in an object called TreeNode.
> In my Server/Client application (using Riena to transfer objects) I want
> to read the child TreeNodes by my self.
> Right now if I read a TreeNode some where in the tree, the whole tree is
> loaded.
>
> Well I can not use PersistenceOptions, because this needs to apply only
> for this Entity and PersistenceOptions.SET_PROXY wouldn't work anyway
> since the objects on the client wouldn't know how to resolve the proxy.
>
> As far as I know using the "FetchType Lazy" also creates proxies.
>
> So what would be the best way to block Teneo/Hibernate to load the childs?
>
> Here the ecore declaration of TreeNode:
>
> <eClassifiers xsi:type="ecore:EClass" name="TreeNode"
> eSuperTypes="#//BasicObject">
> <eOperations name="addChild">
> <eParameters name="node" eType="#//TreeNode"/>
> </eOperations>
> <eOperations name="getChild" eType="#//TreeNode">
> <eParameters name="id" eType="ecore:EDataType
> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
> </eOperations>
> <eOperations name="hasChilds" eType="ecore:EDataType
> http://www.eclipse.org/emf/2002/Ecore#//EBoolean"/>
> <eStructuralFeatures xsi:type="ecore:EAttribute" name="name"
> eType="ecore:EDataType http://www.eclipse.org/emf/2002/Ecore#//EString"/>
> <eStructuralFeatures xsi:type="ecore:EReference" name="childs"
> upperBound="-1"
> eType="#//TreeNode" containment="true"/>
> <eStructuralFeatures xsi:type="ecore:EReference" name="object"
> eType="#//ObjectRef"
> containment="true"/>
> <eStructuralFeatures xsi:type="ecore:EReference" name="parent"
> eType="#//TreeNode"/>
> <eStructuralFeatures xsi:type="ecore:EAttribute" name="type"
> eType="ecore:EDataType http://www.eclipse.org/emf/2002/Ecore#//EString"/>
> </eClassifiers>
>
>
> I appreciate any help, I searched the web but couldn't find a fitting
> solution.
>
>


--

With Regards, Martin Taal

Springsite/Elver.org
Office: Hardwareweg 4, 3821 BV Amersfoort
Postal: Nassaulaan 7, 3941 EC Doorn
The Netherlands
Cell: +31 (0)6 288 48 943
Tel: +31 (0)84 420 2397
Fax: +31 (0)84 225 9307
Mail: mtaal@springsite.com - mtaal@elver.org
Web: www.springsite.com - www.elver.org
Re: Teneo Parent/Child fetching [message #427181 is a reply to message #427179] Thu, 05 February 2009 09:30 Go to previous messageGo to next message
Flavio Donze is currently offline Flavio DonzeFriend
Messages: 211
Registered: July 2009
Location: Switzerland
Senior Member
Hey Martin

Thanks for the quick reply!

Both the childs and the parent are read (the whole tree).

The main problem is the children, I could make a workaround (only use the
parent Id instead of a direct TreeNode reference) or even remove the
parent reference.

But if there is a way to block Teneo from reading the parent reference it
would be great.


thanks and greets
Flavio

Martin Taal wrote:

> Hi Flavio,
> Is also the parent of the treenode read? Or 'only' the children?

> gr. Martin

> Flavio Donzé wrote:
>> Hello Martin
>>
>> I modeled a Parent/Child relationship in an object called TreeNode.
>> In my Server/Client application (using Riena to transfer objects) I want
>> to read the child TreeNodes by my self.
>> Right now if I read a TreeNode some where in the tree, the whole tree is
>> loaded.
>>
>> Well I can not use PersistenceOptions, because this needs to apply only
>> for this Entity and PersistenceOptions.SET_PROXY wouldn't work anyway
>> since the objects on the client wouldn't know how to resolve the proxy.
>>
>> As far as I know using the "FetchType Lazy" also creates proxies.
>>
>> So what would be the best way to block Teneo/Hibernate to load the childs?
>>
>> Here the ecore declaration of TreeNode:
>>
>> <eClassifiers xsi:type="ecore:EClass" name="TreeNode"
>> eSuperTypes="#//BasicObject">
>> <eOperations name="addChild">
>> <eParameters name="node" eType="#//TreeNode"/>
>> </eOperations>
>> <eOperations name="getChild" eType="#//TreeNode">
>> <eParameters name="id" eType="ecore:EDataType
>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>> </eOperations>
>> <eOperations name="hasChilds" eType="ecore:EDataType
>> http://www.eclipse.org/emf/2002/Ecore#//EBoolean"/>
>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="name"
>> eType="ecore:EDataType http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>> <eStructuralFeatures xsi:type="ecore:EReference" name="childs"
>> upperBound="-1"
>> eType="#//TreeNode" containment="true"/>
>> <eStructuralFeatures xsi:type="ecore:EReference" name="object"
>> eType="#//ObjectRef"
>> containment="true"/>
>> <eStructuralFeatures xsi:type="ecore:EReference" name="parent"
>> eType="#//TreeNode"/>
>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="type"
>> eType="ecore:EDataType http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>> </eClassifiers>
>>
>>
>> I appreciate any help, I searched the web but couldn't find a fitting
>> solution.
>>
>>


Prozessmanagement und Qualitätsmanagement Software QMS/IMS
https://www.scodi.ch
Re: Teneo Parent/Child fetching [message #427184 is a reply to message #427181] Thu, 05 February 2009 10:48 Go to previous messageGo to next message
Martin Taal is currently offline Martin TaalFriend
Messages: 5468
Registered: July 2009
Senior Member
Hi Flavio,
There is an issue that econtainer parent relations are eagerly loaded (this issue has not been solved at the moment..).
This should however not lead to the load of the children in the whole tree.
On the server where running Teneo, do you need to persist the econtainer relations? This can be disabled through an
option in PersistenceOptions.

Then why does it load the children... A reason that I can think of is that the code that sends the object over the wire
touches the children collection and thereby forces its load. This can be prevented, but can you check if this is indeed
the case?

gr. Martin

Flavio Donzé wrote:
> Hey Martin
>
> Thanks for the quick reply!
>
> Both the childs and the parent are read (the whole tree).
>
> The main problem is the children, I could make a workaround (only use
> the parent Id instead of a direct TreeNode reference) or even remove the
> parent reference.
>
> But if there is a way to block Teneo from reading the parent reference
> it would be great.
>
>
> thanks and greets
> Flavio
>
> Martin Taal wrote:
>
>> Hi Flavio,
>> Is also the parent of the treenode read? Or 'only' the children?
>
>> gr. Martin
>
>> Flavio Donzé wrote:
>>> Hello Martin
>>>
>>> I modeled a Parent/Child relationship in an object called TreeNode.
>>> In my Server/Client application (using Riena to transfer objects) I
>>> want to read the child TreeNodes by my self.
>>> Right now if I read a TreeNode some where in the tree, the whole tree
>>> is loaded.
>>>
>>> Well I can not use PersistenceOptions, because this needs to apply
>>> only for this Entity and PersistenceOptions.SET_PROXY wouldn't work
>>> anyway since the objects on the client wouldn't know how to resolve
>>> the proxy.
>>>
>>> As far as I know using the "FetchType Lazy" also creates proxies.
>>>
>>> So what would be the best way to block Teneo/Hibernate to load the
>>> childs?
>>>
>>> Here the ecore declaration of TreeNode:
>>>
>>> <eClassifiers xsi:type="ecore:EClass" name="TreeNode"
>>> eSuperTypes="#//BasicObject">
>>> <eOperations name="addChild">
>>> <eParameters name="node" eType="#//TreeNode"/>
>>> </eOperations>
>>> <eOperations name="getChild" eType="#//TreeNode">
>>> <eParameters name="id" eType="ecore:EDataType
>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>> </eOperations>
>>> <eOperations name="hasChilds" eType="ecore:EDataType
>>> http://www.eclipse.org/emf/2002/Ecore#//EBoolean"/>
>>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="name"
>>> eType="ecore:EDataType
>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>> <eStructuralFeatures xsi:type="ecore:EReference" name="childs"
>>> upperBound="-1"
>>> eType="#//TreeNode" containment="true"/>
>>> <eStructuralFeatures xsi:type="ecore:EReference" name="object"
>>> eType="#//ObjectRef"
>>> containment="true"/>
>>> <eStructuralFeatures xsi:type="ecore:EReference" name="parent"
>>> eType="#//TreeNode"/>
>>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="type"
>>> eType="ecore:EDataType
>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>> </eClassifiers>
>>>
>>>
>>> I appreciate any help, I searched the web but couldn't find a fitting
>>> solution.
>>>
>>>
>
>
>
>


--

With Regards, Martin Taal

Springsite/Elver.org
Office: Hardwareweg 4, 3821 BV Amersfoort
Postal: Nassaulaan 7, 3941 EC Doorn
The Netherlands
Cell: +31 (0)6 288 48 943
Tel: +31 (0)84 420 2397
Fax: +31 (0)84 225 9307
Mail: mtaal@springsite.com - mtaal@elver.org
Web: www.springsite.com - www.elver.org
Re: Teneo Parent/Child fetching [message #427185 is a reply to message #427184] Thu, 05 February 2009 11:59 Go to previous messageGo to next message
Thomas Schindl is currently offline Thomas SchindlFriend
Messages: 6651
Registered: July 2009
Senior Member
Martin Taal schrieb:
> Hi Flavio,
> There is an issue that econtainer parent relations are eagerly loaded
> (this issue has not been solved at the moment..). This should however
> not lead to the load of the children in the whole tree.
> On the server where running Teneo, do you need to persist the econtainer
> relations? This can be disabled through an option in PersistenceOptions.
>
> Then why does it load the children... A reason that I can think of is
> that the code that sends the object over the wire touches the children
> collection and thereby forces its load. This can be prevented, but can
> you check if this is indeed the case?
>

The last time I talked with the Riena people they said that when
serializing through their Server-API one needs itself define the point
where the object-graph has to end by nulling references in there.

The problem is that this transfers logic from the client to server
because it has to know exactly what data the client needs. This was the
reason I switched to CDO which handles this transparently for me :-)

Tom

--
B e s t S o l u t i o n . at
------------------------------------------------------------ --------
Tom Schindl JFace-Committer
------------------------------------------------------------ --------
Re: Teneo Parent/Child fetching [message #427200 is a reply to message #427184] Thu, 05 February 2009 14:39 Go to previous messageGo to next message
Flavio Donze is currently offline Flavio DonzeFriend
Messages: 211
Registered: July 2009
Location: Switzerland
Senior Member
Hi Martin

Ok so i did some testing. Here a few code snippets:

Properties hibernateProperties = new Properties();
hibernateProperties
.setProperty(Environment.DRIVER,
preferences.getString(ServerPreferencesConstants.DB_DRIVER)) ;
hibernateProperties.setProperty(Environment.URL,
preferences.getString(ServerPreferencesConstants.DB_URL));
hibernateProperties.setProperty(Environment.USER,
preferences.getString(ServerPreferencesConstants.DB_USER));
hibernateProperties.setProperty(Environment.PASS,
preferences.getString(ServerPreferencesConstants.DB_PASS));
hibernateProperties.setProperty(Environment.DIALECT, preferences
.getString(ServerPreferencesConstants.DB_DIALECT));
hibernateProperties.setProperty(Environment.SHOW_SQL,
showSQL.toString());

hibernateProperties.setProperty(PersistenceOptions.INHERITAN CE_MAPPING,
InheritanceType.TABLE_PER_CLASS.name());
hibernateProperties.setProperty(PersistenceOptions.DEFAULT_I D_FEATURE_NAME,
ID_FIELD_NAME);
hibernateProperties.setProperty(PersistenceOptions.ALWAYS_VE RSION,
Boolean.FALSE.toString());
hibernateProperties.setProperty(PersistenceOptions.ADD_INDEX _FOR_FOREIGN_KEY,
Boolean.TRUE.toString());
hibernateProperties.setProperty(PersistenceOptions.FETCH_CON TAINMENT_EAGERLY,
Boolean.FALSE.toString());

I added PersistenceOptions.FETCH_CONTAINMENT_EAGERLY to my normal settings.


To create some test nodes i did the following:

TreeNode parent = create();
parent.setName("parent");
TreeNode c1 = create();
c1.setName("c1");
TreeNode c2 = create();
c2.setName("c2");
parent.addChild(c1);
parent.addChild(c2);
TreeNode cc1 = create();
cc1.setName("cc1");
TreeNode cc2 = create();
cc2.setName("cc2");
c1.addChild(cc1);
c1.addChild(cc2);

EntityTransaction transaction = beginTransaction();
entityManager.merge(parent);
entityManager.merge(c1);
entityManager.merge(c2);
entityManager.merge(cc1);
entityManager.merge(cc2);
transaction.commit();

Basically the following structure:
parent
-c1
-cc1
-cc2
-c2


Then I added some prints in the getChilds() method (I didn't want to
inspect the object, thought that some magical way the childs might get
loaded through that :-) )
public List<TreeNode> getChilds()
System.out.println(getName() + " childs: " + childs);
if (childs != null) {
System.out.println(getName() + " size: " + childs.size());
if (childs.size() > 0) {
System.out.println(getName() + " first: " + childs.get(0));
}
}
if (childs == null) {
childs = new EObjectContainmentEList<TreeNode>(TreeNode.class, this,
SoftmodelerPackage.TREE_NODE__CHILDS);
}
}

Now I execute the query:

Criteria criteria = session.createCriteria(TreeNode.class);
criteria.add(Restrictions.isNull("parent"));
TreeNode result = (TreeNode) criteria.uniqueResult();
result.getChilds().get(0).getChilds();

Both the creation of the TreeNodes and the query happens on the server.
I tried modeling the 'childs' as containment and as not containment.
I always get the following output:

parent childs: [c1, c2]
parent size: 2
parent first: c1
c1 childs: [cc1, cc2]
c1 size: 2
c1 first: cc1

I guess that this is the way it should behave, loading the whole object
which also contains the childs. Then the child nodes are loaded which also
load the whole object ... and so on.
But I would like to have some kind of annotation to block the loading of
references.

greets
Flavio

Martin Taal wrote:

> Hi Flavio,
> There is an issue that econtainer parent relations are eagerly loaded (this
issue has not been solved at the moment..).
> This should however not lead to the load of the children in the whole tree.
> On the server where running Teneo, do you need to persist the econtainer
relations? This can be disabled through an
> option in PersistenceOptions.

> Then why does it load the children... A reason that I can think of is that
the code that sends the object over the wire
> touches the children collection and thereby forces its load. This can be
prevented, but can you check if this is indeed
> the case?

> gr. Martin

> Flavio Donzé wrote:
>> Hey Martin
>>
>> Thanks for the quick reply!
>>
>> Both the childs and the parent are read (the whole tree).
>>
>> The main problem is the children, I could make a workaround (only use
>> the parent Id instead of a direct TreeNode reference) or even remove the
>> parent reference.
>>
>> But if there is a way to block Teneo from reading the parent reference
>> it would be great.
>>
>>
>> thanks and greets
>> Flavio
>>
>> Martin Taal wrote:
>>
>>> Hi Flavio,
>>> Is also the parent of the treenode read? Or 'only' the children?
>>
>>> gr. Martin
>>
>>> Flavio Donzé wrote:
>>>> Hello Martin
>>>>
>>>> I modeled a Parent/Child relationship in an object called TreeNode.
>>>> In my Server/Client application (using Riena to transfer objects) I
>>>> want to read the child TreeNodes by my self.
>>>> Right now if I read a TreeNode some where in the tree, the whole tree
>>>> is loaded.
>>>>
>>>> Well I can not use PersistenceOptions, because this needs to apply
>>>> only for this Entity and PersistenceOptions.SET_PROXY wouldn't work
>>>> anyway since the objects on the client wouldn't know how to resolve
>>>> the proxy.
>>>>
>>>> As far as I know using the "FetchType Lazy" also creates proxies.
>>>>
>>>> So what would be the best way to block Teneo/Hibernate to load the
>>>> childs?
>>>>
>>>> Here the ecore declaration of TreeNode:
>>>>
>>>> <eClassifiers xsi:type="ecore:EClass" name="TreeNode"
>>>> eSuperTypes="#//BasicObject">
>>>> <eOperations name="addChild">
>>>> <eParameters name="node" eType="#//TreeNode"/>
>>>> </eOperations>
>>>> <eOperations name="getChild" eType="#//TreeNode">
>>>> <eParameters name="id" eType="ecore:EDataType
>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>> </eOperations>
>>>> <eOperations name="hasChilds" eType="ecore:EDataType
>>>> http://www.eclipse.org/emf/2002/Ecore#//EBoolean"/>
>>>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="name"
>>>> eType="ecore:EDataType
>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>> <eStructuralFeatures xsi:type="ecore:EReference" name="childs"
>>>> upperBound="-1"
>>>> eType="#//TreeNode" containment="true"/>
>>>> <eStructuralFeatures xsi:type="ecore:EReference" name="object"
>>>> eType="#//ObjectRef"
>>>> containment="true"/>
>>>> <eStructuralFeatures xsi:type="ecore:EReference" name="parent"
>>>> eType="#//TreeNode"/>
>>>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="type"
>>>> eType="ecore:EDataType
>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>> </eClassifiers>
>>>>
>>>>
>>>> I appreciate any help, I searched the web but couldn't find a fitting
>>>> solution.
>>>>
>>>>
>>
>>
>>
>>


Prozessmanagement und Qualitätsmanagement Software QMS/IMS
https://www.scodi.ch
Re: Teneo Parent/Child fetching [message #427201 is a reply to message #427185] Thu, 05 February 2009 14:48 Go to previous messageGo to next message
Flavio Donze is currently offline Flavio DonzeFriend
Messages: 211
Registered: July 2009
Location: Switzerland
Senior Member
The problem is not the transfer itself, the childs shouldn't even be
loaded on the server in the first place.

We evaluated CDO too, but decided us for Riena because we are more
flexible on the server side. Like adding an Audit/Log entry in the same
transaction and stuff like that.

greets
Flavio


Tom Schindl wrote:
> The last time I talked with the Riena people they said that when
> serializing through their Server-API one needs itself define the point
> where the object-graph has to end by nulling references in there.

> The problem is that this transfers logic from the client to server
> because it has to know exactly what data the client needs. This was the
> reason I switched to CDO which handles this transparently for me :-)

> Tom


Prozessmanagement und Qualitätsmanagement Software QMS/IMS
https://www.scodi.ch
Re: Teneo Parent/Child fetching [message #427202 is a reply to message #427200] Thu, 05 February 2009 15:02 Go to previous messageGo to next message
Martin Taal is currently offline Martin TaalFriend
Messages: 5468
Registered: July 2009
Senior Member
Hi Flavio,
You can also completely remove the explicit econtainer mapping (to the relational db) completely by setting
PersistenceOptions.DISABLE_ECONTAINER_MAPPING to true. Then if you load a single object from the database it will never
have its container set, if you load it through the parent (by accessing for example the getChilds collection) then the
object will have the container set.

But to your code snippet. It is true that debugging loads the list (encountered this myself a few times). A really
confusing behavior!
However to test if a list is set you shouldn't test on nullable, you can do the following:
boolean childsAreLoaded = !(child instanceof PersistableEList) || ((PersistableEList<?>) child).isLoaded();
Normally it should return false, if you didn't touch the childs list.

A completely another solution>>
There is a very specific Hibernate feature (never used it myself): the stateless session interface:
StatelessSession session = sessionFactory.openStatelessSession();
it does not load collections at all, you really get the single object and that's all.

gr. Martin

Flavio Donzé wrote:
> Hi Martin
>
> Ok so i did some testing. Here a few code snippets:
>
> Properties hibernateProperties = new Properties();
> hibernateProperties
> .setProperty(Environment.DRIVER,
> preferences.getString(ServerPreferencesConstants.DB_DRIVER)) ;
> hibernateProperties.setProperty(Environment.URL,
> preferences.getString(ServerPreferencesConstants.DB_URL));
> hibernateProperties.setProperty(Environment.USER,
> preferences.getString(ServerPreferencesConstants.DB_USER));
> hibernateProperties.setProperty(Environment.PASS,
> preferences.getString(ServerPreferencesConstants.DB_PASS));
> hibernateProperties.setProperty(Environment.DIALECT, preferences
> .getString(ServerPreferencesConstants.DB_DIALECT));
> hibernateProperties.setProperty(Environment.SHOW_SQL,
> showSQL.toString());
>
>
> hibernateProperties.setProperty(PersistenceOptions.INHERITAN CE_MAPPING,
> InheritanceType.TABLE_PER_CLASS.name());
>
> hibernateProperties.setProperty(PersistenceOptions.DEFAULT_I D_FEATURE_NAME,
> ID_FIELD_NAME);
>
> hibernateProperties.setProperty(PersistenceOptions.ALWAYS_VE RSION,
> Boolean.FALSE.toString());
>
> hibernateProperties.setProperty(PersistenceOptions.ADD_INDEX _FOR_FOREIGN_KEY,
> Boolean.TRUE.toString());
>
> hibernateProperties.setProperty(PersistenceOptions.FETCH_CON TAINMENT_EAGERLY,
> Boolean.FALSE.toString());
>
> I added PersistenceOptions.FETCH_CONTAINMENT_EAGERLY to my normal settings.
>
>
> To create some test nodes i did the following:
>
> TreeNode parent = create();
> parent.setName("parent");
> TreeNode c1 = create();
> c1.setName("c1");
> TreeNode c2 = create();
> c2.setName("c2");
> parent.addChild(c1);
> parent.addChild(c2);
> TreeNode cc1 = create();
> cc1.setName("cc1");
> TreeNode cc2 = create();
> cc2.setName("cc2");
> c1.addChild(cc1);
> c1.addChild(cc2);
>
> EntityTransaction transaction = beginTransaction();
> entityManager.merge(parent);
> entityManager.merge(c1);
> entityManager.merge(c2);
> entityManager.merge(cc1);
> entityManager.merge(cc2);
> transaction.commit();
>
> Basically the following structure:
> parent
> -c1
> -cc1
> -cc2
> -c2
>
>
> Then I added some prints in the getChilds() method (I didn't want to
> inspect the object, thought that some magical way the childs might get
> loaded through that :-) )
> public List<TreeNode> getChilds()
> System.out.println(getName() + " childs: " + childs);
> if (childs != null) {
> System.out.println(getName() + " size: " + childs.size());
> if (childs.size() > 0) {
> System.out.println(getName() + " first: " + childs.get(0));
> }
> }
> if (childs == null) {
> childs = new
> EObjectContainmentEList<TreeNode>(TreeNode.class, this,
> SoftmodelerPackage.TREE_NODE__CHILDS);
> }
> }
>
> Now I execute the query:
>
> Criteria criteria = session.createCriteria(TreeNode.class);
> criteria.add(Restrictions.isNull("parent"));
> TreeNode result = (TreeNode) criteria.uniqueResult();
> result.getChilds().get(0).getChilds();
>
> Both the creation of the TreeNodes and the query happens on the server.
> I tried modeling the 'childs' as containment and as not containment.
> I always get the following output:
>
> parent childs: [c1, c2]
> parent size: 2
> parent first: c1
> c1 childs: [cc1, cc2]
> c1 size: 2
> c1 first: cc1
>
> I guess that this is the way it should behave, loading the whole object
> which also contains the childs. Then the child nodes are loaded which
> also load the whole object ... and so on.
> But I would like to have some kind of annotation to block the loading of
> references.
>
> greets
> Flavio
>
> Martin Taal wrote:
>
>> Hi Flavio,
>> There is an issue that econtainer parent relations are eagerly loaded
>> (this
> issue has not been solved at the moment..).
>> This should however not lead to the load of the children in the whole
>> tree.
>> On the server where running Teneo, do you need to persist the econtainer
> relations? This can be disabled through an
>> option in PersistenceOptions.
>
>> Then why does it load the children... A reason that I can think of is
>> that
> the code that sends the object over the wire
>> touches the children collection and thereby forces its load. This can be
> prevented, but can you check if this is indeed
>> the case?
>
>> gr. Martin
>
>> Flavio Donzé wrote:
>>> Hey Martin
>>>
>>> Thanks for the quick reply!
>>>
>>> Both the childs and the parent are read (the whole tree).
>>>
>>> The main problem is the children, I could make a workaround (only use
>>> the parent Id instead of a direct TreeNode reference) or even remove
>>> the parent reference.
>>>
>>> But if there is a way to block Teneo from reading the parent
>>> reference it would be great.
>>>
>>>
>>> thanks and greets
>>> Flavio
>>>
>>> Martin Taal wrote:
>>>
>>>> Hi Flavio,
>>>> Is also the parent of the treenode read? Or 'only' the children?
>>>
>>>> gr. Martin
>>>
>>>> Flavio Donzé wrote:
>>>>> Hello Martin
>>>>>
>>>>> I modeled a Parent/Child relationship in an object called TreeNode.
>>>>> In my Server/Client application (using Riena to transfer objects) I
>>>>> want to read the child TreeNodes by my self.
>>>>> Right now if I read a TreeNode some where in the tree, the whole
>>>>> tree is loaded.
>>>>>
>>>>> Well I can not use PersistenceOptions, because this needs to apply
>>>>> only for this Entity and PersistenceOptions.SET_PROXY wouldn't work
>>>>> anyway since the objects on the client wouldn't know how to resolve
>>>>> the proxy.
>>>>>
>>>>> As far as I know using the "FetchType Lazy" also creates proxies.
>>>>>
>>>>> So what would be the best way to block Teneo/Hibernate to load the
>>>>> childs?
>>>>>
>>>>> Here the ecore declaration of TreeNode:
>>>>>
>>>>> <eClassifiers xsi:type="ecore:EClass" name="TreeNode"
>>>>> eSuperTypes="#//BasicObject">
>>>>> <eOperations name="addChild">
>>>>> <eParameters name="node" eType="#//TreeNode"/>
>>>>> </eOperations>
>>>>> <eOperations name="getChild" eType="#//TreeNode">
>>>>> <eParameters name="id" eType="ecore:EDataType
>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>> </eOperations>
>>>>> <eOperations name="hasChilds" eType="ecore:EDataType
>>>>> http://www.eclipse.org/emf/2002/Ecore#//EBoolean"/>
>>>>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="name"
>>>>> eType="ecore:EDataType
>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>> <eStructuralFeatures xsi:type="ecore:EReference" name="childs"
>>>>> upperBound="-1"
>>>>> eType="#//TreeNode" containment="true"/>
>>>>> <eStructuralFeatures xsi:type="ecore:EReference" name="object"
>>>>> eType="#//ObjectRef"
>>>>> containment="true"/>
>>>>> <eStructuralFeatures xsi:type="ecore:EReference" name="parent"
>>>>> eType="#//TreeNode"/>
>>>>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="type"
>>>>> eType="ecore:EDataType
>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>> </eClassifiers>
>>>>>
>>>>>
>>>>> I appreciate any help, I searched the web but couldn't find a
>>>>> fitting solution.
>>>>>
>>>>>
>>>
>>>
>>>
>>>
>
>
>
>


--

With Regards, Martin Taal

Springsite/Elver.org
Office: Hardwareweg 4, 3821 BV Amersfoort
Postal: Nassaulaan 7, 3941 EC Doorn
The Netherlands
Cell: +31 (0)6 288 48 943
Tel: +31 (0)84 420 2397
Fax: +31 (0)84 225 9307
Mail: mtaal@springsite.com - mtaal@elver.org
Web: www.springsite.com - www.elver.org
Re: Teneo Parent/Child fetching [message #427214 is a reply to message #427202] Fri, 06 February 2009 09:25 Go to previous messageGo to next message
Flavio Donze is currently offline Flavio DonzeFriend
Messages: 211
Registered: July 2009
Location: Switzerland
Senior Member
ciao Martin

Ok so I tested:
boolean childsAreLoaded = !(child instanceof PersistableEList) ||
((PersistableEList<?>) child).isLoaded();

And it returns false. The debugger tricked me, as mentioned I was
suspecting something like that. Because there I can step through the whole
tree, all TreeNodes are loaded.

Hmm what would you suggest, Riena will definitely access the collection,
on the client side I have an ArrayList instead of an PersistableEList.
Maybe adding a setChilds(List<TreeNode> childs) method to the TreeNode and
calling setChilds(null) before transferring the TreeNode over the wire?
Kind of ugly...

Just as info, I tried using the StatelessSession. But as soon as I want to
access the childs, an exception is thrown:
HessianServiceException: failed to lazily initialize a collection of role:
TreeNode.childs, no session or session was closed

greets
Flavio

Martin Taal wrote:

> Hi Flavio,
> You can also completely remove the explicit econtainer mapping (to the
relational db) completely by setting
> PersistenceOptions.DISABLE_ECONTAINER_MAPPING to true. Then if you load a
single object from the database it will never
> have its container set, if you load it through the parent (by accessing for
example the getChilds collection) then the
> object will have the container set.

> But to your code snippet. It is true that debugging loads the list
(encountered this myself a few times). A really
> confusing behavior!
> However to test if a list is set you shouldn't test on nullable, you can do
the following:
> boolean childsAreLoaded = !(child instanceof PersistableEList) ||
((PersistableEList<?>) child).isLoaded();
> Normally it should return false, if you didn't touch the childs list.

> A completely another solution>>
> There is a very specific Hibernate feature (never used it myself): the
stateless session interface:
> StatelessSession session = sessionFactory.openStatelessSession();
> it does not load collections at all, you really get the single object and
that's all.

> gr. Martin

> Flavio Donzé wrote:
>> Hi Martin
>>
>> Ok so i did some testing. Here a few code snippets:
>>
>> Properties hibernateProperties = new Properties();
>> hibernateProperties
>> .setProperty(Environment.DRIVER,
>> preferences.getString(ServerPreferencesConstants.DB_DRIVER)) ;
>> hibernateProperties.setProperty(Environment.URL,
>> preferences.getString(ServerPreferencesConstants.DB_URL));
>> hibernateProperties.setProperty(Environment.USER,
>> preferences.getString(ServerPreferencesConstants.DB_USER));
>> hibernateProperties.setProperty(Environment.PASS,
>> preferences.getString(ServerPreferencesConstants.DB_PASS));
>> hibernateProperties.setProperty(Environment.DIALECT, preferences
>> .getString(ServerPreferencesConstants.DB_DIALECT));
>> hibernateProperties.setProperty(Environment.SHOW_SQL,
>> showSQL.toString());
>>
>>
>> hibernateProperties.setProperty(PersistenceOptions.INHERITAN CE_MAPPING,
>> InheritanceType.TABLE_PER_CLASS.name());
>>
>> hibernateProperties.setProperty(PersistenceOptions.DEFAULT_I D_FEATURE_NAME,
>> ID_FIELD_NAME);
>>
>> hibernateProperties.setProperty(PersistenceOptions.ALWAYS_VE RSION,
>> Boolean.FALSE.toString());
>>
>>
hibernateProperties.setProperty(PersistenceOptions.ADD_INDEX _FOR_FOREIGN_KEY,
>> Boolean.TRUE.toString());
>>
>>
hibernateProperties.setProperty(PersistenceOptions.FETCH_CON TAINMENT_EAGERLY,
>> Boolean.FALSE.toString());
>>
>> I added PersistenceOptions.FETCH_CONTAINMENT_EAGERLY to my normal settings.
>>
>>
>> To create some test nodes i did the following:
>>
>> TreeNode parent = create();
>> parent.setName("parent");
>> TreeNode c1 = create();
>> c1.setName("c1");
>> TreeNode c2 = create();
>> c2.setName("c2");
>> parent.addChild(c1);
>> parent.addChild(c2);
>> TreeNode cc1 = create();
>> cc1.setName("cc1");
>> TreeNode cc2 = create();
>> cc2.setName("cc2");
>> c1.addChild(cc1);
>> c1.addChild(cc2);
>>
>> EntityTransaction transaction = beginTransaction();
>> entityManager.merge(parent);
>> entityManager.merge(c1);
>> entityManager.merge(c2);
>> entityManager.merge(cc1);
>> entityManager.merge(cc2);
>> transaction.commit();
>>
>> Basically the following structure:
>> parent
>> -c1
>> -cc1
>> -cc2
>> -c2
>>
>>
>> Then I added some prints in the getChilds() method (I didn't want to
>> inspect the object, thought that some magical way the childs might get
>> loaded through that :-) )
>> public List<TreeNode> getChilds()
>> System.out.println(getName() + " childs: " + childs);
>> if (childs != null) {
>> System.out.println(getName() + " size: " + childs.size());
>> if (childs.size() > 0) {
>> System.out.println(getName() + " first: " + childs.get(0));
>> }
>> }
>> if (childs == null) {
>> childs = new
>> EObjectContainmentEList<TreeNode>(TreeNode.class, this,
>> SoftmodelerPackage.TREE_NODE__CHILDS);
>> }
>> }
>>
>> Now I execute the query:
>>
>> Criteria criteria = session.createCriteria(TreeNode.class);
>> criteria.add(Restrictions.isNull("parent"));
>> TreeNode result = (TreeNode) criteria.uniqueResult();
>> result.getChilds().get(0).getChilds();
>>
>> Both the creation of the TreeNodes and the query happens on the server.
>> I tried modeling the 'childs' as containment and as not containment.
>> I always get the following output:
>>
>> parent childs: [c1, c2]
>> parent size: 2
>> parent first: c1
>> c1 childs: [cc1, cc2]
>> c1 size: 2
>> c1 first: cc1
>>
>> I guess that this is the way it should behave, loading the whole object
>> which also contains the childs. Then the child nodes are loaded which
>> also load the whole object ... and so on.
>> But I would like to have some kind of annotation to block the loading of
>> references.
>>
>> greets
>> Flavio
>>
>> Martin Taal wrote:
>>
>>> Hi Flavio,
>>> There is an issue that econtainer parent relations are eagerly loaded
>>> (this
>> issue has not been solved at the moment..).
>>> This should however not lead to the load of the children in the whole
>>> tree.
>>> On the server where running Teneo, do you need to persist the econtainer
>> relations? This can be disabled through an
>>> option in PersistenceOptions.
>>
>>> Then why does it load the children... A reason that I can think of is
>>> that
>> the code that sends the object over the wire
>>> touches the children collection and thereby forces its load. This can be
>> prevented, but can you check if this is indeed
>>> the case?
>>
>>> gr. Martin
>>
>>> Flavio Donzé wrote:
>>>> Hey Martin
>>>>
>>>> Thanks for the quick reply!
>>>>
>>>> Both the childs and the parent are read (the whole tree).
>>>>
>>>> The main problem is the children, I could make a workaround (only use
>>>> the parent Id instead of a direct TreeNode reference) or even remove
>>>> the parent reference.
>>>>
>>>> But if there is a way to block Teneo from reading the parent
>>>> reference it would be great.
>>>>
>>>>
>>>> thanks and greets
>>>> Flavio
>>>>
>>>> Martin Taal wrote:
>>>>
>>>>> Hi Flavio,
>>>>> Is also the parent of the treenode read? Or 'only' the children?
>>>>
>>>>> gr. Martin
>>>>
>>>>> Flavio Donzé wrote:
>>>>>> Hello Martin
>>>>>>
>>>>>> I modeled a Parent/Child relationship in an object called TreeNode.
>>>>>> In my Server/Client application (using Riena to transfer objects) I
>>>>>> want to read the child TreeNodes by my self.
>>>>>> Right now if I read a TreeNode some where in the tree, the whole
>>>>>> tree is loaded.
>>>>>>
>>>>>> Well I can not use PersistenceOptions, because this needs to apply
>>>>>> only for this Entity and PersistenceOptions.SET_PROXY wouldn't work
>>>>>> anyway since the objects on the client wouldn't know how to resolve
>>>>>> the proxy.
>>>>>>
>>>>>> As far as I know using the "FetchType Lazy" also creates proxies.
>>>>>>
>>>>>> So what would be the best way to block Teneo/Hibernate to load the
>>>>>> childs?
>>>>>>
>>>>>> Here the ecore declaration of TreeNode:
>>>>>>
>>>>>> <eClassifiers xsi:type="ecore:EClass" name="TreeNode"
>>>>>> eSuperTypes="#//BasicObject">
>>>>>> <eOperations name="addChild">
>>>>>> <eParameters name="node" eType="#//TreeNode"/>
>>>>>> </eOperations>
>>>>>> <eOperations name="getChild" eType="#//TreeNode">
>>>>>> <eParameters name="id" eType="ecore:EDataType
>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>>> </eOperations>
>>>>>> <eOperations name="hasChilds" eType="ecore:EDataType
>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EBoolean"/>
>>>>>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="name"
>>>>>> eType="ecore:EDataType
>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>>> <eStructuralFeatures xsi:type="ecore:EReference" name="childs"
>>>>>> upperBound="-1"
>>>>>> eType="#//TreeNode" containment="true"/>
>>>>>> <eStructuralFeatures xsi:type="ecore:EReference" name="object"
>>>>>> eType="#//ObjectRef"
>>>>>> containment="true"/>
>>>>>> <eStructuralFeatures xsi:type="ecore:EReference" name="parent"
>>>>>> eType="#//TreeNode"/>
>>>>>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="type"
>>>>>> eType="ecore:EDataType
>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>>> </eClassifiers>
>>>>>>
>>>>>>
>>>>>> I appreciate any help, I searched the web but couldn't find a
>>>>>> fitting solution.
>>>>>>
>>>>>>
>>>>
>>>>
>>>>
>>>>
>>
>>
>>
>>


Prozessmanagement und Qualitätsmanagement Software QMS/IMS
https://www.scodi.ch
Re: Teneo Parent/Child fetching [message #427215 is a reply to message #427214] Fri, 06 February 2009 09:54 Go to previous messageGo to next message
Thomas Schindl is currently offline Thomas SchindlFriend
Messages: 6651
Registered: July 2009
Senior Member
Flavio Donzé schrieb:
> ciao Martin
>
> Ok so I tested:
> boolean childsAreLoaded = !(child instanceof PersistableEList) ||
> ((PersistableEList<?>) child).isLoaded();
>
> And it returns false. The debugger tricked me, as mentioned I was
> suspecting something like that. Because there I can step through the
> whole tree, all TreeNodes are loaded.
> Hmm what would you suggest, Riena will definitely access the collection,
> on the client side I have an ArrayList instead of an PersistableEList.
> Maybe adding a setChilds(List<TreeNode> childs) method to the TreeNode
> and calling setChilds(null) before transferring the TreeNode over the
> wire? Kind of ugly...
>
> Just as info, I tried using the StatelessSession. But as soon as I want
> to access the childs, an exception is thrown:
> HessianServiceException: failed to lazily initialize a collection of
> role: TreeNode.childs, no session or session was closed
>

IMHO this is a solution to the problem. The other one would be to ask
the riena people to provide a possibility to tweak their serializing
concept so that you can stop serializing at a given point.

The 3rd one is that you create specialized data-object objects for
transfering over the wire (=simple POJOs).

Another problem with nulling some parts of your object graph (or tweak
the serializing as suggested above) is what happens with links inside
your object graph (none-containment references) pointing to an entry. I
have to admit that I've never taken a look at the Riena-Serializing
stuff but I expect that it can deal with none-containment-references and
so you are into trouble when simply nulling parts of the object-graph
because others you forgot using the information there are also nulled
because of this.

In the end the problem I wanted to outlined in my first reply is that
the current concept of not supporting lazy-loading strategies is a real
problem to Riena-Services IMHO because the server-service needs to know
exactly what the client needs. A solution to over come this is that the
client tells the server exactly what parts of the object-graph it needs.

So your service interface looks like this:

PersonService#findPersons(int zip, SerializationStrategy strat)

instead of

PersonService#findPersons(int zip)

Tom

--
B e s t S o l u t i o n . at
------------------------------------------------------------ --------
Tom Schindl JFace-Committer
------------------------------------------------------------ --------
Re: Teneo Parent/Child fetching [message #427217 is a reply to message #427214] Fri, 06 February 2009 10:18 Go to previous messageGo to next message
Martin Taal is currently offline Martin TaalFriend
Messages: 5468
Registered: July 2009
Senior Member
Hi Flavio,
Can you override the Rienna serializing so that you can implement your own non-resolving serialization?

gr. Martin

Flavio Donzé wrote:
> ciao Martin
>
> Ok so I tested:
> boolean childsAreLoaded = !(child instanceof PersistableEList) ||
> ((PersistableEList<?>) child).isLoaded();
>
> And it returns false. The debugger tricked me, as mentioned I was
> suspecting something like that. Because there I can step through the
> whole tree, all TreeNodes are loaded.
> Hmm what would you suggest, Riena will definitely access the collection,
> on the client side I have an ArrayList instead of an PersistableEList.
> Maybe adding a setChilds(List<TreeNode> childs) method to the TreeNode
> and calling setChilds(null) before transferring the TreeNode over the
> wire? Kind of ugly...
>
> Just as info, I tried using the StatelessSession. But as soon as I want
> to access the childs, an exception is thrown:
> HessianServiceException: failed to lazily initialize a collection of
> role: TreeNode.childs, no session or session was closed
>
> greets
> Flavio
>
> Martin Taal wrote:
>
>> Hi Flavio,
>> You can also completely remove the explicit econtainer mapping (to the
> relational db) completely by setting
>> PersistenceOptions.DISABLE_ECONTAINER_MAPPING to true. Then if you load a
> single object from the database it will never
>> have its container set, if you load it through the parent (by
>> accessing for
> example the getChilds collection) then the
>> object will have the container set.
>
>> But to your code snippet. It is true that debugging loads the list
> (encountered this myself a few times). A really
>> confusing behavior!
>> However to test if a list is set you shouldn't test on nullable, you
>> can do
> the following:
>> boolean childsAreLoaded = !(child instanceof PersistableEList) ||
> ((PersistableEList<?>) child).isLoaded();
>> Normally it should return false, if you didn't touch the childs list.
>
>> A completely another solution>>
>> There is a very specific Hibernate feature (never used it myself): the
> stateless session interface:
>> StatelessSession session = sessionFactory.openStatelessSession();
>> it does not load collections at all, you really get the single object and
> that's all.
>
>> gr. Martin
>
>> Flavio Donzé wrote:
>>> Hi Martin
>>>
>>> Ok so i did some testing. Here a few code snippets:
>>>
>>> Properties hibernateProperties = new Properties();
>>> hibernateProperties
>>> .setProperty(Environment.DRIVER,
>>> preferences.getString(ServerPreferencesConstants.DB_DRIVER)) ;
>>> hibernateProperties.setProperty(Environment.URL,
>>> preferences.getString(ServerPreferencesConstants.DB_URL));
>>> hibernateProperties.setProperty(Environment.USER,
>>> preferences.getString(ServerPreferencesConstants.DB_USER));
>>> hibernateProperties.setProperty(Environment.PASS,
>>> preferences.getString(ServerPreferencesConstants.DB_PASS));
>>> hibernateProperties.setProperty(Environment.DIALECT, preferences
>>> .getString(ServerPreferencesConstants.DB_DIALECT));
>>> hibernateProperties.setProperty(Environment.SHOW_SQL,
>>> showSQL.toString());
>>>
>>>
>>> hibernateProperties.setProperty(PersistenceOptions.INHERITAN CE_MAPPING,
>>> InheritanceType.TABLE_PER_CLASS.name());
>>>
>>> hibernateProperties.setProperty(PersistenceOptions.DEFAULT_I D_FEATURE_NAME,
>>> ID_FIELD_NAME);
>>>
>>> hibernateProperties.setProperty(PersistenceOptions.ALWAYS_VE RSION,
>>> Boolean.FALSE.toString());
>>>
> hibernateProperties.setProperty(PersistenceOptions.ADD_INDEX _FOR_FOREIGN_KEY,
>
>>> Boolean.TRUE.toString());
>>>
> hibernateProperties.setProperty(PersistenceOptions.FETCH_CON TAINMENT_EAGERLY,
>
>>> Boolean.FALSE.toString());
>>> I added PersistenceOptions.FETCH_CONTAINMENT_EAGERLY to my
>>> normal settings.
>>>
>>>
>>> To create some test nodes i did the following:
>>>
>>> TreeNode parent = create();
>>> parent.setName("parent");
>>> TreeNode c1 = create();
>>> c1.setName("c1");
>>> TreeNode c2 = create();
>>> c2.setName("c2");
>>> parent.addChild(c1);
>>> parent.addChild(c2);
>>> TreeNode cc1 = create();
>>> cc1.setName("cc1");
>>> TreeNode cc2 = create();
>>> cc2.setName("cc2");
>>> c1.addChild(cc1);
>>> c1.addChild(cc2);
>>>
>>> EntityTransaction transaction = beginTransaction();
>>> entityManager.merge(parent);
>>> entityManager.merge(c1);
>>> entityManager.merge(c2);
>>> entityManager.merge(cc1);
>>> entityManager.merge(cc2);
>>> transaction.commit();
>>> Basically the following structure:
>>> parent
>>> -c1
>>> -cc1
>>> -cc2
>>> -c2
>>>
>>>
>>> Then I added some prints in the getChilds() method (I didn't want to
>>> inspect the object, thought that some magical way the childs might
>>> get loaded through that :-) )
>>> public List<TreeNode> getChilds()
>>> System.out.println(getName() + " childs: " + childs);
>>> if (childs != null) {
>>> System.out.println(getName() + " size: " + childs.size());
>>> if (childs.size() > 0) {
>>> System.out.println(getName() + " first: " +
>>> childs.get(0));
>>> }
>>> }
>>> if (childs == null) {
>>> childs = new
>>> EObjectContainmentEList<TreeNode>(TreeNode.class, this,
>>> SoftmodelerPackage.TREE_NODE__CHILDS);
>>> }
>>> }
>>>
>>> Now I execute the query:
>>>
>>> Criteria criteria = session.createCriteria(TreeNode.class);
>>> criteria.add(Restrictions.isNull("parent"));
>>> TreeNode result = (TreeNode) criteria.uniqueResult();
>>> result.getChilds().get(0).getChilds();
>>>
>>> Both the creation of the TreeNodes and the query happens on the server.
>>> I tried modeling the 'childs' as containment and as not containment.
>>> I always get the following output:
>>>
>>> parent childs: [c1, c2]
>>> parent size: 2
>>> parent first: c1
>>> c1 childs: [cc1, cc2]
>>> c1 size: 2
>>> c1 first: cc1
>>>
>>> I guess that this is the way it should behave, loading the whole
>>> object which also contains the childs. Then the child nodes are
>>> loaded which also load the whole object ... and so on.
>>> But I would like to have some kind of annotation to block the loading
>>> of references.
>>>
>>> greets
>>> Flavio
>>>
>>> Martin Taal wrote:
>>>
>>>> Hi Flavio,
>>>> There is an issue that econtainer parent relations are eagerly
>>>> loaded (this
>>> issue has not been solved at the moment..).
>>>> This should however not lead to the load of the children in the
>>>> whole tree.
>>>> On the server where running Teneo, do you need to persist the
>>>> econtainer
>>> relations? This can be disabled through an
>>>> option in PersistenceOptions.
>>>
>>>> Then why does it load the children... A reason that I can think of
>>>> is that
>>> the code that sends the object over the wire
>>>> touches the children collection and thereby forces its load. This
>>>> can be
>>> prevented, but can you check if this is indeed
>>>> the case?
>>>
>>>> gr. Martin
>>>
>>>> Flavio Donzé wrote:
>>>>> Hey Martin
>>>>>
>>>>> Thanks for the quick reply!
>>>>>
>>>>> Both the childs and the parent are read (the whole tree).
>>>>>
>>>>> The main problem is the children, I could make a workaround (only
>>>>> use the parent Id instead of a direct TreeNode reference) or even
>>>>> remove the parent reference.
>>>>>
>>>>> But if there is a way to block Teneo from reading the parent
>>>>> reference it would be great.
>>>>>
>>>>>
>>>>> thanks and greets
>>>>> Flavio
>>>>>
>>>>> Martin Taal wrote:
>>>>>
>>>>>> Hi Flavio,
>>>>>> Is also the parent of the treenode read? Or 'only' the children?
>>>>>
>>>>>> gr. Martin
>>>>>
>>>>>> Flavio Donzé wrote:
>>>>>>> Hello Martin
>>>>>>>
>>>>>>> I modeled a Parent/Child relationship in an object called TreeNode.
>>>>>>> In my Server/Client application (using Riena to transfer objects)
>>>>>>> I want to read the child TreeNodes by my self.
>>>>>>> Right now if I read a TreeNode some where in the tree, the whole
>>>>>>> tree is loaded.
>>>>>>>
>>>>>>> Well I can not use PersistenceOptions, because this needs to
>>>>>>> apply only for this Entity and PersistenceOptions.SET_PROXY
>>>>>>> wouldn't work anyway since the objects on the client wouldn't
>>>>>>> know how to resolve the proxy.
>>>>>>>
>>>>>>> As far as I know using the "FetchType Lazy" also creates proxies.
>>>>>>>
>>>>>>> So what would be the best way to block Teneo/Hibernate to load
>>>>>>> the childs?
>>>>>>>
>>>>>>> Here the ecore declaration of TreeNode:
>>>>>>>
>>>>>>> <eClassifiers xsi:type="ecore:EClass" name="TreeNode"
>>>>>>> eSuperTypes="#//BasicObject">
>>>>>>> <eOperations name="addChild">
>>>>>>> <eParameters name="node" eType="#//TreeNode"/>
>>>>>>> </eOperations>
>>>>>>> <eOperations name="getChild" eType="#//TreeNode">
>>>>>>> <eParameters name="id" eType="ecore:EDataType
>>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>>>> </eOperations>
>>>>>>> <eOperations name="hasChilds" eType="ecore:EDataType
>>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EBoolean"/>
>>>>>>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="name"
>>>>>>> eType="ecore:EDataType
>>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>>>> <eStructuralFeatures xsi:type="ecore:EReference" name="childs"
>>>>>>> upperBound="-1"
>>>>>>> eType="#//TreeNode" containment="true"/>
>>>>>>> <eStructuralFeatures xsi:type="ecore:EReference" name="object"
>>>>>>> eType="#//ObjectRef"
>>>>>>> containment="true"/>
>>>>>>> <eStructuralFeatures xsi:type="ecore:EReference" name="parent"
>>>>>>> eType="#//TreeNode"/>
>>>>>>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="type"
>>>>>>> eType="ecore:EDataType
>>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>>>> </eClassifiers>
>>>>>>>
>>>>>>>
>>>>>>> I appreciate any help, I searched the web but couldn't find a
>>>>>>> fitting solution.
>>>>>>>
>>>>>>>
>>>>>
>>>>>
>>>>>
>>>>>
>>>
>>>
>>>
>>>
>
>
>
>


--

With Regards, Martin Taal

Springsite/Elver.org
Office: Hardwareweg 4, 3821 BV Amersfoort
Postal: Nassaulaan 7, 3941 EC Doorn
The Netherlands
Cell: +31 (0)6 288 48 943
Tel: +31 (0)84 420 2397
Fax: +31 (0)84 225 9307
Mail: mtaal@springsite.com - mtaal@elver.org
Web: www.springsite.com - www.elver.org
Re: Teneo Parent/Child fetching [message #427275 is a reply to message #427217] Tue, 10 February 2009 16:40 Go to previous messageGo to next message
Flavio Donze is currently offline Flavio DonzeFriend
Messages: 211
Registered: July 2009
Location: Switzerland
Senior Member
Hello Martin, Tom

Riena does provide an ExtensionPoint to override the serialization:
org.eclipse.riena.communication.hessian.AbstractSerializerFa ctory

Here the implemented class:

public class TestSerializerFactory extends
com.caucho.hessian.io.AbstractSerializerFactory {

@SuppressWarnings("unchecked")
@Override
public Deserializer getDeserializer(Class arg0) throws
HessianProtocolException {
System.out.println("de " + arg0);

return null;
}

@SuppressWarnings("unchecked")
@Override
public Serializer getSerializer(Class arg0) throws
HessianProtocolException {
if (arg0.equals(HibernatePersistableEList.class)) {
return new CollectionSerializer() {
@Override
public void writeObject(Object obj, AbstractHessianOutput out) throws
IOException {
HibernatePersistableEList list = (HibernatePersistableEList) obj;
if (list.getEObject() instanceof TreeNode) {
list.clear();
out.writeNull();
} else {
super.writeObject(obj, out);
}
}
};
}
return null;
}
}


After I Nulled the childs I approached the problem of saving client
changes on the server. Since the TreeNode looses his references.
So I decided to go a totally different way. I just modeled the
'connection'.
Here the ecore:

<eClassifiers xsi:type="ecore:EClass" name="TreeNode"
eSuperTypes="#//BasicObject">
<eStructuralFeatures xsi:type="ecore:EAttribute" name="name"
eType="ecore:EDataType http://www.eclipse.org/emf/2002/Ecore#//EString"/>
<eStructuralFeatures xsi:type="ecore:EReference" name="childs"
upperBound="-1"
eType="#//TreeNodeChild" containment="true"
eOpposite="#//TreeNodeChild/parent"
eKeys="#//TreeNodeChild/nodeId"/>
<eStructuralFeatures xsi:type="ecore:EReference" name="object"
eType="#//ObjectRef"
containment="true"/>
<eStructuralFeatures xsi:type="ecore:EAttribute" name="type"
eType="ecore:EDataType http://www.eclipse.org/emf/2002/Ecore#//EString"/>
<eStructuralFeatures xsi:type="ecore:EReference" name="parent"
eType="#//TreeNode"
transient="true"/>
</eClassifiers>
<eClassifiers xsi:type="ecore:EClass" name="TreeNodeChild">
<eStructuralFeatures xsi:type="ecore:EAttribute" name="nodeId"
eType="ecore:EDataType http://www.eclipse.org/emf/2002/Ecore#//EString"
iD="true"/>
<eStructuralFeatures xsi:type="ecore:EReference" name="parent"
eType="#//TreeNode"
eOpposite="#//TreeNode/childs" eKeys="#//BasicObject/id"/>
</eClassifiers>


Also not the best solution but it works :-).
Now I transfer the TreeNode and its TreeNodeChild collection to the
client. If I need to read the childs I pass the TreeNode back to the
server and query the childs using the TreeNodeChild collection.


Thanks guys for your inputs/ideas!



Martin Taal wrote:

> Hi Flavio,
> Can you override the Rienna serializing so that you can implement your own
non-resolving serialization?

> gr. Martin

> Flavio Donzé wrote:
>> ciao Martin
>>
>> Ok so I tested:
>> boolean childsAreLoaded = !(child instanceof PersistableEList) ||
>> ((PersistableEList<?>) child).isLoaded();
>>
>> And it returns false. The debugger tricked me, as mentioned I was
>> suspecting something like that. Because there I can step through the
>> whole tree, all TreeNodes are loaded.
>> Hmm what would you suggest, Riena will definitely access the collection,
>> on the client side I have an ArrayList instead of an PersistableEList.
>> Maybe adding a setChilds(List<TreeNode> childs) method to the TreeNode
>> and calling setChilds(null) before transferring the TreeNode over the
>> wire? Kind of ugly...
>>
>> Just as info, I tried using the StatelessSession. But as soon as I want
>> to access the childs, an exception is thrown:
>> HessianServiceException: failed to lazily initialize a collection of
>> role: TreeNode.childs, no session or session was closed
>>
>> greets
>> Flavio
>>
>> Martin Taal wrote:
>>
>>> Hi Flavio,
>>> You can also completely remove the explicit econtainer mapping (to the
>> relational db) completely by setting
>>> PersistenceOptions.DISABLE_ECONTAINER_MAPPING to true. Then if you load a
>> single object from the database it will never
>>> have its container set, if you load it through the parent (by
>>> accessing for
>> example the getChilds collection) then the
>>> object will have the container set.
>>
>>> But to your code snippet. It is true that debugging loads the list
>> (encountered this myself a few times). A really
>>> confusing behavior!
>>> However to test if a list is set you shouldn't test on nullable, you
>>> can do
>> the following:
>>> boolean childsAreLoaded = !(child instanceof PersistableEList) ||
>> ((PersistableEList<?>) child).isLoaded();
>>> Normally it should return false, if you didn't touch the childs list.
>>
>>> A completely another solution>>
>>> There is a very specific Hibernate feature (never used it myself): the
>> stateless session interface:
>>> StatelessSession session = sessionFactory.openStatelessSession();
>>> it does not load collections at all, you really get the single object and
>> that's all.
>>
>>> gr. Martin
>>
>>> Flavio Donzé wrote:
>>>> Hi Martin
>>>>
>>>> Ok so i did some testing. Here a few code snippets:
>>>>
>>>> Properties hibernateProperties = new Properties();
>>>> hibernateProperties
>>>> .setProperty(Environment.DRIVER,
>>>> preferences.getString(ServerPreferencesConstants.DB_DRIVER)) ;
>>>> hibernateProperties.setProperty(Environment.URL,
>>>> preferences.getString(ServerPreferencesConstants.DB_URL));
>>>> hibernateProperties.setProperty(Environment.USER,
>>>> preferences.getString(ServerPreferencesConstants.DB_USER));
>>>> hibernateProperties.setProperty(Environment.PASS,
>>>> preferences.getString(ServerPreferencesConstants.DB_PASS));
>>>> hibernateProperties.setProperty(Environment.DIALECT, preferences
>>>> .getString(ServerPreferencesConstants.DB_DIALECT));
>>>> hibernateProperties.setProperty(Environment.SHOW_SQL,
>>>> showSQL.toString());
>>>>
>>>>
>>>> hibernateProperties.setProperty(PersistenceOptions.INHERITAN CE_MAPPING,
>>>> InheritanceType.TABLE_PER_CLASS.name());
>>>>
>>>>
hibernateProperties.setProperty(PersistenceOptions.DEFAULT_I D_FEATURE_NAME,
>>>> ID_FIELD_NAME);
>>>>
>>>> hibernateProperties.setProperty(PersistenceOptions.ALWAYS_VE RSION,
>>>> Boolean.FALSE.toString());
>>>>
>>
hibernateProperties.setProperty(PersistenceOptions.ADD_INDEX _FOR_FOREIGN_KEY,
>>
>>>> Boolean.TRUE.toString());
>>>>
>>
hibernateProperties.setProperty(PersistenceOptions.FETCH_CON TAINMENT_EAGERLY,
>>
>>>> Boolean.FALSE.toString());
>>>> I added PersistenceOptions.FETCH_CONTAINMENT_EAGERLY to my
>>>> normal settings.
>>>>
>>>>
>>>> To create some test nodes i did the following:
>>>>
>>>> TreeNode parent = create();
>>>> parent.setName("parent");
>>>> TreeNode c1 = create();
>>>> c1.setName("c1");
>>>> TreeNode c2 = create();
>>>> c2.setName("c2");
>>>> parent.addChild(c1);
>>>> parent.addChild(c2);
>>>> TreeNode cc1 = create();
>>>> cc1.setName("cc1");
>>>> TreeNode cc2 = create();
>>>> cc2.setName("cc2");
>>>> c1.addChild(cc1);
>>>> c1.addChild(cc2);
>>>>
>>>> EntityTransaction transaction = beginTransaction();
>>>> entityManager.merge(parent);
>>>> entityManager.merge(c1);
>>>> entityManager.merge(c2);
>>>> entityManager.merge(cc1);
>>>> entityManager.merge(cc2);
>>>> transaction.commit();
>>>> Basically the following structure:
>>>> parent
>>>> -c1
>>>> -cc1
>>>> -cc2
>>>> -c2
>>>>
>>>>
>>>> Then I added some prints in the getChilds() method (I didn't want to
>>>> inspect the object, thought that some magical way the childs might
>>>> get loaded through that :-) )
>>>> public List<TreeNode> getChilds()
>>>> System.out.println(getName() + " childs: " + childs);
>>>> if (childs != null) {
>>>> System.out.println(getName() + " size: " + childs.size());
>>>> if (childs.size() > 0) {
>>>> System.out.println(getName() + " first: " +
>>>> childs.get(0));
>>>> }
>>>> }
>>>> if (childs == null) {
>>>> childs = new
>>>> EObjectContainmentEList<TreeNode>(TreeNode.class, this,
>>>> SoftmodelerPackage.TREE_NODE__CHILDS);
>>>> }
>>>> }
>>>>
>>>> Now I execute the query:
>>>>
>>>> Criteria criteria = session.createCriteria(TreeNode.class);
>>>> criteria.add(Restrictions.isNull("parent"));
>>>> TreeNode result = (TreeNode) criteria.uniqueResult();
>>>> result.getChilds().get(0).getChilds();
>>>>
>>>> Both the creation of the TreeNodes and the query happens on the server.
>>>> I tried modeling the 'childs' as containment and as not containment.
>>>> I always get the following output:
>>>>
>>>> parent childs: [c1, c2]
>>>> parent size: 2
>>>> parent first: c1
>>>> c1 childs: [cc1, cc2]
>>>> c1 size: 2
>>>> c1 first: cc1
>>>>
>>>> I guess that this is the way it should behave, loading the whole
>>>> object which also contains the childs. Then the child nodes are
>>>> loaded which also load the whole object ... and so on.
>>>> But I would like to have some kind of annotation to block the loading
>>>> of references.
>>>>
>>>> greets
>>>> Flavio
>>>>
>>>> Martin Taal wrote:
>>>>
>>>>> Hi Flavio,
>>>>> There is an issue that econtainer parent relations are eagerly
>>>>> loaded (this
>>>> issue has not been solved at the moment..).
>>>>> This should however not lead to the load of the children in the
>>>>> whole tree.
>>>>> On the server where running Teneo, do you need to persist the
>>>>> econtainer
>>>> relations? This can be disabled through an
>>>>> option in PersistenceOptions.
>>>>
>>>>> Then why does it load the children... A reason that I can think of
>>>>> is that
>>>> the code that sends the object over the wire
>>>>> touches the children collection and thereby forces its load. This
>>>>> can be
>>>> prevented, but can you check if this is indeed
>>>>> the case?
>>>>
>>>>> gr. Martin
>>>>
>>>>> Flavio Donzé wrote:
>>>>>> Hey Martin
>>>>>>
>>>>>> Thanks for the quick reply!
>>>>>>
>>>>>> Both the childs and the parent are read (the whole tree).
>>>>>>
>>>>>> The main problem is the children, I could make a workaround (only
>>>>>> use the parent Id instead of a direct TreeNode reference) or even
>>>>>> remove the parent reference.
>>>>>>
>>>>>> But if there is a way to block Teneo from reading the parent
>>>>>> reference it would be great.
>>>>>>
>>>>>>
>>>>>> thanks and greets
>>>>>> Flavio
>>>>>>
>>>>>> Martin Taal wrote:
>>>>>>
>>>>>>> Hi Flavio,
>>>>>>> Is also the parent of the treenode read? Or 'only' the children?
>>>>>>
>>>>>>> gr. Martin
>>>>>>
>>>>>>> Flavio Donzé wrote:
>>>>>>>> Hello Martin
>>>>>>>>
>>>>>>>> I modeled a Parent/Child relationship in an object called TreeNode.
>>>>>>>> In my Server/Client application (using Riena to transfer objects)
>>>>>>>> I want to read the child TreeNodes by my self.
>>>>>>>> Right now if I read a TreeNode some where in the tree, the whole
>>>>>>>> tree is loaded.
>>>>>>>>
>>>>>>>> Well I can not use PersistenceOptions, because this needs to
>>>>>>>> apply only for this Entity and PersistenceOptions.SET_PROXY
>>>>>>>> wouldn't work anyway since the objects on the client wouldn't
>>>>>>>> know how to resolve the proxy.
>>>>>>>>
>>>>>>>> As far as I know using the "FetchType Lazy" also creates proxies.
>>>>>>>>
>>>>>>>> So what would be the best way to block Teneo/Hibernate to load
>>>>>>>> the childs?
>>>>>>>>
>>>>>>>> Here the ecore declaration of TreeNode:
>>>>>>>>
>>>>>>>> <eClassifiers xsi:type="ecore:EClass" name="TreeNode"
>>>>>>>> eSuperTypes="#//BasicObject">
>>>>>>>> <eOperations name="addChild">
>>>>>>>> <eParameters name="node" eType="#//TreeNode"/>
>>>>>>>> </eOperations>
>>>>>>>> <eOperations name="getChild" eType="#//TreeNode">
>>>>>>>> <eParameters name="id" eType="ecore:EDataType
>>>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>>>>> </eOperations>
>>>>>>>> <eOperations name="hasChilds" eType="ecore:EDataType
>>>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EBoolean"/>
>>>>>>>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="name"
>>>>>>>> eType="ecore:EDataType
>>>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>>>>> <eStructuralFeatures xsi:type="ecore:EReference" name="childs"
>>>>>>>> upperBound="-1"
>>>>>>>> eType="#//TreeNode" containment="true"/>
>>>>>>>> <eStructuralFeatures xsi:type="ecore:EReference" name="object"
>>>>>>>> eType="#//ObjectRef"
>>>>>>>> containment="true"/>
>>>>>>>> <eStructuralFeatures xsi:type="ecore:EReference" name="parent"
>>>>>>>> eType="#//TreeNode"/>
>>>>>>>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="type"
>>>>>>>> eType="ecore:EDataType
>>>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>>>>> </eClassifiers>
>>>>>>>>
>>>>>>>>
>>>>>>>> I appreciate any help, I searched the web but couldn't find a
>>>>>>>> fitting solution.
>>>>>>>>
>>>>>>>>
>>>>>>
>>>>>>
>>>>>>
>>>>>>
>>>>
>>>>
>>>>
>>>>
>>
>>
>>
>>


Prozessmanagement und Qualitätsmanagement Software QMS/IMS
https://www.scodi.ch
Re: Teneo Parent/Child fetching [message #427277 is a reply to message #427275] Tue, 10 February 2009 17:50 Go to previous messageGo to next message
Martin Taal is currently offline Martin TaalFriend
Messages: 5468
Registered: July 2009
Senior Member
Hi Flavio,
Thanks for the update, always interesting!

One remark (let me know if I miss the point), you do list.clear(), if you then commit the transaction then the list will
also be cleared in the db. Or did you not encounter this behavior? Do you need to do list.clear() or would just
out.writeNull be enough?

gr. Martin

Flavio Donzé wrote:
> Hello Martin, Tom
>
> Riena does provide an ExtensionPoint to override the serialization:
> org.eclipse.riena.communication.hessian.AbstractSerializerFa ctory
>
> Here the implemented class:
>
> public class TestSerializerFactory extends
> com.caucho.hessian.io.AbstractSerializerFactory {
>
> @SuppressWarnings("unchecked")
> @Override
> public Deserializer getDeserializer(Class arg0) throws
> HessianProtocolException {
> System.out.println("de " + arg0);
>
> return null;
> }
>
> @SuppressWarnings("unchecked")
> @Override
> public Serializer getSerializer(Class arg0) throws
> HessianProtocolException {
> if (arg0.equals(HibernatePersistableEList.class)) {
> return new CollectionSerializer() {
> @Override
> public void writeObject(Object obj,
> AbstractHessianOutput out) throws IOException {
> HibernatePersistableEList list =
> (HibernatePersistableEList) obj;
> if (list.getEObject() instanceof TreeNode) {
> list.clear();
> out.writeNull();
> } else {
> super.writeObject(obj, out);
> }
> }
> };
> }
> return null;
> }
> }
>
>
> After I Nulled the childs I approached the problem of saving client
> changes on the server. Since the TreeNode looses his references. So I
> decided to go a totally different way. I just modeled the 'connection'.
> Here the ecore:
>
> <eClassifiers xsi:type="ecore:EClass" name="TreeNode"
> eSuperTypes="#//BasicObject">
> <eStructuralFeatures xsi:type="ecore:EAttribute" name="name"
> eType="ecore:EDataType http://www.eclipse.org/emf/2002/Ecore#//EString"/>
> <eStructuralFeatures xsi:type="ecore:EReference" name="childs"
> upperBound="-1"
> eType="#//TreeNodeChild" containment="true"
> eOpposite="#//TreeNodeChild/parent"
> eKeys="#//TreeNodeChild/nodeId"/>
> <eStructuralFeatures xsi:type="ecore:EReference" name="object"
> eType="#//ObjectRef"
> containment="true"/>
> <eStructuralFeatures xsi:type="ecore:EAttribute" name="type"
> eType="ecore:EDataType http://www.eclipse.org/emf/2002/Ecore#//EString"/>
> <eStructuralFeatures xsi:type="ecore:EReference" name="parent"
> eType="#//TreeNode"
> transient="true"/>
> </eClassifiers>
> <eClassifiers xsi:type="ecore:EClass" name="TreeNodeChild">
> <eStructuralFeatures xsi:type="ecore:EAttribute" name="nodeId"
> eType="ecore:EDataType http://www.eclipse.org/emf/2002/Ecore#//EString"
> iD="true"/>
> <eStructuralFeatures xsi:type="ecore:EReference" name="parent"
> eType="#//TreeNode"
> eOpposite="#//TreeNode/childs" eKeys="#//BasicObject/id"/>
> </eClassifiers>
>
>
> Also not the best solution but it works :-).
> Now I transfer the TreeNode and its TreeNodeChild collection to the
> client. If I need to read the childs I pass the TreeNode back to the
> server and query the childs using the TreeNodeChild collection.
>
>
> Thanks guys for your inputs/ideas!
>
>
>
> Martin Taal wrote:
>
>> Hi Flavio,
>> Can you override the Rienna serializing so that you can implement your
>> own
> non-resolving serialization?
>
>> gr. Martin
>
>> Flavio Donzé wrote:
>>> ciao Martin
>>>
>>> Ok so I tested:
>>> boolean childsAreLoaded = !(child instanceof PersistableEList) ||
>>> ((PersistableEList<?>) child).isLoaded();
>>>
>>> And it returns false. The debugger tricked me, as mentioned I was
>>> suspecting something like that. Because there I can step through the
>>> whole tree, all TreeNodes are loaded.
>>> Hmm what would you suggest, Riena will definitely access the
>>> collection, on the client side I have an ArrayList instead of an
>>> PersistableEList.
>>> Maybe adding a setChilds(List<TreeNode> childs) method to the
>>> TreeNode and calling setChilds(null) before transferring the TreeNode
>>> over the wire? Kind of ugly...
>>>
>>> Just as info, I tried using the StatelessSession. But as soon as I
>>> want to access the childs, an exception is thrown:
>>> HessianServiceException: failed to lazily initialize a collection of
>>> role: TreeNode.childs, no session or session was closed
>>>
>>> greets
>>> Flavio
>>>
>>> Martin Taal wrote:
>>>
>>>> Hi Flavio,
>>>> You can also completely remove the explicit econtainer mapping (to the
>>> relational db) completely by setting
>>>> PersistenceOptions.DISABLE_ECONTAINER_MAPPING to true. Then if you
>>>> load a
>>> single object from the database it will never
>>>> have its container set, if you load it through the parent (by
>>>> accessing for
>>> example the getChilds collection) then the
>>>> object will have the container set.
>>>
>>>> But to your code snippet. It is true that debugging loads the list
>>> (encountered this myself a few times). A really
>>>> confusing behavior!
>>>> However to test if a list is set you shouldn't test on nullable, you
>>>> can do
>>> the following:
>>>> boolean childsAreLoaded = !(child instanceof PersistableEList) ||
>>> ((PersistableEList<?>) child).isLoaded();
>>>> Normally it should return false, if you didn't touch the childs list.
>>>
>>>> A completely another solution>>
>>>> There is a very specific Hibernate feature (never used it myself): the
>>> stateless session interface:
>>>> StatelessSession session = sessionFactory.openStatelessSession();
>>>> it does not load collections at all, you really get the single
>>>> object and
>>> that's all.
>>>
>>>> gr. Martin
>>>
>>>> Flavio Donzé wrote:
>>>>> Hi Martin
>>>>>
>>>>> Ok so i did some testing. Here a few code snippets:
>>>>>
>>>>> Properties hibernateProperties = new Properties();
>>>>> hibernateProperties
>>>>> .setProperty(Environment.DRIVER,
>>>>> preferences.getString(ServerPreferencesConstants.DB_DRIVER)) ;
>>>>> hibernateProperties.setProperty(Environment.URL,
>>>>> preferences.getString(ServerPreferencesConstants.DB_URL));
>>>>> hibernateProperties.setProperty(Environment.USER,
>>>>> preferences.getString(ServerPreferencesConstants.DB_USER));
>>>>> hibernateProperties.setProperty(Environment.PASS,
>>>>> preferences.getString(ServerPreferencesConstants.DB_PASS));
>>>>> hibernateProperties.setProperty(Environment.DIALECT,
>>>>> preferences
>>>>> .getString(ServerPreferencesConstants.DB_DIALECT));
>>>>> hibernateProperties.setProperty(Environment.SHOW_SQL,
>>>>> showSQL.toString());
>>>>>
>>>>>
>>>>> hibernateProperties.setProperty(PersistenceOptions.INHERITAN CE_MAPPING,
>>>>> InheritanceType.TABLE_PER_CLASS.name());
>>>>>
> hibernateProperties.setProperty(PersistenceOptions.DEFAULT_I D_FEATURE_NAME,
>>>>> ID_FIELD_NAME);
>>>>>
>>>>> hibernateProperties.setProperty(PersistenceOptions.ALWAYS_VE RSION,
>>>>> Boolean.FALSE.toString());
>>>>>
>>>
> hibernateProperties.setProperty(PersistenceOptions.ADD_INDEX _FOR_FOREIGN_KEY,
>
>>>
>>>>> Boolean.TRUE.toString());
>>>>>
>>>
> hibernateProperties.setProperty(PersistenceOptions.FETCH_CON TAINMENT_EAGERLY,
>
>>>
>>>>> Boolean.FALSE.toString());
>>>>> I added PersistenceOptions.FETCH_CONTAINMENT_EAGERLY to my
>>>>> normal settings.
>>>>>
>>>>>
>>>>> To create some test nodes i did the following:
>>>>>
>>>>> TreeNode parent = create();
>>>>> parent.setName("parent");
>>>>> TreeNode c1 = create();
>>>>> c1.setName("c1");
>>>>> TreeNode c2 = create();
>>>>> c2.setName("c2");
>>>>> parent.addChild(c1);
>>>>> parent.addChild(c2);
>>>>> TreeNode cc1 = create();
>>>>> cc1.setName("cc1");
>>>>> TreeNode cc2 = create();
>>>>> cc2.setName("cc2");
>>>>> c1.addChild(cc1);
>>>>> c1.addChild(cc2);
>>>>>
>>>>> EntityTransaction transaction = beginTransaction();
>>>>> entityManager.merge(parent);
>>>>> entityManager.merge(c1);
>>>>> entityManager.merge(c2);
>>>>> entityManager.merge(cc1);
>>>>> entityManager.merge(cc2);
>>>>> transaction.commit();
>>>>> Basically the following structure:
>>>>> parent
>>>>> -c1
>>>>> -cc1
>>>>> -cc2
>>>>> -c2
>>>>>
>>>>>
>>>>> Then I added some prints in the getChilds() method (I didn't want
>>>>> to inspect the object, thought that some magical way the childs
>>>>> might get loaded through that :-) )
>>>>> public List<TreeNode> getChilds()
>>>>> System.out.println(getName() + " childs: " + childs);
>>>>> if (childs != null) {
>>>>> System.out.println(getName() + " size: " + childs.size());
>>>>> if (childs.size() > 0) {
>>>>> System.out.println(getName() + " first: " +
>>>>> childs.get(0));
>>>>> }
>>>>> }
>>>>> if (childs == null) {
>>>>> childs = new
>>>>> EObjectContainmentEList<TreeNode>(TreeNode.class, this,
>>>>> SoftmodelerPackage.TREE_NODE__CHILDS);
>>>>> }
>>>>> }
>>>>>
>>>>> Now I execute the query:
>>>>>
>>>>> Criteria criteria = session.createCriteria(TreeNode.class);
>>>>> criteria.add(Restrictions.isNull("parent"));
>>>>> TreeNode result = (TreeNode) criteria.uniqueResult();
>>>>> result.getChilds().get(0).getChilds();
>>>>>
>>>>> Both the creation of the TreeNodes and the query happens on the
>>>>> server.
>>>>> I tried modeling the 'childs' as containment and as not containment.
>>>>> I always get the following output:
>>>>>
>>>>> parent childs: [c1, c2]
>>>>> parent size: 2
>>>>> parent first: c1
>>>>> c1 childs: [cc1, cc2]
>>>>> c1 size: 2
>>>>> c1 first: cc1
>>>>>
>>>>> I guess that this is the way it should behave, loading the whole
>>>>> object which also contains the childs. Then the child nodes are
>>>>> loaded which also load the whole object ... and so on.
>>>>> But I would like to have some kind of annotation to block the
>>>>> loading of references.
>>>>>
>>>>> greets
>>>>> Flavio
>>>>>
>>>>> Martin Taal wrote:
>>>>>
>>>>>> Hi Flavio,
>>>>>> There is an issue that econtainer parent relations are eagerly
>>>>>> loaded (this
>>>>> issue has not been solved at the moment..).
>>>>>> This should however not lead to the load of the children in the
>>>>>> whole tree.
>>>>>> On the server where running Teneo, do you need to persist the
>>>>>> econtainer
>>>>> relations? This can be disabled through an
>>>>>> option in PersistenceOptions.
>>>>>
>>>>>> Then why does it load the children... A reason that I can think of
>>>>>> is that
>>>>> the code that sends the object over the wire
>>>>>> touches the children collection and thereby forces its load. This
>>>>>> can be
>>>>> prevented, but can you check if this is indeed
>>>>>> the case?
>>>>>
>>>>>> gr. Martin
>>>>>
>>>>>> Flavio Donzé wrote:
>>>>>>> Hey Martin
>>>>>>>
>>>>>>> Thanks for the quick reply!
>>>>>>>
>>>>>>> Both the childs and the parent are read (the whole tree).
>>>>>>>
>>>>>>> The main problem is the children, I could make a workaround (only
>>>>>>> use the parent Id instead of a direct TreeNode reference) or even
>>>>>>> remove the parent reference.
>>>>>>>
>>>>>>> But if there is a way to block Teneo from reading the parent
>>>>>>> reference it would be great.
>>>>>>>
>>>>>>>
>>>>>>> thanks and greets
>>>>>>> Flavio
>>>>>>>
>>>>>>> Martin Taal wrote:
>>>>>>>
>>>>>>>> Hi Flavio,
>>>>>>>> Is also the parent of the treenode read? Or 'only' the children?
>>>>>>>
>>>>>>>> gr. Martin
>>>>>>>
>>>>>>>> Flavio Donzé wrote:
>>>>>>>>> Hello Martin
>>>>>>>>>
>>>>>>>>> I modeled a Parent/Child relationship in an object called
>>>>>>>>> TreeNode.
>>>>>>>>> In my Server/Client application (using Riena to transfer
>>>>>>>>> objects) I want to read the child TreeNodes by my self.
>>>>>>>>> Right now if I read a TreeNode some where in the tree, the
>>>>>>>>> whole tree is loaded.
>>>>>>>>>
>>>>>>>>> Well I can not use PersistenceOptions, because this needs to
>>>>>>>>> apply only for this Entity and PersistenceOptions.SET_PROXY
>>>>>>>>> wouldn't work anyway since the objects on the client wouldn't
>>>>>>>>> know how to resolve the proxy.
>>>>>>>>>
>>>>>>>>> As far as I know using the "FetchType Lazy" also creates proxies.
>>>>>>>>>
>>>>>>>>> So what would be the best way to block Teneo/Hibernate to load
>>>>>>>>> the childs?
>>>>>>>>>
>>>>>>>>> Here the ecore declaration of TreeNode:
>>>>>>>>>
>>>>>>>>> <eClassifiers xsi:type="ecore:EClass" name="TreeNode"
>>>>>>>>> eSuperTypes="#//BasicObject">
>>>>>>>>> <eOperations name="addChild">
>>>>>>>>> <eParameters name="node" eType="#//TreeNode"/>
>>>>>>>>> </eOperations>
>>>>>>>>> <eOperations name="getChild" eType="#//TreeNode">
>>>>>>>>> <eParameters name="id" eType="ecore:EDataType
>>>>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>>>>>> </eOperations>
>>>>>>>>> <eOperations name="hasChilds" eType="ecore:EDataType
>>>>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EBoolean"/>
>>>>>>>>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="name"
>>>>>>>>> eType="ecore:EDataType
>>>>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>>>>>> <eStructuralFeatures xsi:type="ecore:EReference"
>>>>>>>>> name="childs" upperBound="-1"
>>>>>>>>> eType="#//TreeNode" containment="true"/>
>>>>>>>>> <eStructuralFeatures xsi:type="ecore:EReference"
>>>>>>>>> name="object" eType="#//ObjectRef"
>>>>>>>>> containment="true"/>
>>>>>>>>> <eStructuralFeatures xsi:type="ecore:EReference"
>>>>>>>>> name="parent" eType="#//TreeNode"/>
>>>>>>>>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="type"
>>>>>>>>> eType="ecore:EDataType
>>>>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>>>>>> </eClassifiers>
>>>>>>>>>
>>>>>>>>>
>>>>>>>>> I appreciate any help, I searched the web but couldn't find a
>>>>>>>>> fitting solution.
>>>>>>>>>
>>>>>>>>>
>>>>>>>
>>>>>>>
>>>>>>>
>>>>>>>
>>>>>
>>>>>
>>>>>
>>>>>
>>>
>>>
>>>
>>>
>
>
>
>


--

With Regards, Martin Taal

Springsite/Elver.org
Office: Hardwareweg 4, 3821 BV Amersfoort
Postal: Nassaulaan 7, 3941 EC Doorn
The Netherlands
Cell: +31 (0)6 288 48 943
Tel: +31 (0)84 420 2397
Fax: +31 (0)84 225 9307
Mail: mtaal@springsite.com - mtaal@elver.org
Web: www.springsite.com - www.elver.org
Re: Teneo Parent/Child fetching [message #427278 is a reply to message #427277] Tue, 10 February 2009 18:05 Go to previous message
Flavio Donze is currently offline Flavio DonzeFriend
Messages: 211
Registered: July 2009
Location: Switzerland
Senior Member
hey Martin

writeNull would be enough.
Nothing happens to the db doing list.clear(). I just thought I could help
the garbage collector a little :-)

cheers
flavio

Martin Taal wrote:

> Hi Flavio,
> Thanks for the update, always interesting!

> One remark (let me know if I miss the point), you do list.clear(), if you
then commit the transaction then the list will
> also be cleared in the db. Or did you not encounter this behavior? Do you
need to do list.clear() or would just
> out.writeNull be enough?

> gr. Martin

> Flavio Donzé wrote:
>> Hello Martin, Tom
>>
>> Riena does provide an ExtensionPoint to override the serialization:
>> org.eclipse.riena.communication.hessian.AbstractSerializerFa ctory
>>
>> Here the implemented class:
>>
>> public class TestSerializerFactory extends
>> com.caucho.hessian.io.AbstractSerializerFactory {
>>
>> @SuppressWarnings("unchecked")
>> @Override
>> public Deserializer getDeserializer(Class arg0) throws
>> HessianProtocolException {
>> System.out.println("de " + arg0);
>>
>> return null;
>> }
>>
>> @SuppressWarnings("unchecked")
>> @Override
>> public Serializer getSerializer(Class arg0) throws
>> HessianProtocolException {
>> if (arg0.equals(HibernatePersistableEList.class)) {
>> return new CollectionSerializer() {
>> @Override
>> public void writeObject(Object obj,
>> AbstractHessianOutput out) throws IOException {
>> HibernatePersistableEList list =
>> (HibernatePersistableEList) obj;
>> if (list.getEObject() instanceof TreeNode) {
>> list.clear();
>> out.writeNull();
>> } else {
>> super.writeObject(obj, out);
>> }
>> }
>> };
>> }
>> return null;
>> }
>> }
>>
>>
>> After I Nulled the childs I approached the problem of saving client
>> changes on the server. Since the TreeNode looses his references. So I
>> decided to go a totally different way. I just modeled the 'connection'.
>> Here the ecore:
>>
>> <eClassifiers xsi:type="ecore:EClass" name="TreeNode"
>> eSuperTypes="#//BasicObject">
>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="name"
>> eType="ecore:EDataType http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>> <eStructuralFeatures xsi:type="ecore:EReference" name="childs"
>> upperBound="-1"
>> eType="#//TreeNodeChild" containment="true"
>> eOpposite="#//TreeNodeChild/parent"
>> eKeys="#//TreeNodeChild/nodeId"/>
>> <eStructuralFeatures xsi:type="ecore:EReference" name="object"
>> eType="#//ObjectRef"
>> containment="true"/>
>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="type"
>> eType="ecore:EDataType http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>> <eStructuralFeatures xsi:type="ecore:EReference" name="parent"
>> eType="#//TreeNode"
>> transient="true"/>
>> </eClassifiers>
>> <eClassifiers xsi:type="ecore:EClass" name="TreeNodeChild">
>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="nodeId"
>> eType="ecore:EDataType http://www.eclipse.org/emf/2002/Ecore#//EString"
>> iD="true"/>
>> <eStructuralFeatures xsi:type="ecore:EReference" name="parent"
>> eType="#//TreeNode"
>> eOpposite="#//TreeNode/childs" eKeys="#//BasicObject/id"/>
>> </eClassifiers>
>>
>>
>> Also not the best solution but it works :-).
>> Now I transfer the TreeNode and its TreeNodeChild collection to the
>> client. If I need to read the childs I pass the TreeNode back to the
>> server and query the childs using the TreeNodeChild collection.
>>
>>
>> Thanks guys for your inputs/ideas!
>>
>>
>>
>> Martin Taal wrote:
>>
>>> Hi Flavio,
>>> Can you override the Rienna serializing so that you can implement your
>>> own
>> non-resolving serialization?
>>
>>> gr. Martin
>>
>>> Flavio Donzé wrote:
>>>> ciao Martin
>>>>
>>>> Ok so I tested:
>>>> boolean childsAreLoaded = !(child instanceof PersistableEList) ||
>>>> ((PersistableEList<?>) child).isLoaded();
>>>>
>>>> And it returns false. The debugger tricked me, as mentioned I was
>>>> suspecting something like that. Because there I can step through the
>>>> whole tree, all TreeNodes are loaded.
>>>> Hmm what would you suggest, Riena will definitely access the
>>>> collection, on the client side I have an ArrayList instead of an
>>>> PersistableEList.
>>>> Maybe adding a setChilds(List<TreeNode> childs) method to the
>>>> TreeNode and calling setChilds(null) before transferring the TreeNode
>>>> over the wire? Kind of ugly...
>>>>
>>>> Just as info, I tried using the StatelessSession. But as soon as I
>>>> want to access the childs, an exception is thrown:
>>>> HessianServiceException: failed to lazily initialize a collection of
>>>> role: TreeNode.childs, no session or session was closed
>>>>
>>>> greets
>>>> Flavio
>>>>
>>>> Martin Taal wrote:
>>>>
>>>>> Hi Flavio,
>>>>> You can also completely remove the explicit econtainer mapping (to the
>>>> relational db) completely by setting
>>>>> PersistenceOptions.DISABLE_ECONTAINER_MAPPING to true. Then if you
>>>>> load a
>>>> single object from the database it will never
>>>>> have its container set, if you load it through the parent (by
>>>>> accessing for
>>>> example the getChilds collection) then the
>>>>> object will have the container set.
>>>>
>>>>> But to your code snippet. It is true that debugging loads the list
>>>> (encountered this myself a few times). A really
>>>>> confusing behavior!
>>>>> However to test if a list is set you shouldn't test on nullable, you
>>>>> can do
>>>> the following:
>>>>> boolean childsAreLoaded = !(child instanceof PersistableEList) ||
>>>> ((PersistableEList<?>) child).isLoaded();
>>>>> Normally it should return false, if you didn't touch the childs list.
>>>>
>>>>> A completely another solution>>
>>>>> There is a very specific Hibernate feature (never used it myself): the
>>>> stateless session interface:
>>>>> StatelessSession session = sessionFactory.openStatelessSession();
>>>>> it does not load collections at all, you really get the single
>>>>> object and
>>>> that's all.
>>>>
>>>>> gr. Martin
>>>>
>>>>> Flavio Donzé wrote:
>>>>>> Hi Martin
>>>>>>
>>>>>> Ok so i did some testing. Here a few code snippets:
>>>>>>
>>>>>> Properties hibernateProperties = new Properties();
>>>>>> hibernateProperties
>>>>>> .setProperty(Environment.DRIVER,
>>>>>> preferences.getString(ServerPreferencesConstants.DB_DRIVER)) ;
>>>>>> hibernateProperties.setProperty(Environment.URL,
>>>>>> preferences.getString(ServerPreferencesConstants.DB_URL));
>>>>>> hibernateProperties.setProperty(Environment.USER,
>>>>>> preferences.getString(ServerPreferencesConstants.DB_USER));
>>>>>> hibernateProperties.setProperty(Environment.PASS,
>>>>>> preferences.getString(ServerPreferencesConstants.DB_PASS));
>>>>>> hibernateProperties.setProperty(Environment.DIALECT,
>>>>>> preferences
>>>>>> .getString(ServerPreferencesConstants.DB_DIALECT));
>>>>>> hibernateProperties.setProperty(Environment.SHOW_SQL,
>>>>>> showSQL.toString());
>>>>>>
>>>>>>
>>>>>> hibernateProperties.setProperty(PersistenceOptions.INHERITAN CE_MAPPING,
>>>>>> InheritanceType.TABLE_PER_CLASS.name());
>>>>>>
>> hibernateProperties.setProperty(PersistenceOptions.DEFAULT_I D_FEATURE_NAME,
>>>>>> ID_FIELD_NAME);
>>>>>>
>>>>>> hibernateProperties.setProperty(PersistenceOptions.ALWAYS_VE RSION,
>>>>>> Boolean.FALSE.toString());
>>>>>>
>>>>
>>
hibernateProperties.setProperty(PersistenceOptions.ADD_INDEX _FOR_FOREIGN_KEY,
>>
>>>>
>>>>>> Boolean.TRUE.toString());
>>>>>>
>>>>
>>
hibernateProperties.setProperty(PersistenceOptions.FETCH_CON TAINMENT_EAGERLY,
>>
>>>>
>>>>>> Boolean.FALSE.toString());
>>>>>> I added PersistenceOptions.FETCH_CONTAINMENT_EAGERLY to my
>>>>>> normal settings.
>>>>>>
>>>>>>
>>>>>> To create some test nodes i did the following:
>>>>>>
>>>>>> TreeNode parent = create();
>>>>>> parent.setName("parent");
>>>>>> TreeNode c1 = create();
>>>>>> c1.setName("c1");
>>>>>> TreeNode c2 = create();
>>>>>> c2.setName("c2");
>>>>>> parent.addChild(c1);
>>>>>> parent.addChild(c2);
>>>>>> TreeNode cc1 = create();
>>>>>> cc1.setName("cc1");
>>>>>> TreeNode cc2 = create();
>>>>>> cc2.setName("cc2");
>>>>>> c1.addChild(cc1);
>>>>>> c1.addChild(cc2);
>>>>>>
>>>>>> EntityTransaction transaction = beginTransaction();
>>>>>> entityManager.merge(parent);
>>>>>> entityManager.merge(c1);
>>>>>> entityManager.merge(c2);
>>>>>> entityManager.merge(cc1);
>>>>>> entityManager.merge(cc2);
>>>>>> transaction.commit();
>>>>>> Basically the following structure:
>>>>>> parent
>>>>>> -c1
>>>>>> -cc1
>>>>>> -cc2
>>>>>> -c2
>>>>>>
>>>>>>
>>>>>> Then I added some prints in the getChilds() method (I didn't want
>>>>>> to inspect the object, thought that some magical way the childs
>>>>>> might get loaded through that :-) )
>>>>>> public List<TreeNode> getChilds()
>>>>>> System.out.println(getName() + " childs: " + childs);
>>>>>> if (childs != null) {
>>>>>> System.out.println(getName() + " size: " + childs.size());
>>>>>> if (childs.size() > 0) {
>>>>>> System.out.println(getName() + " first: " +
>>>>>> childs.get(0));
>>>>>> }
>>>>>> }
>>>>>> if (childs == null) {
>>>>>> childs = new
>>>>>> EObjectContainmentEList<TreeNode>(TreeNode.class, this,
>>>>>> SoftmodelerPackage.TREE_NODE__CHILDS);
>>>>>> }
>>>>>> }
>>>>>>
>>>>>> Now I execute the query:
>>>>>>
>>>>>> Criteria criteria = session.createCriteria(TreeNode.class);
>>>>>> criteria.add(Restrictions.isNull("parent"));
>>>>>> TreeNode result = (TreeNode) criteria.uniqueResult();
>>>>>> result.getChilds().get(0).getChilds();
>>>>>>
>>>>>> Both the creation of the TreeNodes and the query happens on the
>>>>>> server.
>>>>>> I tried modeling the 'childs' as containment and as not containment.
>>>>>> I always get the following output:
>>>>>>
>>>>>> parent childs: [c1, c2]
>>>>>> parent size: 2
>>>>>> parent first: c1
>>>>>> c1 childs: [cc1, cc2]
>>>>>> c1 size: 2
>>>>>> c1 first: cc1
>>>>>>
>>>>>> I guess that this is the way it should behave, loading the whole
>>>>>> object which also contains the childs. Then the child nodes are
>>>>>> loaded which also load the whole object ... and so on.
>>>>>> But I would like to have some kind of annotation to block the
>>>>>> loading of references.
>>>>>>
>>>>>> greets
>>>>>> Flavio
>>>>>>
>>>>>> Martin Taal wrote:
>>>>>>
>>>>>>> Hi Flavio,
>>>>>>> There is an issue that econtainer parent relations are eagerly
>>>>>>> loaded (this
>>>>>> issue has not been solved at the moment..).
>>>>>>> This should however not lead to the load of the children in the
>>>>>>> whole tree.
>>>>>>> On the server where running Teneo, do you need to persist the
>>>>>>> econtainer
>>>>>> relations? This can be disabled through an
>>>>>>> option in PersistenceOptions.
>>>>>>
>>>>>>> Then why does it load the children... A reason that I can think of
>>>>>>> is that
>>>>>> the code that sends the object over the wire
>>>>>>> touches the children collection and thereby forces its load. This
>>>>>>> can be
>>>>>> prevented, but can you check if this is indeed
>>>>>>> the case?
>>>>>>
>>>>>>> gr. Martin
>>>>>>
>>>>>>> Flavio Donzé wrote:
>>>>>>>> Hey Martin
>>>>>>>>
>>>>>>>> Thanks for the quick reply!
>>>>>>>>
>>>>>>>> Both the childs and the parent are read (the whole tree).
>>>>>>>>
>>>>>>>> The main problem is the children, I could make a workaround (only
>>>>>>>> use the parent Id instead of a direct TreeNode reference) or even
>>>>>>>> remove the parent reference.
>>>>>>>>
>>>>>>>> But if there is a way to block Teneo from reading the parent
>>>>>>>> reference it would be great.
>>>>>>>>
>>>>>>>>
>>>>>>>> thanks and greets
>>>>>>>> Flavio
>>>>>>>>
>>>>>>>> Martin Taal wrote:
>>>>>>>>
>>>>>>>>> Hi Flavio,
>>>>>>>>> Is also the parent of the treenode read? Or 'only' the children?
>>>>>>>>
>>>>>>>>> gr. Martin
>>>>>>>>
>>>>>>>>> Flavio Donzé wrote:
>>>>>>>>>> Hello Martin
>>>>>>>>>>
>>>>>>>>>> I modeled a Parent/Child relationship in an object called
>>>>>>>>>> TreeNode.
>>>>>>>>>> In my Server/Client application (using Riena to transfer
>>>>>>>>>> objects) I want to read the child TreeNodes by my self.
>>>>>>>>>> Right now if I read a TreeNode some where in the tree, the
>>>>>>>>>> whole tree is loaded.
>>>>>>>>>>
>>>>>>>>>> Well I can not use PersistenceOptions, because this needs to
>>>>>>>>>> apply only for this Entity and PersistenceOptions.SET_PROXY
>>>>>>>>>> wouldn't work anyway since the objects on the client wouldn't
>>>>>>>>>> know how to resolve the proxy.
>>>>>>>>>>
>>>>>>>>>> As far as I know using the "FetchType Lazy" also creates proxies.
>>>>>>>>>>
>>>>>>>>>> So what would be the best way to block Teneo/Hibernate to load
>>>>>>>>>> the childs?
>>>>>>>>>>
>>>>>>>>>> Here the ecore declaration of TreeNode:
>>>>>>>>>>
>>>>>>>>>> <eClassifiers xsi:type="ecore:EClass" name="TreeNode"
>>>>>>>>>> eSuperTypes="#//BasicObject">
>>>>>>>>>> <eOperations name="addChild">
>>>>>>>>>> <eParameters name="node" eType="#//TreeNode"/>
>>>>>>>>>> </eOperations>
>>>>>>>>>> <eOperations name="getChild" eType="#//TreeNode">
>>>>>>>>>> <eParameters name="id" eType="ecore:EDataType
>>>>>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>>>>>>> </eOperations>
>>>>>>>>>> <eOperations name="hasChilds" eType="ecore:EDataType
>>>>>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EBoolean"/>
>>>>>>>>>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="name"
>>>>>>>>>> eType="ecore:EDataType
>>>>>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>>>>>>> <eStructuralFeatures xsi:type="ecore:EReference"
>>>>>>>>>> name="childs" upperBound="-1"
>>>>>>>>>> eType="#//TreeNode" containment="true"/>
>>>>>>>>>> <eStructuralFeatures xsi:type="ecore:EReference"
>>>>>>>>>> name="object" eType="#//ObjectRef"
>>>>>>>>>> containment="true"/>
>>>>>>>>>> <eStructuralFeatures xsi:type="ecore:EReference"
>>>>>>>>>> name="parent" eType="#//TreeNode"/>
>>>>>>>>>> <eStructuralFeatures xsi:type="ecore:EAttribute" name="type"
>>>>>>>>>> eType="ecore:EDataType
>>>>>>>>>> http://www.eclipse.org/emf/2002/Ecore#//EString"/>
>>>>>>>>>> </eClassifiers>
>>>>>>>>>>
>>>>>>>>>>
>>>>>>>>>> I appreciate any help, I searched the web but couldn't find a
>>>>>>>>>> fitting solution.
>>>>>>>>>>
>>>>>>>>>>
>>>>>>>>
>>>>>>>>
>>>>>>>>
>>>>>>>>
>>>>>>
>>>>>>
>>>>>>
>>>>>>
>>>>
>>>>
>>>>
>>>>
>>
>>
>>
>>


Prozessmanagement und Qualitätsmanagement Software QMS/IMS
https://www.scodi.ch
Previous Topic:PackageNotFoundException: Package with uri 'http://schema.omg.org/spec/XMI/2.1' not found
Next Topic:EMF.edit: Filtering list objects in the tree
Goto Forum:
  


Current Time: Thu Apr 18 04:57:09 GMT 2024

Powered by FUDForum. Page generated in 0.02724 seconds
.:: Contact :: Home ::.

Powered by: FUDforum 3.0.2.
Copyright ©2001-2010 FUDforum Bulletin Board Software

Back to the top