You are viewing a plain text version of this content. The canonical link for it is here.
Posted to user@cayenne.apache.org by Ramiro Aparicio <ra...@prot-on.com> on 2012/10/05 16:28:30 UTC

Re: Vertical inheritance with relationships

El 19/09/2012 22:12, Andrus Adamchik escribió:
> On Sep 19, 2012, at 11:24 AM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>
>> BTW I tried to do everything with 3.0.2 modeller and finally updated to 3.1.B1 modeller, Will the model created with 3.1.B1 modeller work with 3.0.2 runtime? (I want to update the runtime but just in case I can not do it).
> No, once you upgrade the Model to 3.1, there's no (automated) way to go back to 3.0. The project structure is different in 3.1. The biggest change is that the new projects have at most 1 domain per project. It is probably doable by manually editing XML, but there's little point in that. After all the only reason to use the new Modeler is if you are planning to use the new runtime.
>
> I'll try to find time to get to the rest of your message. I rarely if ever use vertical inheritance, but I may try out your scenario.
>
> Andrus
>

Hi again,
Ok after the big refactoring I am now able to test this and I get this 
exception on commit:
"Cannot set the read-only flattened relationship 'toUser' in ObjEntity 
'SessionLogWeb'."
or
"Cannot set the read-only flattened relationship 'runtimeRelationship1' 
in ObjEntity 'SessionLog'."
depending on which side I try to use when setting the relationship.
(SessionLogWeb is WebSession on my previous example and SessionLog is 
Session)

So even if only one side of the relationship is marked as read only it 
is not possible to set the relationship from either side, as this kind 
of mapping is a bit unexplored using cayenne I will happily try any 
different options but I would like to mantain the vertical inheritance 
as this is a logging table that will hold millions of records so using a 
shared table will waste too much space.

Thanks in advance.

Ramiro Aparicio

Re: Vertical inheritance with relationships

Posted by Ramiro Aparicio <ra...@prot-on.com>.
Uppss sorry I was refering to single table, I read the docs some time 
ago and I think horizontal and single table got merged on my mind :D

El 10/10/2012 13:33, Andrus Adamchik escribió:
> Hmm… I am confused about you mentioning horizontal inheritance. AFAIK we never claimed that Cayenne would support that:
>
> http://cayenne.apache.org/doc/modeling-inheritance.html
>
>
>> I think that you are proposing using a non abstract session_log
> It can be abstract if you want.
>
>> and just use relationships to session_log_api and session_log_web that could work,
>> indeed is that would be the only way to be able to traverse from activity_log to session_log_api/web as with plain vertical I did not found a way.
> Correct.
>
>
> On Oct 10, 2012, at 1:19 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>
>> Hi Andrus,
>>
>> Nice you were able to track the error, I finally yesterday changed the model to be horizontal inheritance and it seems it is working. I am not sure of your proposed changes to the model, I think that you are proposing using a non abstract session_log and just use relationships to session_log_api and session_log_web that could work, indeed is that would be the only way to be able to traverse from activity_log to session_log_api/web as with plain vertical I did not found a way.
>>
>> Anyway I think I will continue with horizontal as one of the problems I found is that I need  to query based on user name and that was really dificult to handle using vertical (it can be reached to User but it needs to process different paths).
>>
>> Anyway aside from the already reported bugs here is the list of bugs I think it should be addressed to have vertical working:
>> 1.- Instanciating problem, I think this leads to a major rewrite on result instanciating, but for inheritance what is expected is that the correct child class is instanciated even if the function return type is the abstract class, this happens with every relationship from and to a parent class.
>> 2.- Modeller creating multiple relationships for the same parent relationship, if parent table has a relationship, syncing objectEntity creates 3 relationships (parent and 2 childs) and it should take into account how it where modelled or at least just create one for parent and use the previous point to return the correct child one (but anyway this is open to discussion). The problem is that right now I need to be able to retrieve the SessionLog from ActivityLog so I must check which of the 2 relationships have a non null value (imagine the same with 4 or 5 children).
>> 3.- Using vertical there is no easy way using expressions to make a query like this: select * from A a, C c where a.bId = c.id AND c.name = "foo" when A <-> B and B is parent of C (at least I did not found a way).
>> 4.- Using horizontal I now get this warnings on modeller: "Using of super entity's relationships A.relation as reversed relationship for sub entity is discouraged" this happens with several relationships in my model but I just deleted everyone I don't use except SessionLog <-> ActivityLog where I left the 3 created by point 2.
>>
>> I will continue with my testing today so I will write back with any new info I find.
>>
>>
>> El 09/10/2012 20:56, Andrus Adamchik escribió:
>>> Hi Ramiro,
>>>
>>> based on the model that you sent me earlier, I was able to reproduce another error and identify its cause:
>>>
>>> https://issues.apache.org/jira/browse/CAY-1746
>>>
>>> So slowly getting there...
>>>
>>>> Maybe I am just doing everything the wrong way, butI am starting to think that vertical inheritance is just not supported at all :( at least not it if has relationships, I am willing to help testing but even I will love to contribute, my boss won't allow me to work full time on this to be able to understand and fix all the issues, so I think I will need to move to horizontal inheritance even it is not what I would like to do :(
>>> No actually your mapping is correct. And I don't see problems with vertical inheritance per se, but rather with the flattened relationships and attributes present in common inheritance mappings. There are certainly rough spots in those. And common vertical inheritance scenarios are helping us to identify them. We'll work on fixing those of course.
>>>
>>> I really appreciate your desire to help fixing all these, and perfectly understand your work situation. Bearing with me on all these issues is already helping us :)
>>>
>>> As to what you should do in your application, I suggest the following - since "vertical" inheritance in Cayenne is really the same as "single table", only with flattened attributes and relationships (and it is the combination of the later that is giving us hard time), how about you keep the inheritance, but "unflatten" everything in subclasses, using individual ObjEntities and regular relationships for session_log_api and session_log_web?
>>>
>>> This should work more reliably.
>>>
>>> Thanks,
>>> Andrus
>>>
>>>
>>> On Oct 8, 2012, at 7:28 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>>> I found another error in this case, if Session has a couple of attributes and a relationship on his own, you can not recover Session from the related entities.
>>>> In my case Session it is related to ActivityLog so what I am doing here is just calling activityLog.getToSession() and this raises an instanciation error because Session is abstract and does not try to instanciate the subclass
>>>>
>>>> org.apache.cayenne.CayenneRuntimeException: [v.3.1B1 May 28 2012 18:42:43] Error creating object of class 'com.proton.ks.persistence.SessionLog'
>>>>   at org.apache.cayenne.reflect.PersistentDescriptor.createObject(PersistentDescriptor.java:288)
>>>>   at org.apache.cayenne.reflect.LazyClassDescriptorDecorator.createObject(LazyClassDescriptorDecorator.java:73)
>>>>   at org.apache.cayenne.access.DataContext.findOrCreateObject(DataContext.java:1178)
>>>>   at org.apache.cayenne.access.ObjectResolver.objectFromDataRow(ObjectResolver.java:151)
>>>>   at org.apache.cayenne.access.ObjectResolver.objectFromDataRow(ObjectResolver.java:137)
>>>>   at org.apache.cayenne.access.ObjectResolver.objectsFromDataRows(ObjectResolver.java:121)
>>>>   at org.apache.cayenne.access.ObjectResolver.synchronizedObjectsFromDataRows(ObjectResolver.java:102)
>>>>   at org.apache.cayenne.access.ObjectResolver.synchronizedRootResultNodeFromDataRows(ObjectResolver.java:93)
>>>>   at org.apache.cayenne.access.DataDomainQueryAction$ObjectConversionStrategy.toResultsTree(DataDomainQueryAction.java:581)
>>>>   at org.apache.cayenne.access.DataDomainQueryAction$SingleObjectConversionStrategy.convert(DataDomainQueryAction.java:637)
>>>>   at org.apache.cayenne.access.DataDomainQueryAction.interceptObjectConversion(DataDomainQueryAction.java:465)
>>>>   at org.apache.cayenne.access.DataDomainQueryAction.execute(DataDomainQueryAction.java:129)
>>>>   at org.apache.cayenne.access.DataDomain.onQueryNoFilters(DataDomain.java:754)
>>>>   at org.apache.cayenne.access.DataDomain$DataDomainQueryFilterChain.onQuery(DataDomain.java:1003)
>>>>   at org.apache.cayenne.access.DataDomain.onQuery(DataDomain.java:744)
>>>>   at org.apache.cayenne.util.ObjectContextQueryAction.runQuery(ObjectContextQueryAction.java:350)
>>>>   at org.apache.cayenne.util.ObjectContextQueryAction.executePostCache(ObjectContextQueryAction.java:106)
>>>>   at org.apache.cayenne.util.ObjectContextQueryAction.execute(ObjectContextQueryAction.java:93)
>>>>   at org.apache.cayenne.access.DataContext.onQuery(DataContext.java:989)
>>>>   at org.apache.cayenne.access.DataContext.performQuery(DataContext.java:978)
>>>>   at org.apache.cayenne.access.ToOneFault.doResolveFault(ToOneFault.java:81)
>>>>   at org.apache.cayenne.access.ToOneFault.resolveFault(ToOneFault.java:54)
>>>>   at org.apache.cayenne.CayenneDataObject.readProperty(CayenneDataObject.java:186)
>>>>   at com.proton.ks.persistence.cayenne._ActivityLog.getToSessionLog(_ActivityLog.java:73)
>>>>
>>>> I can just make Session (SessionLog in my app) non abstract but even then I will not be able to reach SessionWeb or SessionClient (and their attributes) as I can not create a relationship to them. In modeller session table there is such relations, but in classes there aren't and can not be created.
>>>>
>>>> Maybe I am just doing everything the wrong way, butI am starting to think that vertical inheritance is just not supported at all :( at least not it if has relationships, I am willing to help testing but even I will love to contribute, my boss won't allow me to work full time on this to be able to understand and fix all the issues, so I think I will need to move to horizontal inheritance even it is not what I would like to do :(
>>>>
>>>>
>>>>
>>>>
>>>> El 08/10/2012 14:15, Andrus Adamchik escribió:
>>>>>> In our model the session table is a MYSQL autoincrement field so it is marked as database generated on Session table, but as sessionWeb and sessionClient rely on Session id they have PK strategy as default, but on commit I get an error creating the sessionWeb row as id is null.
>>>>> The first thing to doublecheck is a DbRelationship between Session and sessionWeb (and Session and sessionClient) - it must be 1..1 and have "To Dep PK" checked. This should propagate the PK from Session to the dependent tables.
>>>>>
>>>>> If that doesn't help, yeah, you can send me the model.
>>>>>
>>>>> Andrus
>>>>>
>>>>>
>>>>> On Oct 8, 2012, at 2:44 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>>>>
>>>>>> Hi Andrus,
>>>>>>
>>>>>> First of all thank you for all the effort and the fast reply time, I really appreciate your help with this issue.
>>>>>> Then the bad news after some decompiling to understand how to load modules on web containers I was able to configure everything but it seemed that still did not want to work, debugging the problem is that my relationships are marked as runtime even if they are defined in the model, so to avoid that I just removed that condition from your code (not sure if that can create some problems in the future) but now I am struggling against a commit exception because of the PK.
>>>>>> In our model the session table is a MYSQL autoincrement field so it is marked as database generated on Session table, but as sessionWeb and sessionClient rely on Session id they have PK strategy as default, but on commit I get an error creating the sessionWeb row as id is null.
>>>>>>
>>>>>> Here is the sequence of inserts as logged:
>>>>>>
>>>>>> [2012-10-08 13:38:05,376] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logBeginTransaction:350)- --- transaction started.
>>>>>> [2012-10-08 13:38:05,392] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO session_log (sessionStart, sessionType) VALUES (?, ?)
>>>>>> [2012-10-08 13:38:05,392] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [bind: 1->sessionStart:'2012-10-08 13:38:05.314', 2->sessionType:2]
>>>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logGeneratedKey:218)- Generated PK: session_log.idSessionLog = 102839
>>>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logUpdateCount:344)- === updated 1 row.
>>>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO activity_log (Document_idDocument, SessionLog_idSessionLog, action, log_datetime, msg_params, successful) VALUES (?, ?, ?, ?, ?, ?)
>>>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [bind: 1->Document_idDocument:NULL, 2->SessionLog_idSessionLog:102839, 3->action:04, 4->log_datetime:'2012-10-08 13:38:05.314', 5->msg_params:NULL, 6->successful:NULL]
>>>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logGeneratedKey:218)- Generated PK: activity_log.idActivityLog = 124301
>>>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logUpdateCount:344)- === updated 1 row.
>>>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO session_log_web (User_idUser, id, ip, userAgent) VALUES (?, ?, ?, ?)
>>>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [batch bind: 1->User_idUser:NULL, 2->id:NULL, 3->ip:< 7F,00,00,01>, 4->userAgent:'Computer/Windows 7/Firefox']
>>>>>>
>>>>>> I need to check why the idUser is null but that maybe a controller error.
>>>>>> If you are ok with that I can send you the full model so you can check everything is configured as it should (I think I double checked everything but just in case).
>>>>>>
>>>>>> I will try any workaround I am able to imagine and publish any new info.
>>>>>>
>>>>>> Ramiro Aparicio
>>>>>>
>>>>>> El 05/10/2012 23:12, Andrus Adamchik escribió:
>>>>>>> Oh, and actually I think we can fix it in the interim per https://issues.apache.org/jira/browse/CAY-1744 … The "hack" in the example makes me blush :)
>>>>>>>
>>>>>>> Andrus
>>>>>>>
>>>>>>>
>>>>>>> On Oct 6, 2012, at 12:04 AM, Andrus Adamchik <an...@objectstyle.org> wrote:
>>>>>>>
>>>>>>>> Hi Ramiro,
>>>>>>>>
>>>>>>>> Finally I have something specific for you: https://issues.apache.org/jira/browse/CAY-1743
>>>>>>>>
>>>>>>>> In the source code attached to this Jira, I am simply blocking "readOnly" status of all model relationships. The example is a completely self-conatined project. It is built against 3.2M1-SNAPSHOT (SVN trunk), but it should work with 3.1B1 as well. And for 3.0.x, you can simply "inline" the fancy DI module code in "cayennehacks"…
>>>>>>>>
>>>>>>>> Take a look at Main.java and cayennehacks package. The "hacks" is what it takes now to make vertical inheritance relationships work.
>>>>>>>>
>>>>>>>>> If I try to creat a entity relationship on User I must set the target to Session entity and not WebSession, if I set it to WebSession tells me there is no mapping and if I choose the correct mapping to WebSession then as there is no entity linked to that table it complains about no target entity.
>>>>>>>> This part worked for me on 3.1B1 Modeler.
>>>>>>>>
>>>>>>>> Andrus
>>>>>>>>
>>>>>>>>
>>>>>>>>
>>>>>>>> On Oct 5, 2012, at 5:28 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>>>>>>>
>>>>>>>>> El 19/09/2012 22:12, Andrus Adamchik escribió:
>>>>>>>>>> On Sep 19, 2012, at 11:24 AM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>>>>>>>>>
>>>>>>>>>>> BTW I tried to do everything with 3.0.2 modeller and finally updated to 3.1.B1 modeller, Will the model created with 3.1.B1 modeller work with 3.0.2 runtime? (I want to update the runtime but just in case I can not do it).
>>>>>>>>>> No, once you upgrade the Model to 3.1, there's no (automated) way to go back to 3.0. The project structure is different in 3.1. The biggest change is that the new projects have at most 1 domain per project. It is probably doable by manually editing XML, but there's little point in that. After all the only reason to use the new Modeler is if you are planning to use the new runtime.
>>>>>>>>>>
>>>>>>>>>> I'll try to find time to get to the rest of your message. I rarely if ever use vertical inheritance, but I may try out your scenario.
>>>>>>>>>>
>>>>>>>>>> Andrus
>>>>>>>>>>
>>>>>>>>> Hi again,
>>>>>>>>> Ok after the big refactoring I am now able to test this and I get this exception on commit:
>>>>>>>>> "Cannot set the read-only flattened relationship 'toUser' in ObjEntity 'SessionLogWeb'."
>>>>>>>>> or
>>>>>>>>> "Cannot set the read-only flattened relationship 'runtimeRelationship1' in ObjEntity 'SessionLog'."
>>>>>>>>> depending on which side I try to use when setting the relationship.
>>>>>>>>> (SessionLogWeb is WebSession on my previous example and SessionLog is Session)
>>>>>>>>>
>>>>>>>>> So even if only one side of the relationship is marked as read only it is not possible to set the relationship from either side, as this kind of mapping is a bit unexplored using cayenne I will happily try any different options but I would like to mantain the vertical inheritance as this is a logging table that will hold millions of records so using a shared table will waste too much space.
>>>>>>>>>
>>>>>>>>> Thanks in advance.
>>>>>>>>>
>>>>>>>>> Ramiro Aparicio
>>>>>>>>>
>>


Re: Vertical inheritance with relationships

Posted by Andrus Adamchik <an...@objectstyle.org>.
Hmm… I am confused about you mentioning horizontal inheritance. AFAIK we never claimed that Cayenne would support that: 

http://cayenne.apache.org/doc/modeling-inheritance.html


> I think that you are proposing using a non abstract session_log

It can be abstract if you want.

> and just use relationships to session_log_api and session_log_web that could work,
> indeed is that would be the only way to be able to traverse from activity_log to session_log_api/web as with plain vertical I did not found a way.

Correct. 


On Oct 10, 2012, at 1:19 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:

> Hi Andrus,
> 
> Nice you were able to track the error, I finally yesterday changed the model to be horizontal inheritance and it seems it is working. I am not sure of your proposed changes to the model, I think that you are proposing using a non abstract session_log and just use relationships to session_log_api and session_log_web that could work, indeed is that would be the only way to be able to traverse from activity_log to session_log_api/web as with plain vertical I did not found a way.
> 
> Anyway I think I will continue with horizontal as one of the problems I found is that I need  to query based on user name and that was really dificult to handle using vertical (it can be reached to User but it needs to process different paths).
> 
> Anyway aside from the already reported bugs here is the list of bugs I think it should be addressed to have vertical working:
> 1.- Instanciating problem, I think this leads to a major rewrite on result instanciating, but for inheritance what is expected is that the correct child class is instanciated even if the function return type is the abstract class, this happens with every relationship from and to a parent class.
> 2.- Modeller creating multiple relationships for the same parent relationship, if parent table has a relationship, syncing objectEntity creates 3 relationships (parent and 2 childs) and it should take into account how it where modelled or at least just create one for parent and use the previous point to return the correct child one (but anyway this is open to discussion). The problem is that right now I need to be able to retrieve the SessionLog from ActivityLog so I must check which of the 2 relationships have a non null value (imagine the same with 4 or 5 children).
> 3.- Using vertical there is no easy way using expressions to make a query like this: select * from A a, C c where a.bId = c.id AND c.name = "foo" when A <-> B and B is parent of C (at least I did not found a way).
> 4.- Using horizontal I now get this warnings on modeller: "Using of super entity's relationships A.relation as reversed relationship for sub entity is discouraged" this happens with several relationships in my model but I just deleted everyone I don't use except SessionLog <-> ActivityLog where I left the 3 created by point 2.
> 
> I will continue with my testing today so I will write back with any new info I find.
> 
> 
> El 09/10/2012 20:56, Andrus Adamchik escribió:
>> Hi Ramiro,
>> 
>> based on the model that you sent me earlier, I was able to reproduce another error and identify its cause:
>> 
>> https://issues.apache.org/jira/browse/CAY-1746
>> 
>> So slowly getting there...
>> 
>>> Maybe I am just doing everything the wrong way, butI am starting to think that vertical inheritance is just not supported at all :( at least not it if has relationships, I am willing to help testing but even I will love to contribute, my boss won't allow me to work full time on this to be able to understand and fix all the issues, so I think I will need to move to horizontal inheritance even it is not what I would like to do :(
>> No actually your mapping is correct. And I don't see problems with vertical inheritance per se, but rather with the flattened relationships and attributes present in common inheritance mappings. There are certainly rough spots in those. And common vertical inheritance scenarios are helping us to identify them. We'll work on fixing those of course.
>> 
>> I really appreciate your desire to help fixing all these, and perfectly understand your work situation. Bearing with me on all these issues is already helping us :)
>> 
>> As to what you should do in your application, I suggest the following - since "vertical" inheritance in Cayenne is really the same as "single table", only with flattened attributes and relationships (and it is the combination of the later that is giving us hard time), how about you keep the inheritance, but "unflatten" everything in subclasses, using individual ObjEntities and regular relationships for session_log_api and session_log_web?
>> 
>> This should work more reliably.
>> 
>> Thanks,
>> Andrus
>> 
>> 
>> On Oct 8, 2012, at 7:28 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>> I found another error in this case, if Session has a couple of attributes and a relationship on his own, you can not recover Session from the related entities.
>>> In my case Session it is related to ActivityLog so what I am doing here is just calling activityLog.getToSession() and this raises an instanciation error because Session is abstract and does not try to instanciate the subclass
>>> 
>>> org.apache.cayenne.CayenneRuntimeException: [v.3.1B1 May 28 2012 18:42:43] Error creating object of class 'com.proton.ks.persistence.SessionLog'
>>>  at org.apache.cayenne.reflect.PersistentDescriptor.createObject(PersistentDescriptor.java:288)
>>>  at org.apache.cayenne.reflect.LazyClassDescriptorDecorator.createObject(LazyClassDescriptorDecorator.java:73)
>>>  at org.apache.cayenne.access.DataContext.findOrCreateObject(DataContext.java:1178)
>>>  at org.apache.cayenne.access.ObjectResolver.objectFromDataRow(ObjectResolver.java:151)
>>>  at org.apache.cayenne.access.ObjectResolver.objectFromDataRow(ObjectResolver.java:137)
>>>  at org.apache.cayenne.access.ObjectResolver.objectsFromDataRows(ObjectResolver.java:121)
>>>  at org.apache.cayenne.access.ObjectResolver.synchronizedObjectsFromDataRows(ObjectResolver.java:102)
>>>  at org.apache.cayenne.access.ObjectResolver.synchronizedRootResultNodeFromDataRows(ObjectResolver.java:93)
>>>  at org.apache.cayenne.access.DataDomainQueryAction$ObjectConversionStrategy.toResultsTree(DataDomainQueryAction.java:581)
>>>  at org.apache.cayenne.access.DataDomainQueryAction$SingleObjectConversionStrategy.convert(DataDomainQueryAction.java:637)
>>>  at org.apache.cayenne.access.DataDomainQueryAction.interceptObjectConversion(DataDomainQueryAction.java:465)
>>>  at org.apache.cayenne.access.DataDomainQueryAction.execute(DataDomainQueryAction.java:129)
>>>  at org.apache.cayenne.access.DataDomain.onQueryNoFilters(DataDomain.java:754)
>>>  at org.apache.cayenne.access.DataDomain$DataDomainQueryFilterChain.onQuery(DataDomain.java:1003)
>>>  at org.apache.cayenne.access.DataDomain.onQuery(DataDomain.java:744)
>>>  at org.apache.cayenne.util.ObjectContextQueryAction.runQuery(ObjectContextQueryAction.java:350)
>>>  at org.apache.cayenne.util.ObjectContextQueryAction.executePostCache(ObjectContextQueryAction.java:106)
>>>  at org.apache.cayenne.util.ObjectContextQueryAction.execute(ObjectContextQueryAction.java:93)
>>>  at org.apache.cayenne.access.DataContext.onQuery(DataContext.java:989)
>>>  at org.apache.cayenne.access.DataContext.performQuery(DataContext.java:978)
>>>  at org.apache.cayenne.access.ToOneFault.doResolveFault(ToOneFault.java:81)
>>>  at org.apache.cayenne.access.ToOneFault.resolveFault(ToOneFault.java:54)
>>>  at org.apache.cayenne.CayenneDataObject.readProperty(CayenneDataObject.java:186)
>>>  at com.proton.ks.persistence.cayenne._ActivityLog.getToSessionLog(_ActivityLog.java:73)
>>> 
>>> I can just make Session (SessionLog in my app) non abstract but even then I will not be able to reach SessionWeb or SessionClient (and their attributes) as I can not create a relationship to them. In modeller session table there is such relations, but in classes there aren't and can not be created.
>>> 
>>> Maybe I am just doing everything the wrong way, butI am starting to think that vertical inheritance is just not supported at all :( at least not it if has relationships, I am willing to help testing but even I will love to contribute, my boss won't allow me to work full time on this to be able to understand and fix all the issues, so I think I will need to move to horizontal inheritance even it is not what I would like to do :(
>>> 
>>> 
>>> 
>>> 
>>> El 08/10/2012 14:15, Andrus Adamchik escribió:
>>>>> In our model the session table is a MYSQL autoincrement field so it is marked as database generated on Session table, but as sessionWeb and sessionClient rely on Session id they have PK strategy as default, but on commit I get an error creating the sessionWeb row as id is null.
>>>> The first thing to doublecheck is a DbRelationship between Session and sessionWeb (and Session and sessionClient) - it must be 1..1 and have "To Dep PK" checked. This should propagate the PK from Session to the dependent tables.
>>>> 
>>>> If that doesn't help, yeah, you can send me the model.
>>>> 
>>>> Andrus
>>>> 
>>>> 
>>>> On Oct 8, 2012, at 2:44 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>>> 
>>>>> Hi Andrus,
>>>>> 
>>>>> First of all thank you for all the effort and the fast reply time, I really appreciate your help with this issue.
>>>>> Then the bad news after some decompiling to understand how to load modules on web containers I was able to configure everything but it seemed that still did not want to work, debugging the problem is that my relationships are marked as runtime even if they are defined in the model, so to avoid that I just removed that condition from your code (not sure if that can create some problems in the future) but now I am struggling against a commit exception because of the PK.
>>>>> In our model the session table is a MYSQL autoincrement field so it is marked as database generated on Session table, but as sessionWeb and sessionClient rely on Session id they have PK strategy as default, but on commit I get an error creating the sessionWeb row as id is null.
>>>>> 
>>>>> Here is the sequence of inserts as logged:
>>>>> 
>>>>> [2012-10-08 13:38:05,376] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logBeginTransaction:350)- --- transaction started.
>>>>> [2012-10-08 13:38:05,392] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO session_log (sessionStart, sessionType) VALUES (?, ?)
>>>>> [2012-10-08 13:38:05,392] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [bind: 1->sessionStart:'2012-10-08 13:38:05.314', 2->sessionType:2]
>>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logGeneratedKey:218)- Generated PK: session_log.idSessionLog = 102839
>>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logUpdateCount:344)- === updated 1 row.
>>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO activity_log (Document_idDocument, SessionLog_idSessionLog, action, log_datetime, msg_params, successful) VALUES (?, ?, ?, ?, ?, ?)
>>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [bind: 1->Document_idDocument:NULL, 2->SessionLog_idSessionLog:102839, 3->action:04, 4->log_datetime:'2012-10-08 13:38:05.314', 5->msg_params:NULL, 6->successful:NULL]
>>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logGeneratedKey:218)- Generated PK: activity_log.idActivityLog = 124301
>>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logUpdateCount:344)- === updated 1 row.
>>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO session_log_web (User_idUser, id, ip, userAgent) VALUES (?, ?, ?, ?)
>>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [batch bind: 1->User_idUser:NULL, 2->id:NULL, 3->ip:< 7F,00,00,01>, 4->userAgent:'Computer/Windows 7/Firefox']
>>>>> 
>>>>> I need to check why the idUser is null but that maybe a controller error.
>>>>> If you are ok with that I can send you the full model so you can check everything is configured as it should (I think I double checked everything but just in case).
>>>>> 
>>>>> I will try any workaround I am able to imagine and publish any new info.
>>>>> 
>>>>> Ramiro Aparicio
>>>>> 
>>>>> El 05/10/2012 23:12, Andrus Adamchik escribió:
>>>>>> Oh, and actually I think we can fix it in the interim per https://issues.apache.org/jira/browse/CAY-1744 … The "hack" in the example makes me blush :)
>>>>>> 
>>>>>> Andrus
>>>>>> 
>>>>>> 
>>>>>> On Oct 6, 2012, at 12:04 AM, Andrus Adamchik <an...@objectstyle.org> wrote:
>>>>>> 
>>>>>>> Hi Ramiro,
>>>>>>> 
>>>>>>> Finally I have something specific for you: https://issues.apache.org/jira/browse/CAY-1743
>>>>>>> 
>>>>>>> In the source code attached to this Jira, I am simply blocking "readOnly" status of all model relationships. The example is a completely self-conatined project. It is built against 3.2M1-SNAPSHOT (SVN trunk), but it should work with 3.1B1 as well. And for 3.0.x, you can simply "inline" the fancy DI module code in "cayennehacks"…
>>>>>>> 
>>>>>>> Take a look at Main.java and cayennehacks package. The "hacks" is what it takes now to make vertical inheritance relationships work.
>>>>>>> 
>>>>>>>> If I try to creat a entity relationship on User I must set the target to Session entity and not WebSession, if I set it to WebSession tells me there is no mapping and if I choose the correct mapping to WebSession then as there is no entity linked to that table it complains about no target entity.
>>>>>>> This part worked for me on 3.1B1 Modeler.
>>>>>>> 
>>>>>>> Andrus
>>>>>>> 
>>>>>>> 
>>>>>>> 
>>>>>>> On Oct 5, 2012, at 5:28 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>>>>>> 
>>>>>>>> El 19/09/2012 22:12, Andrus Adamchik escribió:
>>>>>>>>> On Sep 19, 2012, at 11:24 AM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>>>>>>>> 
>>>>>>>>>> BTW I tried to do everything with 3.0.2 modeller and finally updated to 3.1.B1 modeller, Will the model created with 3.1.B1 modeller work with 3.0.2 runtime? (I want to update the runtime but just in case I can not do it).
>>>>>>>>> No, once you upgrade the Model to 3.1, there's no (automated) way to go back to 3.0. The project structure is different in 3.1. The biggest change is that the new projects have at most 1 domain per project. It is probably doable by manually editing XML, but there's little point in that. After all the only reason to use the new Modeler is if you are planning to use the new runtime.
>>>>>>>>> 
>>>>>>>>> I'll try to find time to get to the rest of your message. I rarely if ever use vertical inheritance, but I may try out your scenario.
>>>>>>>>> 
>>>>>>>>> Andrus
>>>>>>>>> 
>>>>>>>> Hi again,
>>>>>>>> Ok after the big refactoring I am now able to test this and I get this exception on commit:
>>>>>>>> "Cannot set the read-only flattened relationship 'toUser' in ObjEntity 'SessionLogWeb'."
>>>>>>>> or
>>>>>>>> "Cannot set the read-only flattened relationship 'runtimeRelationship1' in ObjEntity 'SessionLog'."
>>>>>>>> depending on which side I try to use when setting the relationship.
>>>>>>>> (SessionLogWeb is WebSession on my previous example and SessionLog is Session)
>>>>>>>> 
>>>>>>>> So even if only one side of the relationship is marked as read only it is not possible to set the relationship from either side, as this kind of mapping is a bit unexplored using cayenne I will happily try any different options but I would like to mantain the vertical inheritance as this is a logging table that will hold millions of records so using a shared table will waste too much space.
>>>>>>>> 
>>>>>>>> Thanks in advance.
>>>>>>>> 
>>>>>>>> Ramiro Aparicio
>>>>>>>> 
>>> 
> 
> 


Re: Vertical inheritance with relationships

Posted by Ramiro Aparicio <ra...@prot-on.com>.
Hi Andrus,

Nice you were able to track the error, I finally yesterday changed the 
model to be horizontal inheritance and it seems it is working. I am not 
sure of your proposed changes to the model, I think that you are 
proposing using a non abstract session_log and just use relationships to 
session_log_api and session_log_web that could work, indeed is that 
would be the only way to be able to traverse from activity_log to 
session_log_api/web as with plain vertical I did not found a way.

Anyway I think I will continue with horizontal as one of the problems I 
found is that I need  to query based on user name and that was really 
dificult to handle using vertical (it can be reached to User but it 
needs to process different paths).

Anyway aside from the already reported bugs here is the list of bugs I 
think it should be addressed to have vertical working:
  1.- Instanciating problem, I think this leads to a major rewrite on 
result instanciating, but for inheritance what is expected is that the 
correct child class is instanciated even if the function return type is 
the abstract class, this happens with every relationship from and to a 
parent class.
  2.- Modeller creating multiple relationships for the same parent 
relationship, if parent table has a relationship, syncing objectEntity 
creates 3 relationships (parent and 2 childs) and it should take into 
account how it where modelled or at least just create one for parent and 
use the previous point to return the correct child one (but anyway this 
is open to discussion). The problem is that right now I need to be able 
to retrieve the SessionLog from ActivityLog so I must check which of the 
2 relationships have a non null value (imagine the same with 4 or 5 
children).
  3.- Using vertical there is no easy way using expressions to make a 
query like this: select * from A a, C c where a.bId = c.id AND c.name = 
"foo" when A <-> B and B is parent of C (at least I did not found a way).
  4.- Using horizontal I now get this warnings on modeller: "Using of 
super entity's relationships A.relation as reversed relationship for sub 
entity is discouraged" this happens with several relationships in my 
model but I just deleted everyone I don't use except SessionLog <-> 
ActivityLog where I left the 3 created by point 2.

I will continue with my testing today so I will write back with any new 
info I find.


El 09/10/2012 20:56, Andrus Adamchik escribió:
> Hi Ramiro,
>
> based on the model that you sent me earlier, I was able to reproduce another error and identify its cause:
>
> https://issues.apache.org/jira/browse/CAY-1746
>
> So slowly getting there...
>
>> Maybe I am just doing everything the wrong way, butI am starting to think that vertical inheritance is just not supported at all :( at least not it if has relationships, I am willing to help testing but even I will love to contribute, my boss won't allow me to work full time on this to be able to understand and fix all the issues, so I think I will need to move to horizontal inheritance even it is not what I would like to do :(
> No actually your mapping is correct. And I don't see problems with vertical inheritance per se, but rather with the flattened relationships and attributes present in common inheritance mappings. There are certainly rough spots in those. And common vertical inheritance scenarios are helping us to identify them. We'll work on fixing those of course.
>
> I really appreciate your desire to help fixing all these, and perfectly understand your work situation. Bearing with me on all these issues is already helping us :)
>
> As to what you should do in your application, I suggest the following - since "vertical" inheritance in Cayenne is really the same as "single table", only with flattened attributes and relationships (and it is the combination of the later that is giving us hard time), how about you keep the inheritance, but "unflatten" everything in subclasses, using individual ObjEntities and regular relationships for session_log_api and session_log_web?
>
> This should work more reliably.
>
> Thanks,
> Andrus
>
>
> On Oct 8, 2012, at 7:28 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>> I found another error in this case, if Session has a couple of attributes and a relationship on his own, you can not recover Session from the related entities.
>> In my case Session it is related to ActivityLog so what I am doing here is just calling activityLog.getToSession() and this raises an instanciation error because Session is abstract and does not try to instanciate the subclass
>>
>> org.apache.cayenne.CayenneRuntimeException: [v.3.1B1 May 28 2012 18:42:43] Error creating object of class 'com.proton.ks.persistence.SessionLog'
>>   at org.apache.cayenne.reflect.PersistentDescriptor.createObject(PersistentDescriptor.java:288)
>>   at org.apache.cayenne.reflect.LazyClassDescriptorDecorator.createObject(LazyClassDescriptorDecorator.java:73)
>>   at org.apache.cayenne.access.DataContext.findOrCreateObject(DataContext.java:1178)
>>   at org.apache.cayenne.access.ObjectResolver.objectFromDataRow(ObjectResolver.java:151)
>>   at org.apache.cayenne.access.ObjectResolver.objectFromDataRow(ObjectResolver.java:137)
>>   at org.apache.cayenne.access.ObjectResolver.objectsFromDataRows(ObjectResolver.java:121)
>>   at org.apache.cayenne.access.ObjectResolver.synchronizedObjectsFromDataRows(ObjectResolver.java:102)
>>   at org.apache.cayenne.access.ObjectResolver.synchronizedRootResultNodeFromDataRows(ObjectResolver.java:93)
>>   at org.apache.cayenne.access.DataDomainQueryAction$ObjectConversionStrategy.toResultsTree(DataDomainQueryAction.java:581)
>>   at org.apache.cayenne.access.DataDomainQueryAction$SingleObjectConversionStrategy.convert(DataDomainQueryAction.java:637)
>>   at org.apache.cayenne.access.DataDomainQueryAction.interceptObjectConversion(DataDomainQueryAction.java:465)
>>   at org.apache.cayenne.access.DataDomainQueryAction.execute(DataDomainQueryAction.java:129)
>>   at org.apache.cayenne.access.DataDomain.onQueryNoFilters(DataDomain.java:754)
>>   at org.apache.cayenne.access.DataDomain$DataDomainQueryFilterChain.onQuery(DataDomain.java:1003)
>>   at org.apache.cayenne.access.DataDomain.onQuery(DataDomain.java:744)
>>   at org.apache.cayenne.util.ObjectContextQueryAction.runQuery(ObjectContextQueryAction.java:350)
>>   at org.apache.cayenne.util.ObjectContextQueryAction.executePostCache(ObjectContextQueryAction.java:106)
>>   at org.apache.cayenne.util.ObjectContextQueryAction.execute(ObjectContextQueryAction.java:93)
>>   at org.apache.cayenne.access.DataContext.onQuery(DataContext.java:989)
>>   at org.apache.cayenne.access.DataContext.performQuery(DataContext.java:978)
>>   at org.apache.cayenne.access.ToOneFault.doResolveFault(ToOneFault.java:81)
>>   at org.apache.cayenne.access.ToOneFault.resolveFault(ToOneFault.java:54)
>>   at org.apache.cayenne.CayenneDataObject.readProperty(CayenneDataObject.java:186)
>>   at com.proton.ks.persistence.cayenne._ActivityLog.getToSessionLog(_ActivityLog.java:73)
>>
>> I can just make Session (SessionLog in my app) non abstract but even then I will not be able to reach SessionWeb or SessionClient (and their attributes) as I can not create a relationship to them. In modeller session table there is such relations, but in classes there aren't and can not be created.
>>
>> Maybe I am just doing everything the wrong way, butI am starting to think that vertical inheritance is just not supported at all :( at least not it if has relationships, I am willing to help testing but even I will love to contribute, my boss won't allow me to work full time on this to be able to understand and fix all the issues, so I think I will need to move to horizontal inheritance even it is not what I would like to do :(
>>
>>
>>
>>
>> El 08/10/2012 14:15, Andrus Adamchik escribió:
>>>> In our model the session table is a MYSQL autoincrement field so it is marked as database generated on Session table, but as sessionWeb and sessionClient rely on Session id they have PK strategy as default, but on commit I get an error creating the sessionWeb row as id is null.
>>> The first thing to doublecheck is a DbRelationship between Session and sessionWeb (and Session and sessionClient) - it must be 1..1 and have "To Dep PK" checked. This should propagate the PK from Session to the dependent tables.
>>>
>>> If that doesn't help, yeah, you can send me the model.
>>>
>>> Andrus
>>>
>>>
>>> On Oct 8, 2012, at 2:44 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>>
>>>> Hi Andrus,
>>>>
>>>> First of all thank you for all the effort and the fast reply time, I really appreciate your help with this issue.
>>>> Then the bad news after some decompiling to understand how to load modules on web containers I was able to configure everything but it seemed that still did not want to work, debugging the problem is that my relationships are marked as runtime even if they are defined in the model, so to avoid that I just removed that condition from your code (not sure if that can create some problems in the future) but now I am struggling against a commit exception because of the PK.
>>>> In our model the session table is a MYSQL autoincrement field so it is marked as database generated on Session table, but as sessionWeb and sessionClient rely on Session id they have PK strategy as default, but on commit I get an error creating the sessionWeb row as id is null.
>>>>
>>>> Here is the sequence of inserts as logged:
>>>>
>>>> [2012-10-08 13:38:05,376] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logBeginTransaction:350)- --- transaction started.
>>>> [2012-10-08 13:38:05,392] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO session_log (sessionStart, sessionType) VALUES (?, ?)
>>>> [2012-10-08 13:38:05,392] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [bind: 1->sessionStart:'2012-10-08 13:38:05.314', 2->sessionType:2]
>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logGeneratedKey:218)- Generated PK: session_log.idSessionLog = 102839
>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logUpdateCount:344)- === updated 1 row.
>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO activity_log (Document_idDocument, SessionLog_idSessionLog, action, log_datetime, msg_params, successful) VALUES (?, ?, ?, ?, ?, ?)
>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [bind: 1->Document_idDocument:NULL, 2->SessionLog_idSessionLog:102839, 3->action:04, 4->log_datetime:'2012-10-08 13:38:05.314', 5->msg_params:NULL, 6->successful:NULL]
>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logGeneratedKey:218)- Generated PK: activity_log.idActivityLog = 124301
>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logUpdateCount:344)- === updated 1 row.
>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO session_log_web (User_idUser, id, ip, userAgent) VALUES (?, ?, ?, ?)
>>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [batch bind: 1->User_idUser:NULL, 2->id:NULL, 3->ip:< 7F,00,00,01>, 4->userAgent:'Computer/Windows 7/Firefox']
>>>>
>>>> I need to check why the idUser is null but that maybe a controller error.
>>>> If you are ok with that I can send you the full model so you can check everything is configured as it should (I think I double checked everything but just in case).
>>>>
>>>> I will try any workaround I am able to imagine and publish any new info.
>>>>
>>>> Ramiro Aparicio
>>>>
>>>> El 05/10/2012 23:12, Andrus Adamchik escribió:
>>>>> Oh, and actually I think we can fix it in the interim per https://issues.apache.org/jira/browse/CAY-1744 … The "hack" in the example makes me blush :)
>>>>>
>>>>> Andrus
>>>>>
>>>>>
>>>>> On Oct 6, 2012, at 12:04 AM, Andrus Adamchik <an...@objectstyle.org> wrote:
>>>>>
>>>>>> Hi Ramiro,
>>>>>>
>>>>>> Finally I have something specific for you: https://issues.apache.org/jira/browse/CAY-1743
>>>>>>
>>>>>> In the source code attached to this Jira, I am simply blocking "readOnly" status of all model relationships. The example is a completely self-conatined project. It is built against 3.2M1-SNAPSHOT (SVN trunk), but it should work with 3.1B1 as well. And for 3.0.x, you can simply "inline" the fancy DI module code in "cayennehacks"…
>>>>>>
>>>>>> Take a look at Main.java and cayennehacks package. The "hacks" is what it takes now to make vertical inheritance relationships work.
>>>>>>
>>>>>>> If I try to creat a entity relationship on User I must set the target to Session entity and not WebSession, if I set it to WebSession tells me there is no mapping and if I choose the correct mapping to WebSession then as there is no entity linked to that table it complains about no target entity.
>>>>>> This part worked for me on 3.1B1 Modeler.
>>>>>>
>>>>>> Andrus
>>>>>>
>>>>>>
>>>>>>
>>>>>> On Oct 5, 2012, at 5:28 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>>>>>
>>>>>>> El 19/09/2012 22:12, Andrus Adamchik escribió:
>>>>>>>> On Sep 19, 2012, at 11:24 AM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>>>>>>>
>>>>>>>>> BTW I tried to do everything with 3.0.2 modeller and finally updated to 3.1.B1 modeller, Will the model created with 3.1.B1 modeller work with 3.0.2 runtime? (I want to update the runtime but just in case I can not do it).
>>>>>>>> No, once you upgrade the Model to 3.1, there's no (automated) way to go back to 3.0. The project structure is different in 3.1. The biggest change is that the new projects have at most 1 domain per project. It is probably doable by manually editing XML, but there's little point in that. After all the only reason to use the new Modeler is if you are planning to use the new runtime.
>>>>>>>>
>>>>>>>> I'll try to find time to get to the rest of your message. I rarely if ever use vertical inheritance, but I may try out your scenario.
>>>>>>>>
>>>>>>>> Andrus
>>>>>>>>
>>>>>>> Hi again,
>>>>>>> Ok after the big refactoring I am now able to test this and I get this exception on commit:
>>>>>>> "Cannot set the read-only flattened relationship 'toUser' in ObjEntity 'SessionLogWeb'."
>>>>>>> or
>>>>>>> "Cannot set the read-only flattened relationship 'runtimeRelationship1' in ObjEntity 'SessionLog'."
>>>>>>> depending on which side I try to use when setting the relationship.
>>>>>>> (SessionLogWeb is WebSession on my previous example and SessionLog is Session)
>>>>>>>
>>>>>>> So even if only one side of the relationship is marked as read only it is not possible to set the relationship from either side, as this kind of mapping is a bit unexplored using cayenne I will happily try any different options but I would like to mantain the vertical inheritance as this is a logging table that will hold millions of records so using a shared table will waste too much space.
>>>>>>>
>>>>>>> Thanks in advance.
>>>>>>>
>>>>>>> Ramiro Aparicio
>>>>>>>
>>


Re: Vertical inheritance with relationships

Posted by Andrus Adamchik <an...@objectstyle.org>.
Hi Ramiro,

based on the model that you sent me earlier, I was able to reproduce another error and identify its cause:

https://issues.apache.org/jira/browse/CAY-1746

So slowly getting there...

> Maybe I am just doing everything the wrong way, butI am starting to think that vertical inheritance is just not supported at all :( at least not it if has relationships, I am willing to help testing but even I will love to contribute, my boss won't allow me to work full time on this to be able to understand and fix all the issues, so I think I will need to move to horizontal inheritance even it is not what I would like to do :(

No actually your mapping is correct. And I don't see problems with vertical inheritance per se, but rather with the flattened relationships and attributes present in common inheritance mappings. There are certainly rough spots in those. And common vertical inheritance scenarios are helping us to identify them. We'll work on fixing those of course.

I really appreciate your desire to help fixing all these, and perfectly understand your work situation. Bearing with me on all these issues is already helping us :)

As to what you should do in your application, I suggest the following - since "vertical" inheritance in Cayenne is really the same as "single table", only with flattened attributes and relationships (and it is the combination of the later that is giving us hard time), how about you keep the inheritance, but "unflatten" everything in subclasses, using individual ObjEntities and regular relationships for session_log_api and session_log_web?

This should work more reliably.

Thanks,
Andrus


On Oct 8, 2012, at 7:28 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
> I found another error in this case, if Session has a couple of attributes and a relationship on his own, you can not recover Session from the related entities.
> In my case Session it is related to ActivityLog so what I am doing here is just calling activityLog.getToSession() and this raises an instanciation error because Session is abstract and does not try to instanciate the subclass
> 
> org.apache.cayenne.CayenneRuntimeException: [v.3.1B1 May 28 2012 18:42:43] Error creating object of class 'com.proton.ks.persistence.SessionLog'
>  at org.apache.cayenne.reflect.PersistentDescriptor.createObject(PersistentDescriptor.java:288)
>  at org.apache.cayenne.reflect.LazyClassDescriptorDecorator.createObject(LazyClassDescriptorDecorator.java:73)
>  at org.apache.cayenne.access.DataContext.findOrCreateObject(DataContext.java:1178)
>  at org.apache.cayenne.access.ObjectResolver.objectFromDataRow(ObjectResolver.java:151)
>  at org.apache.cayenne.access.ObjectResolver.objectFromDataRow(ObjectResolver.java:137)
>  at org.apache.cayenne.access.ObjectResolver.objectsFromDataRows(ObjectResolver.java:121)
>  at org.apache.cayenne.access.ObjectResolver.synchronizedObjectsFromDataRows(ObjectResolver.java:102)
>  at org.apache.cayenne.access.ObjectResolver.synchronizedRootResultNodeFromDataRows(ObjectResolver.java:93)
>  at org.apache.cayenne.access.DataDomainQueryAction$ObjectConversionStrategy.toResultsTree(DataDomainQueryAction.java:581)
>  at org.apache.cayenne.access.DataDomainQueryAction$SingleObjectConversionStrategy.convert(DataDomainQueryAction.java:637)
>  at org.apache.cayenne.access.DataDomainQueryAction.interceptObjectConversion(DataDomainQueryAction.java:465)
>  at org.apache.cayenne.access.DataDomainQueryAction.execute(DataDomainQueryAction.java:129)
>  at org.apache.cayenne.access.DataDomain.onQueryNoFilters(DataDomain.java:754)
>  at org.apache.cayenne.access.DataDomain$DataDomainQueryFilterChain.onQuery(DataDomain.java:1003)
>  at org.apache.cayenne.access.DataDomain.onQuery(DataDomain.java:744)
>  at org.apache.cayenne.util.ObjectContextQueryAction.runQuery(ObjectContextQueryAction.java:350)
>  at org.apache.cayenne.util.ObjectContextQueryAction.executePostCache(ObjectContextQueryAction.java:106)
>  at org.apache.cayenne.util.ObjectContextQueryAction.execute(ObjectContextQueryAction.java:93)
>  at org.apache.cayenne.access.DataContext.onQuery(DataContext.java:989)
>  at org.apache.cayenne.access.DataContext.performQuery(DataContext.java:978)
>  at org.apache.cayenne.access.ToOneFault.doResolveFault(ToOneFault.java:81)
>  at org.apache.cayenne.access.ToOneFault.resolveFault(ToOneFault.java:54)
>  at org.apache.cayenne.CayenneDataObject.readProperty(CayenneDataObject.java:186)
>  at com.proton.ks.persistence.cayenne._ActivityLog.getToSessionLog(_ActivityLog.java:73)
> 
> I can just make Session (SessionLog in my app) non abstract but even then I will not be able to reach SessionWeb or SessionClient (and their attributes) as I can not create a relationship to them. In modeller session table there is such relations, but in classes there aren't and can not be created.
> 
> Maybe I am just doing everything the wrong way, butI am starting to think that vertical inheritance is just not supported at all :( at least not it if has relationships, I am willing to help testing but even I will love to contribute, my boss won't allow me to work full time on this to be able to understand and fix all the issues, so I think I will need to move to horizontal inheritance even it is not what I would like to do :(
> 
> 
> 
> 
> El 08/10/2012 14:15, Andrus Adamchik escribió:
>>> In our model the session table is a MYSQL autoincrement field so it is marked as database generated on Session table, but as sessionWeb and sessionClient rely on Session id they have PK strategy as default, but on commit I get an error creating the sessionWeb row as id is null.
>> The first thing to doublecheck is a DbRelationship between Session and sessionWeb (and Session and sessionClient) - it must be 1..1 and have "To Dep PK" checked. This should propagate the PK from Session to the dependent tables.
>> 
>> If that doesn't help, yeah, you can send me the model.
>> 
>> Andrus
>> 
>> 
>> On Oct 8, 2012, at 2:44 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>> 
>>> Hi Andrus,
>>> 
>>> First of all thank you for all the effort and the fast reply time, I really appreciate your help with this issue.
>>> Then the bad news after some decompiling to understand how to load modules on web containers I was able to configure everything but it seemed that still did not want to work, debugging the problem is that my relationships are marked as runtime even if they are defined in the model, so to avoid that I just removed that condition from your code (not sure if that can create some problems in the future) but now I am struggling against a commit exception because of the PK.
>>> In our model the session table is a MYSQL autoincrement field so it is marked as database generated on Session table, but as sessionWeb and sessionClient rely on Session id they have PK strategy as default, but on commit I get an error creating the sessionWeb row as id is null.
>>> 
>>> Here is the sequence of inserts as logged:
>>> 
>>> [2012-10-08 13:38:05,376] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logBeginTransaction:350)- --- transaction started.
>>> [2012-10-08 13:38:05,392] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO session_log (sessionStart, sessionType) VALUES (?, ?)
>>> [2012-10-08 13:38:05,392] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [bind: 1->sessionStart:'2012-10-08 13:38:05.314', 2->sessionType:2]
>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logGeneratedKey:218)- Generated PK: session_log.idSessionLog = 102839
>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logUpdateCount:344)- === updated 1 row.
>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO activity_log (Document_idDocument, SessionLog_idSessionLog, action, log_datetime, msg_params, successful) VALUES (?, ?, ?, ?, ?, ?)
>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [bind: 1->Document_idDocument:NULL, 2->SessionLog_idSessionLog:102839, 3->action:04, 4->log_datetime:'2012-10-08 13:38:05.314', 5->msg_params:NULL, 6->successful:NULL]
>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logGeneratedKey:218)- Generated PK: activity_log.idActivityLog = 124301
>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logUpdateCount:344)- === updated 1 row.
>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO session_log_web (User_idUser, id, ip, userAgent) VALUES (?, ?, ?, ?)
>>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [batch bind: 1->User_idUser:NULL, 2->id:NULL, 3->ip:< 7F,00,00,01>, 4->userAgent:'Computer/Windows 7/Firefox']
>>> 
>>> I need to check why the idUser is null but that maybe a controller error.
>>> If you are ok with that I can send you the full model so you can check everything is configured as it should (I think I double checked everything but just in case).
>>> 
>>> I will try any workaround I am able to imagine and publish any new info.
>>> 
>>> Ramiro Aparicio
>>> 
>>> El 05/10/2012 23:12, Andrus Adamchik escribió:
>>>> Oh, and actually I think we can fix it in the interim per https://issues.apache.org/jira/browse/CAY-1744 … The "hack" in the example makes me blush :)
>>>> 
>>>> Andrus
>>>> 
>>>> 
>>>> On Oct 6, 2012, at 12:04 AM, Andrus Adamchik <an...@objectstyle.org> wrote:
>>>> 
>>>>> Hi Ramiro,
>>>>> 
>>>>> Finally I have something specific for you: https://issues.apache.org/jira/browse/CAY-1743
>>>>> 
>>>>> In the source code attached to this Jira, I am simply blocking "readOnly" status of all model relationships. The example is a completely self-conatined project. It is built against 3.2M1-SNAPSHOT (SVN trunk), but it should work with 3.1B1 as well. And for 3.0.x, you can simply "inline" the fancy DI module code in "cayennehacks"…
>>>>> 
>>>>> Take a look at Main.java and cayennehacks package. The "hacks" is what it takes now to make vertical inheritance relationships work.
>>>>> 
>>>>>> If I try to creat a entity relationship on User I must set the target to Session entity and not WebSession, if I set it to WebSession tells me there is no mapping and if I choose the correct mapping to WebSession then as there is no entity linked to that table it complains about no target entity.
>>>>> This part worked for me on 3.1B1 Modeler.
>>>>> 
>>>>> Andrus
>>>>> 
>>>>> 
>>>>> 
>>>>> On Oct 5, 2012, at 5:28 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>>>> 
>>>>>> El 19/09/2012 22:12, Andrus Adamchik escribió:
>>>>>>> On Sep 19, 2012, at 11:24 AM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>>>>>> 
>>>>>>>> BTW I tried to do everything with 3.0.2 modeller and finally updated to 3.1.B1 modeller, Will the model created with 3.1.B1 modeller work with 3.0.2 runtime? (I want to update the runtime but just in case I can not do it).
>>>>>>> No, once you upgrade the Model to 3.1, there's no (automated) way to go back to 3.0. The project structure is different in 3.1. The biggest change is that the new projects have at most 1 domain per project. It is probably doable by manually editing XML, but there's little point in that. After all the only reason to use the new Modeler is if you are planning to use the new runtime.
>>>>>>> 
>>>>>>> I'll try to find time to get to the rest of your message. I rarely if ever use vertical inheritance, but I may try out your scenario.
>>>>>>> 
>>>>>>> Andrus
>>>>>>> 
>>>>>> Hi again,
>>>>>> Ok after the big refactoring I am now able to test this and I get this exception on commit:
>>>>>> "Cannot set the read-only flattened relationship 'toUser' in ObjEntity 'SessionLogWeb'."
>>>>>> or
>>>>>> "Cannot set the read-only flattened relationship 'runtimeRelationship1' in ObjEntity 'SessionLog'."
>>>>>> depending on which side I try to use when setting the relationship.
>>>>>> (SessionLogWeb is WebSession on my previous example and SessionLog is Session)
>>>>>> 
>>>>>> So even if only one side of the relationship is marked as read only it is not possible to set the relationship from either side, as this kind of mapping is a bit unexplored using cayenne I will happily try any different options but I would like to mantain the vertical inheritance as this is a logging table that will hold millions of records so using a shared table will waste too much space.
>>>>>> 
>>>>>> Thanks in advance.
>>>>>> 
>>>>>> Ramiro Aparicio
>>>>>> 
>>> 
> 
> 


Re: Vertical inheritance with relationships

Posted by Ramiro Aparicio <ra...@prot-on.com>.
I found another error in this case, if Session has a couple of 
attributes and a relationship on his own, you can not recover Session 
from the related entities.
In my case Session it is related to ActivityLog so what I am doing here 
is just calling activityLog.getToSession() and this raises an 
instanciation error because Session is abstract and does not try to 
instanciate the subclass

org.apache.cayenne.CayenneRuntimeException: [v.3.1B1 May 28 2012 
18:42:43] Error creating object of class 
'com.proton.ks.persistence.SessionLog'
     at 
org.apache.cayenne.reflect.PersistentDescriptor.createObject(PersistentDescriptor.java:288)
     at 
org.apache.cayenne.reflect.LazyClassDescriptorDecorator.createObject(LazyClassDescriptorDecorator.java:73)
     at 
org.apache.cayenne.access.DataContext.findOrCreateObject(DataContext.java:1178)
     at 
org.apache.cayenne.access.ObjectResolver.objectFromDataRow(ObjectResolver.java:151)
     at 
org.apache.cayenne.access.ObjectResolver.objectFromDataRow(ObjectResolver.java:137)
     at 
org.apache.cayenne.access.ObjectResolver.objectsFromDataRows(ObjectResolver.java:121)
     at 
org.apache.cayenne.access.ObjectResolver.synchronizedObjectsFromDataRows(ObjectResolver.java:102)
     at 
org.apache.cayenne.access.ObjectResolver.synchronizedRootResultNodeFromDataRows(ObjectResolver.java:93)
     at 
org.apache.cayenne.access.DataDomainQueryAction$ObjectConversionStrategy.toResultsTree(DataDomainQueryAction.java:581)
     at 
org.apache.cayenne.access.DataDomainQueryAction$SingleObjectConversionStrategy.convert(DataDomainQueryAction.java:637)
     at 
org.apache.cayenne.access.DataDomainQueryAction.interceptObjectConversion(DataDomainQueryAction.java:465)
     at 
org.apache.cayenne.access.DataDomainQueryAction.execute(DataDomainQueryAction.java:129)
     at 
org.apache.cayenne.access.DataDomain.onQueryNoFilters(DataDomain.java:754)
     at 
org.apache.cayenne.access.DataDomain$DataDomainQueryFilterChain.onQuery(DataDomain.java:1003)
     at org.apache.cayenne.access.DataDomain.onQuery(DataDomain.java:744)
     at 
org.apache.cayenne.util.ObjectContextQueryAction.runQuery(ObjectContextQueryAction.java:350)
     at 
org.apache.cayenne.util.ObjectContextQueryAction.executePostCache(ObjectContextQueryAction.java:106)
     at 
org.apache.cayenne.util.ObjectContextQueryAction.execute(ObjectContextQueryAction.java:93)
     at org.apache.cayenne.access.DataContext.onQuery(DataContext.java:989)
     at 
org.apache.cayenne.access.DataContext.performQuery(DataContext.java:978)
     at 
org.apache.cayenne.access.ToOneFault.doResolveFault(ToOneFault.java:81)
     at 
org.apache.cayenne.access.ToOneFault.resolveFault(ToOneFault.java:54)
     at 
org.apache.cayenne.CayenneDataObject.readProperty(CayenneDataObject.java:186)
     at 
com.proton.ks.persistence.cayenne._ActivityLog.getToSessionLog(_ActivityLog.java:73)

I can just make Session (SessionLog in my app) non abstract but even 
then I will not be able to reach SessionWeb or SessionClient (and their 
attributes) as I can not create a relationship to them. In modeller 
session table there is such relations, but in classes there aren't and 
can not be created.

Maybe I am just doing everything the wrong way, butI am starting to 
think that vertical inheritance is just not supported at all :( at least 
not it if has relationships, I am willing to help testing but even I 
will love to contribute, my boss won't allow me to work full time on 
this to be able to understand and fix all the issues, so I think I will 
need to move to horizontal inheritance even it is not what I would like 
to do :(




El 08/10/2012 14:15, Andrus Adamchik escribió:
>> In our model the session table is a MYSQL autoincrement field so it is marked as database generated on Session table, but as sessionWeb and sessionClient rely on Session id they have PK strategy as default, but on commit I get an error creating the sessionWeb row as id is null.
> The first thing to doublecheck is a DbRelationship between Session and sessionWeb (and Session and sessionClient) - it must be 1..1 and have "To Dep PK" checked. This should propagate the PK from Session to the dependent tables.
>
> If that doesn't help, yeah, you can send me the model.
>
> Andrus
>
>
> On Oct 8, 2012, at 2:44 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>
>> Hi Andrus,
>>
>> First of all thank you for all the effort and the fast reply time, I really appreciate your help with this issue.
>> Then the bad news after some decompiling to understand how to load modules on web containers I was able to configure everything but it seemed that still did not want to work, debugging the problem is that my relationships are marked as runtime even if they are defined in the model, so to avoid that I just removed that condition from your code (not sure if that can create some problems in the future) but now I am struggling against a commit exception because of the PK.
>> In our model the session table is a MYSQL autoincrement field so it is marked as database generated on Session table, but as sessionWeb and sessionClient rely on Session id they have PK strategy as default, but on commit I get an error creating the sessionWeb row as id is null.
>>
>> Here is the sequence of inserts as logged:
>>
>> [2012-10-08 13:38:05,376] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logBeginTransaction:350)- --- transaction started.
>> [2012-10-08 13:38:05,392] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO session_log (sessionStart, sessionType) VALUES (?, ?)
>> [2012-10-08 13:38:05,392] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [bind: 1->sessionStart:'2012-10-08 13:38:05.314', 2->sessionType:2]
>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logGeneratedKey:218)- Generated PK: session_log.idSessionLog = 102839
>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logUpdateCount:344)- === updated 1 row.
>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO activity_log (Document_idDocument, SessionLog_idSessionLog, action, log_datetime, msg_params, successful) VALUES (?, ?, ?, ?, ?, ?)
>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [bind: 1->Document_idDocument:NULL, 2->SessionLog_idSessionLog:102839, 3->action:04, 4->log_datetime:'2012-10-08 13:38:05.314', 5->msg_params:NULL, 6->successful:NULL]
>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logGeneratedKey:218)- Generated PK: activity_log.idActivityLog = 124301
>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logUpdateCount:344)- === updated 1 row.
>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO session_log_web (User_idUser, id, ip, userAgent) VALUES (?, ?, ?, ?)
>> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [batch bind: 1->User_idUser:NULL, 2->id:NULL, 3->ip:< 7F,00,00,01>, 4->userAgent:'Computer/Windows 7/Firefox']
>>
>> I need to check why the idUser is null but that maybe a controller error.
>> If you are ok with that I can send you the full model so you can check everything is configured as it should (I think I double checked everything but just in case).
>>
>> I will try any workaround I am able to imagine and publish any new info.
>>
>> Ramiro Aparicio
>>
>> El 05/10/2012 23:12, Andrus Adamchik escribió:
>>> Oh, and actually I think we can fix it in the interim per https://issues.apache.org/jira/browse/CAY-1744 … The "hack" in the example makes me blush :)
>>>
>>> Andrus
>>>
>>>
>>> On Oct 6, 2012, at 12:04 AM, Andrus Adamchik <an...@objectstyle.org> wrote:
>>>
>>>> Hi Ramiro,
>>>>
>>>> Finally I have something specific for you: https://issues.apache.org/jira/browse/CAY-1743
>>>>
>>>> In the source code attached to this Jira, I am simply blocking "readOnly" status of all model relationships. The example is a completely self-conatined project. It is built against 3.2M1-SNAPSHOT (SVN trunk), but it should work with 3.1B1 as well. And for 3.0.x, you can simply "inline" the fancy DI module code in "cayennehacks"…
>>>>
>>>> Take a look at Main.java and cayennehacks package. The "hacks" is what it takes now to make vertical inheritance relationships work.
>>>>
>>>>> If I try to creat a entity relationship on User I must set the target to Session entity and not WebSession, if I set it to WebSession tells me there is no mapping and if I choose the correct mapping to WebSession then as there is no entity linked to that table it complains about no target entity.
>>>> This part worked for me on 3.1B1 Modeler.
>>>>
>>>> Andrus
>>>>
>>>>
>>>>
>>>> On Oct 5, 2012, at 5:28 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>>>
>>>>> El 19/09/2012 22:12, Andrus Adamchik escribió:
>>>>>> On Sep 19, 2012, at 11:24 AM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>>>>>
>>>>>>> BTW I tried to do everything with 3.0.2 modeller and finally updated to 3.1.B1 modeller, Will the model created with 3.1.B1 modeller work with 3.0.2 runtime? (I want to update the runtime but just in case I can not do it).
>>>>>> No, once you upgrade the Model to 3.1, there's no (automated) way to go back to 3.0. The project structure is different in 3.1. The biggest change is that the new projects have at most 1 domain per project. It is probably doable by manually editing XML, but there's little point in that. After all the only reason to use the new Modeler is if you are planning to use the new runtime.
>>>>>>
>>>>>> I'll try to find time to get to the rest of your message. I rarely if ever use vertical inheritance, but I may try out your scenario.
>>>>>>
>>>>>> Andrus
>>>>>>
>>>>> Hi again,
>>>>> Ok after the big refactoring I am now able to test this and I get this exception on commit:
>>>>> "Cannot set the read-only flattened relationship 'toUser' in ObjEntity 'SessionLogWeb'."
>>>>> or
>>>>> "Cannot set the read-only flattened relationship 'runtimeRelationship1' in ObjEntity 'SessionLog'."
>>>>> depending on which side I try to use when setting the relationship.
>>>>> (SessionLogWeb is WebSession on my previous example and SessionLog is Session)
>>>>>
>>>>> So even if only one side of the relationship is marked as read only it is not possible to set the relationship from either side, as this kind of mapping is a bit unexplored using cayenne I will happily try any different options but I would like to mantain the vertical inheritance as this is a logging table that will hold millions of records so using a shared table will waste too much space.
>>>>>
>>>>> Thanks in advance.
>>>>>
>>>>> Ramiro Aparicio
>>>>>
>>


Re: Vertical inheritance with relationships

Posted by Andrus Adamchik <an...@objectstyle.org>.
> 
> In our model the session table is a MYSQL autoincrement field so it is marked as database generated on Session table, but as sessionWeb and sessionClient rely on Session id they have PK strategy as default, but on commit I get an error creating the sessionWeb row as id is null.

The first thing to doublecheck is a DbRelationship between Session and sessionWeb (and Session and sessionClient) - it must be 1..1 and have "To Dep PK" checked. This should propagate the PK from Session to the dependent tables.

If that doesn't help, yeah, you can send me the model. 

Andrus


On Oct 8, 2012, at 2:44 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:

> Hi Andrus,
> 
> First of all thank you for all the effort and the fast reply time, I really appreciate your help with this issue.
> Then the bad news after some decompiling to understand how to load modules on web containers I was able to configure everything but it seemed that still did not want to work, debugging the problem is that my relationships are marked as runtime even if they are defined in the model, so to avoid that I just removed that condition from your code (not sure if that can create some problems in the future) but now I am struggling against a commit exception because of the PK.
> In our model the session table is a MYSQL autoincrement field so it is marked as database generated on Session table, but as sessionWeb and sessionClient rely on Session id they have PK strategy as default, but on commit I get an error creating the sessionWeb row as id is null.
> 
> Here is the sequence of inserts as logged:
> 
> [2012-10-08 13:38:05,376] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logBeginTransaction:350)- --- transaction started.
> [2012-10-08 13:38:05,392] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO session_log (sessionStart, sessionType) VALUES (?, ?)
> [2012-10-08 13:38:05,392] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [bind: 1->sessionStart:'2012-10-08 13:38:05.314', 2->sessionType:2]
> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logGeneratedKey:218)- Generated PK: session_log.idSessionLog = 102839
> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logUpdateCount:344)- === updated 1 row.
> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO activity_log (Document_idDocument, SessionLog_idSessionLog, action, log_datetime, msg_params, successful) VALUES (?, ?, ?, ?, ?, ?)
> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [bind: 1->Document_idDocument:NULL, 2->SessionLog_idSessionLog:102839, 3->action:04, 4->log_datetime:'2012-10-08 13:38:05.314', 5->msg_params:NULL, 6->successful:NULL]
> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logGeneratedKey:218)- Generated PK: activity_log.idActivityLog = 124301
> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logUpdateCount:344)- === updated 1 row.
> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO session_log_web (User_idUser, id, ip, userAgent) VALUES (?, ?, ?, ?)
> [2012-10-08 13:38:05,408] [http-8443-2] INFO (CommonsJdbcEventLogger.java:logQueryParameters:312)- [batch bind: 1->User_idUser:NULL, 2->id:NULL, 3->ip:< 7F,00,00,01>, 4->userAgent:'Computer/Windows 7/Firefox']
> 
> I need to check why the idUser is null but that maybe a controller error.
> If you are ok with that I can send you the full model so you can check everything is configured as it should (I think I double checked everything but just in case).
> 
> I will try any workaround I am able to imagine and publish any new info.
> 
> Ramiro Aparicio
> 
> El 05/10/2012 23:12, Andrus Adamchik escribió:
>> Oh, and actually I think we can fix it in the interim per https://issues.apache.org/jira/browse/CAY-1744 … The "hack" in the example makes me blush :)
>> 
>> Andrus
>> 
>> 
>> On Oct 6, 2012, at 12:04 AM, Andrus Adamchik <an...@objectstyle.org> wrote:
>> 
>>> Hi Ramiro,
>>> 
>>> Finally I have something specific for you: https://issues.apache.org/jira/browse/CAY-1743
>>> 
>>> In the source code attached to this Jira, I am simply blocking "readOnly" status of all model relationships. The example is a completely self-conatined project. It is built against 3.2M1-SNAPSHOT (SVN trunk), but it should work with 3.1B1 as well. And for 3.0.x, you can simply "inline" the fancy DI module code in "cayennehacks"…
>>> 
>>> Take a look at Main.java and cayennehacks package. The "hacks" is what it takes now to make vertical inheritance relationships work.
>>> 
>>>> If I try to creat a entity relationship on User I must set the target to Session entity and not WebSession, if I set it to WebSession tells me there is no mapping and if I choose the correct mapping to WebSession then as there is no entity linked to that table it complains about no target entity.
>>> This part worked for me on 3.1B1 Modeler.
>>> 
>>> Andrus
>>> 
>>> 
>>> 
>>> On Oct 5, 2012, at 5:28 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>> 
>>>> El 19/09/2012 22:12, Andrus Adamchik escribió:
>>>>> On Sep 19, 2012, at 11:24 AM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>>>> 
>>>>>> BTW I tried to do everything with 3.0.2 modeller and finally updated to 3.1.B1 modeller, Will the model created with 3.1.B1 modeller work with 3.0.2 runtime? (I want to update the runtime but just in case I can not do it).
>>>>> No, once you upgrade the Model to 3.1, there's no (automated) way to go back to 3.0. The project structure is different in 3.1. The biggest change is that the new projects have at most 1 domain per project. It is probably doable by manually editing XML, but there's little point in that. After all the only reason to use the new Modeler is if you are planning to use the new runtime.
>>>>> 
>>>>> I'll try to find time to get to the rest of your message. I rarely if ever use vertical inheritance, but I may try out your scenario.
>>>>> 
>>>>> Andrus
>>>>> 
>>>> Hi again,
>>>> Ok after the big refactoring I am now able to test this and I get this exception on commit:
>>>> "Cannot set the read-only flattened relationship 'toUser' in ObjEntity 'SessionLogWeb'."
>>>> or
>>>> "Cannot set the read-only flattened relationship 'runtimeRelationship1' in ObjEntity 'SessionLog'."
>>>> depending on which side I try to use when setting the relationship.
>>>> (SessionLogWeb is WebSession on my previous example and SessionLog is Session)
>>>> 
>>>> So even if only one side of the relationship is marked as read only it is not possible to set the relationship from either side, as this kind of mapping is a bit unexplored using cayenne I will happily try any different options but I would like to mantain the vertical inheritance as this is a logging table that will hold millions of records so using a shared table will waste too much space.
>>>> 
>>>> Thanks in advance.
>>>> 
>>>> Ramiro Aparicio
>>>> 
>>> 
> 
> 


Re: Vertical inheritance with relationships

Posted by Ramiro Aparicio <ra...@prot-on.com>.
Hi Andrus,

First of all thank you for all the effort and the fast reply time, I 
really appreciate your help with this issue.
Then the bad news after some decompiling to understand how to load 
modules on web containers I was able to configure everything but it 
seemed that still did not want to work, debugging the problem is that my 
relationships are marked as runtime even if they are defined in the 
model, so to avoid that I just removed that condition from your code 
(not sure if that can create some problems in the future) but now I am 
struggling against a commit exception because of the PK.
In our model the session table is a MYSQL autoincrement field so it is 
marked as database generated on Session table, but as sessionWeb and 
sessionClient rely on Session id they have PK strategy as default, but 
on commit I get an error creating the sessionWeb row as id is null.

Here is the sequence of inserts as logged:

[2012-10-08 13:38:05,376] [http-8443-2] INFO 
(CommonsJdbcEventLogger.java:logBeginTransaction:350)- --- transaction 
started.
[2012-10-08 13:38:05,392] [http-8443-2] INFO 
(CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO session_log 
(sessionStart, sessionType) VALUES (?, ?)
[2012-10-08 13:38:05,392] [http-8443-2] INFO 
(CommonsJdbcEventLogger.java:logQueryParameters:312)- [bind: 
1->sessionStart:'2012-10-08 13:38:05.314', 2->sessionType:2]
[2012-10-08 13:38:05,408] [http-8443-2] INFO 
(CommonsJdbcEventLogger.java:logGeneratedKey:218)- Generated PK: 
session_log.idSessionLog = 102839
[2012-10-08 13:38:05,408] [http-8443-2] INFO 
(CommonsJdbcEventLogger.java:logUpdateCount:344)- === updated 1 row.
[2012-10-08 13:38:05,408] [http-8443-2] INFO 
(CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO activity_log 
(Document_idDocument, SessionLog_idSessionLog, action, log_datetime, 
msg_params, successful) VALUES (?, ?, ?, ?, ?, ?)
[2012-10-08 13:38:05,408] [http-8443-2] INFO 
(CommonsJdbcEventLogger.java:logQueryParameters:312)- [bind: 
1->Document_idDocument:NULL, 2->SessionLog_idSessionLog:102839, 
3->action:04, 4->log_datetime:'2012-10-08 13:38:05.314', 
5->msg_params:NULL, 6->successful:NULL]
[2012-10-08 13:38:05,408] [http-8443-2] INFO 
(CommonsJdbcEventLogger.java:logGeneratedKey:218)- Generated PK: 
activity_log.idActivityLog = 124301
[2012-10-08 13:38:05,408] [http-8443-2] INFO 
(CommonsJdbcEventLogger.java:logUpdateCount:344)- === updated 1 row.
[2012-10-08 13:38:05,408] [http-8443-2] INFO 
(CommonsJdbcEventLogger.java:logQuery:299)- INSERT INTO session_log_web 
(User_idUser, id, ip, userAgent) VALUES (?, ?, ?, ?)
[2012-10-08 13:38:05,408] [http-8443-2] INFO 
(CommonsJdbcEventLogger.java:logQueryParameters:312)- [batch bind: 
1->User_idUser:NULL, 2->id:NULL, 3->ip:< 7F,00,00,01>, 
4->userAgent:'Computer/Windows 7/Firefox']

I need to check why the idUser is null but that maybe a controller error.
If you are ok with that I can send you the full model so you can check 
everything is configured as it should (I think I double checked 
everything but just in case).

I will try any workaround I am able to imagine and publish any new info.

Ramiro Aparicio

El 05/10/2012 23:12, Andrus Adamchik escribió:
> Oh, and actually I think we can fix it in the interim per https://issues.apache.org/jira/browse/CAY-1744 … The "hack" in the example makes me blush :)
>
> Andrus
>
>
> On Oct 6, 2012, at 12:04 AM, Andrus Adamchik <an...@objectstyle.org> wrote:
>
>> Hi Ramiro,
>>
>> Finally I have something specific for you: https://issues.apache.org/jira/browse/CAY-1743
>>
>> In the source code attached to this Jira, I am simply blocking "readOnly" status of all model relationships. The example is a completely self-conatined project. It is built against 3.2M1-SNAPSHOT (SVN trunk), but it should work with 3.1B1 as well. And for 3.0.x, you can simply "inline" the fancy DI module code in "cayennehacks"…
>>
>> Take a look at Main.java and cayennehacks package. The "hacks" is what it takes now to make vertical inheritance relationships work.
>>
>>> If I try to creat a entity relationship on User I must set the target to Session entity and not WebSession, if I set it to WebSession tells me there is no mapping and if I choose the correct mapping to WebSession then as there is no entity linked to that table it complains about no target entity.
>> This part worked for me on 3.1B1 Modeler.
>>
>> Andrus
>>
>>
>>
>> On Oct 5, 2012, at 5:28 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>
>>> El 19/09/2012 22:12, Andrus Adamchik escribió:
>>>> On Sep 19, 2012, at 11:24 AM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>>>
>>>>> BTW I tried to do everything with 3.0.2 modeller and finally updated to 3.1.B1 modeller, Will the model created with 3.1.B1 modeller work with 3.0.2 runtime? (I want to update the runtime but just in case I can not do it).
>>>> No, once you upgrade the Model to 3.1, there's no (automated) way to go back to 3.0. The project structure is different in 3.1. The biggest change is that the new projects have at most 1 domain per project. It is probably doable by manually editing XML, but there's little point in that. After all the only reason to use the new Modeler is if you are planning to use the new runtime.
>>>>
>>>> I'll try to find time to get to the rest of your message. I rarely if ever use vertical inheritance, but I may try out your scenario.
>>>>
>>>> Andrus
>>>>
>>> Hi again,
>>> Ok after the big refactoring I am now able to test this and I get this exception on commit:
>>> "Cannot set the read-only flattened relationship 'toUser' in ObjEntity 'SessionLogWeb'."
>>> or
>>> "Cannot set the read-only flattened relationship 'runtimeRelationship1' in ObjEntity 'SessionLog'."
>>> depending on which side I try to use when setting the relationship.
>>> (SessionLogWeb is WebSession on my previous example and SessionLog is Session)
>>>
>>> So even if only one side of the relationship is marked as read only it is not possible to set the relationship from either side, as this kind of mapping is a bit unexplored using cayenne I will happily try any different options but I would like to mantain the vertical inheritance as this is a logging table that will hold millions of records so using a shared table will waste too much space.
>>>
>>> Thanks in advance.
>>>
>>> Ramiro Aparicio
>>>
>>


Re: Vertical inheritance with relationships

Posted by Andrus Adamchik <an...@objectstyle.org>.
Oh, and actually I think we can fix it in the interim per https://issues.apache.org/jira/browse/CAY-1744 … The "hack" in the example makes me blush :)

Andrus


On Oct 6, 2012, at 12:04 AM, Andrus Adamchik <an...@objectstyle.org> wrote:

> Hi Ramiro,
> 
> Finally I have something specific for you: https://issues.apache.org/jira/browse/CAY-1743
> 
> In the source code attached to this Jira, I am simply blocking "readOnly" status of all model relationships. The example is a completely self-conatined project. It is built against 3.2M1-SNAPSHOT (SVN trunk), but it should work with 3.1B1 as well. And for 3.0.x, you can simply "inline" the fancy DI module code in "cayennehacks"… 
> 
> Take a look at Main.java and cayennehacks package. The "hacks" is what it takes now to make vertical inheritance relationships work.
> 
>> If I try to creat a entity relationship on User I must set the target to Session entity and not WebSession, if I set it to WebSession tells me there is no mapping and if I choose the correct mapping to WebSession then as there is no entity linked to that table it complains about no target entity.
> 
> This part worked for me on 3.1B1 Modeler. 
> 
> Andrus
> 
> 
> 
> On Oct 5, 2012, at 5:28 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:
> 
>> El 19/09/2012 22:12, Andrus Adamchik escribió:
>>> On Sep 19, 2012, at 11:24 AM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>>> 
>>>> BTW I tried to do everything with 3.0.2 modeller and finally updated to 3.1.B1 modeller, Will the model created with 3.1.B1 modeller work with 3.0.2 runtime? (I want to update the runtime but just in case I can not do it).
>>> No, once you upgrade the Model to 3.1, there's no (automated) way to go back to 3.0. The project structure is different in 3.1. The biggest change is that the new projects have at most 1 domain per project. It is probably doable by manually editing XML, but there's little point in that. After all the only reason to use the new Modeler is if you are planning to use the new runtime.
>>> 
>>> I'll try to find time to get to the rest of your message. I rarely if ever use vertical inheritance, but I may try out your scenario.
>>> 
>>> Andrus
>>> 
>> 
>> Hi again,
>> Ok after the big refactoring I am now able to test this and I get this exception on commit:
>> "Cannot set the read-only flattened relationship 'toUser' in ObjEntity 'SessionLogWeb'."
>> or
>> "Cannot set the read-only flattened relationship 'runtimeRelationship1' in ObjEntity 'SessionLog'."
>> depending on which side I try to use when setting the relationship.
>> (SessionLogWeb is WebSession on my previous example and SessionLog is Session)
>> 
>> So even if only one side of the relationship is marked as read only it is not possible to set the relationship from either side, as this kind of mapping is a bit unexplored using cayenne I will happily try any different options but I would like to mantain the vertical inheritance as this is a logging table that will hold millions of records so using a shared table will waste too much space.
>> 
>> Thanks in advance.
>> 
>> Ramiro Aparicio
>> 
> 
> 


Re: Vertical inheritance with relationships

Posted by Andrus Adamchik <an...@objectstyle.org>.
Hi Ramiro,

Finally I have something specific for you: https://issues.apache.org/jira/browse/CAY-1743

In the source code attached to this Jira, I am simply blocking "readOnly" status of all model relationships. The example is a completely self-conatined project. It is built against 3.2M1-SNAPSHOT (SVN trunk), but it should work with 3.1B1 as well. And for 3.0.x, you can simply "inline" the fancy DI module code in "cayennehacks"… 

Take a look at Main.java and cayennehacks package. The "hacks" is what it takes now to make vertical inheritance relationships work.

> If I try to creat a entity relationship on User I must set the target to Session entity and not WebSession, if I set it to WebSession tells me there is no mapping and if I choose the correct mapping to WebSession then as there is no entity linked to that table it complains about no target entity.

This part worked for me on 3.1B1 Modeler. 

Andrus



On Oct 5, 2012, at 5:28 PM, Ramiro Aparicio <ra...@prot-on.com> wrote:

> El 19/09/2012 22:12, Andrus Adamchik escribió:
>> On Sep 19, 2012, at 11:24 AM, Ramiro Aparicio <ra...@prot-on.com> wrote:
>> 
>>> BTW I tried to do everything with 3.0.2 modeller and finally updated to 3.1.B1 modeller, Will the model created with 3.1.B1 modeller work with 3.0.2 runtime? (I want to update the runtime but just in case I can not do it).
>> No, once you upgrade the Model to 3.1, there's no (automated) way to go back to 3.0. The project structure is different in 3.1. The biggest change is that the new projects have at most 1 domain per project. It is probably doable by manually editing XML, but there's little point in that. After all the only reason to use the new Modeler is if you are planning to use the new runtime.
>> 
>> I'll try to find time to get to the rest of your message. I rarely if ever use vertical inheritance, but I may try out your scenario.
>> 
>> Andrus
>> 
> 
> Hi again,
> Ok after the big refactoring I am now able to test this and I get this exception on commit:
> "Cannot set the read-only flattened relationship 'toUser' in ObjEntity 'SessionLogWeb'."
> or
> "Cannot set the read-only flattened relationship 'runtimeRelationship1' in ObjEntity 'SessionLog'."
> depending on which side I try to use when setting the relationship.
> (SessionLogWeb is WebSession on my previous example and SessionLog is Session)
> 
> So even if only one side of the relationship is marked as read only it is not possible to set the relationship from either side, as this kind of mapping is a bit unexplored using cayenne I will happily try any different options but I would like to mantain the vertical inheritance as this is a logging table that will hold millions of records so using a shared table will waste too much space.
> 
> Thanks in advance.
> 
> Ramiro Aparicio
>