3 Replies Latest reply on Feb 25, 2008 5:22 PM by Francisco Peredo

    CRUD relationships for new objects, single save: temporary PK?

    Francisco Jose Peredo Noguez Master

      Hi!
      First let me say I love seam-gen, specially when run from eclipse using jboss-tools, i am starting a new project, and seam-gen has helped me impress my coworkers... I also love the architecture, I think that seam is the first web framework that makes me feel like I am using a modern version of WebObjects (I have been looking for a replacement of WebObjects everywhere, first with WebWork, then with Spring, then in ASP.NET, but now, with seam I think I have finally found it)
      Well, lets start with my question:
      One of the things I still miss from the equivalent of seam-gen in WebObjects, was the single save button, what do I mean by that? well, in seam-gen if you generate the CRUD pages for 2 entites connected by a one-to-many relationship (one P to many Q), you will have to save the P first and then you can connect it with the Q, that means you can not save both of in the same  user transaction (the user has to hit the save button 2 times). I believe that applications generated by seam-gen shouldn't have this limitation... since seam has conversations support (A thing AFAIK Webobjects didn't have) it should be possible to avoid this problem...IMHO the problem is that the Add Q buttons in the P editor shouldn't have to add the primary key to the url, it should:
      1) Store the current master object in the conversation scope, and use that to link the Q to P
      2) Add to seam (or hibernate?) the ability to automatically add a kind of temporal primary key that would allow to select a particular unmanaged pojo


      I think that the first solution should be pretty easy to implement.. I am planning on implementing it by altering the freemarker templates of seam-gen... but I am worried because I don't get why it wasn't built like this the first time, IMHO it would have been an excelent way to show off the great conversational and transactional features of seam... is there a caveat I am not seeing?


      I think the second solution might also need to be implemented... why? well, after adding several Q to P, those Q shouldn't have a primary key (after all, nothing should be saved until the save button in P is clicked) but what if I want to go back to a particular Q and modify it? how do I identify it on a grid?


      I am right to think that this single save approach should be somewhat easier to build with seam that with the other, stateless (conversationless) frameworks? how do you tipically solve the problem of the lack of primary key for an unsaved pojo that needs to be referenced from a JSF control? should I perhaps initialize the pk with a fake perhaps negative value (-1, -2, -3)? since hibernate can use the @version property to determine if a pojo was saved, then there should be no problem? could it happen that my pojo ended up being persisted with the temporary primary key? what do you recommend for this problem?


      Thanks a lot, and congratulations on this new great framework site.


      bye


      LuxSpes



        • 1. Re: CRUD relationships for new objects, single save: temporary PK?
          Nicklas Karlsson Master

          If you have a long-running conversation and manual flushmode, you can generate the object graph as you please and with correct cascade mode the whole graph is written on the entitymanager flush (several pages and operations later)


          Do you really need to reference the primary key? Is it a non-automatic key with some business meaning?

          • 2. Re: CRUD relationships for new objects, single save: temporary PK?
            Nicklas Karlsson Master

            If the entities are in a list, you can probably identity it by the row number in the list, otherwise you could wrap it in something with an id.

            • 3. Re: CRUD relationships for new objects, single save: temporary PK?
              Francisco Peredo Newbie

              Hi!
              I think that the row number is not really convenient, because the list might change between clicks (changes made by another user perhaps) and therefore  you might end up selecting the wrong row.
              Wrapping it in something with an id sounds like a better idea... but if that is what it takes, why not have the entity generate its own unique negative id (perhaps by creating a new component with ScopeType.APPLICATION that generates conscutive negative numbers, and calling it just after the new objects are created)


              But what really surprises me is that there isn't an official way to deal with this, IMO very common problem... and what surprises me even more is that the seam-gen generated crud screens do not use by default the manual flushmode... I tried adding the begin annotation with manual flush mode to the createInstance method in the entityHome, but it didn't seam to work.


              Another problem is that in my experience with older versions of Hibernate (2.x) the manual flushmode didn't work for new objects (it was great for updates an deletes, but it was unable to delay the inserts).
              Do anyone here knows if thats is still an issue? (could that be the reason that this didn't do the trick):


              @Begin(flushMode=MANUAL)
              protected SomeEntity createInstance() {
                  SomeEntity se= new SomeEntity ();
                  this.getEntityManager().persist(se)
                  return se;
              }
              
              



              This apparently should work, because it adds an id to the new pojo, it adds it to the entityManager so now it is managed... and the CRUD pages generated by seam-gen now allow you to add items as childs to the new uncommited pojo, but sadly the INSERT generated by the persist doesn't seem to be delayed at all... maybe that is fine... as long as it doesn't commit the transaction... but... how do I tell seam that unless to rollback it? and... why seam doesn't generate this in the first place?