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 <[email protected]> 
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 <[email protected]> 
>> 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 <[email protected]> 
>>>> 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 <[email protected]> 
>>>>>> 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 
>>>>>>> <[email protected]> wrote:
>>>>>>> 
>>>>>>>> El 19/09/2012 22:12, Andrus Adamchik escribió:
>>>>>>>>> On Sep 19, 2012, at 11:24 AM, Ramiro Aparicio 
>>>>>>>>> <[email protected]> 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
>>>>>>>> 
>>> 
> 
> 

Reply via email to