9 Replies Latest reply on Jan 29, 2009 10:06 PM by Francisco Jose Peredo Noguez

    CRUD is conversational, but seam-gen is not

    Francisco Jose Peredo Noguez Master

      Hi!


      Lets say you have 2 classes:


      class Parent{
          private Long id; private Integer version; private String name;
          private Set <Child> children;
      }
      
      



      and


      class Child{
          private Long id;private Integer version; private String name;    
          private Parent parent;
      }
      



      with a typical one to many / many to one relationship (Parent.children.Child/Child.parent.Parent)


      So you want them to become @Entities and add the required @Annotations. Then you run seam-gen on them, and run you generated application:



      1. You click the Parent List menu option.

      2. You are presented with the page ParentList.seam that allows you search parents, or to create a new one.

      3. You click the Create parent button.

      4. You write a name for the parent: Peter.

      5. You click Save.

      6. You are presented with the page Parent.seam, that displays you newly persisted entity in a read-only way

      7. You click Done



      so far so good... but then



      1. You click the Child List menu option.

      2. You are presented with the page ChildList.seam that allows you search children, or to create a new one

      3. You click the Create child button.

      4. You are presented with the page ChildEdit.seam.

      5. You write a name for your new Child entity: John

      6. You decide that you want connect this new Child entity with a parent entity, and then you click Select parent.

      7. You are presented again with ParentList.seam that allows you to select a parent.

      8. So, you select Peter by clicking in the Select link

      9. And you return to ChildEdit.seam, but the value for the name property of the Child is now lost.



      I think seam-gen should be able to do this correctly, it may not seem like such a big deal in this simple example, but imagine if Child had 15 or 25 fields! Why should I need to re-write their values?


      This is the kind of behaviour that should just work, by default, since seam-gen generates an application that is built on top of a conversational framework (Seam), but it does not... I seems to me that seam-gen was build based on the mistaken assumption that a CRUD application does not need conversations, but, it in fact does...


      What do you think about this omission? Do you build a lot of applications to do CRUD with seam? how do you deal with this problem? Would you vote for a JIRA requesting a conversational seam-gen?


        • 1. Re: CRUD is conversational, but seam-gen is not
          Francisco Jose Peredo Noguez Master

          The first problem with all this seems to be, the fact that the Select parent button in ChildEdit.seam is an s:button and it does not submit the form, therefore all the values in the from are lost.


          So I guess that s:button and master-detail CRUD pages do not play good together... this would not be a big problem if it not were because h:commandButton and seam navigation do not easily play very good together h:commandButton does not work as a drop-in replacement for s:button because it does not support the view attribute...



          What changes to I have to make to this to make CRUD work properly?:


          <s:button value="#{childHome.instance.parent != null ? 'Change' : 'Select'} parent"
                                 view="/ParentList.xhtml">
                          <f:param name="from" value="ChildEdit"/>
          </s:button>
          

          • 2. Re: CRUD is conversational, but seam-gen is not
            Francisco Jose Peredo Noguez Master

            I is too hard... when I changed s:button to a:commandButton, I starting having too many problems:



            1. The from parameter gets lost (it is no longer a GET request, it is a POST )

            2. My seam-gen has heavy modifications (I Ajaxified it a lot)... the thing is I have 2 regions, (one for the form with the data) and another with the tabs that link to other entities... and it seems that a button inside one ajax region will not submit the values of a form in another region...



            Any hints on how to solve this? Is it impossible?

            • 3. Re: CRUD is conversational, but seam-gen is not
              Binesh Gummadi Novice

              Ok let me try to answer this.


              Solution 1:
              If your parents list is not huge, say 20-30, you don't really need a search feature and you can have a dropdown list of parents and map the property to the parent object in your child object.


              Solution 2:
              If the list is huge say greater than 30 then you can have a select parent icon or link in your childEdit.xhtml and when clicked, show a modal panel with the list of parents. Have a select link at the end of each row and populate your parent object when selected. Since the selection happens in the same conversation parent reference is not lost when you save the child.


              Both these solutions are not part of seam-gen. Try to see if you can reuse the parentList in the modal panel.


              You think this might work?

              • 4. Re: CRUD is conversational, but seam-gen is not
                Francisco Jose Peredo Noguez Master

                Hi! Thanks for answering



                Binny G wrote on Jan 09, 2009 22:52:


                Ok let me try to answer this.

                Solution 1:
                If your parents list is not huge, say 20-30, you don't really need a search feature and you can have a dropdown list of parents and map the property to the parent object in your child object.



                Yes, I already did this for other cases (I even created an annotation that changes what seam-gen does and makes it generate a dropdown list of parents and map the property to the parent object in your child object, the problem is when the list is huge.



                Solution 2:
                If the list is huge say greater than 30 then you can have a select parent icon or link in your childEdit.xhtml and when clicked, show a modal panel with the list of parents. Have a select link at the end of each row and populate your parent object when selected. Since the selection happens in the same conversation parent reference is not lost when you save the child.



                Yes, I guess using a modal panel is the answer... but.. isn't it a little sad that I have to resort to that? I mean, Seam main strength should be this kind of cases... but if this is really the best way to solve this problem... then that means that the right way to deal with conversational stuff is plain: do it client-side using a modal panel.




                Both these solutions are not part of seam-gen. Try to see if you can reuse the parentList in the modal panel.


                I think it could work, but I do not think it is the right way to solve it... not with a conversational framework like seam...


                You think this might work?



                There is only one way to find out ;-)


                Thanks again



                • 5. Re: CRUD is conversational, but seam-gen is not
                  Francisco Jose Peredo Noguez Master

                  Tried showing a rich:modalPanel panel with the list of parents... first I tried with ui:include but it does not work (it says that the <h:messages> in the included ParentList.xhtml and the one in the current ChildEdit.xhtml have the same id globalMessages. One would expect that there would be a way to prefix the id of the stuff included by ui:include (similar to the way h:form prefixes the tags inside it) but I couldn't find a way to do it.


                  So I tried putting an iframe inside the rich:modalPanel, and it works, but now I have the problem of using a different ui:composition template when the pages are called inside the iframe (and also the problem of changing the behavior of the links so that they close rich:modalPanel when the nested client side conversation simulated with modal panels ends.

                  • 6. Re: CRUD is conversational, but seam-gen is not
                    Binesh Gummadi Novice

                    Is this how you have it?


                    ChildEdit.xhtml


                    <h:form id="childForm">
                      <!-- your child component code -->
                    </h:form>
                    
                    <rich:modalPanel id="ModalPanel" width="600" height="300">
                      <ui:include src="ParentList.xhtml" />
                    </rich:modalPanel>



                    ParentList.xhtml


                    <h:form>
                      <!-- Your parent list -->
                    </h:form>



                    This is working for me. But remember modal panels are such a pain if you want to do validations.

                    • 7. Re: CRUD is conversational, but seam-gen is not
                      Francisco Jose Peredo Noguez Master

                      Yes, that is how I have it, but I since my seam-gen has been heavily modified to make more use of ajax, I guess my pages are very different from yours.


                      To make a long story short, there is a way to prefix the id of the stuff included by ui:include (similar to the way h:form prefixes the tags inside it), I had to use the f:subview tag:


                      <rich:modalPanel id="ModalPanel" width="600" height="300">
                      <f:subview id="relationshipToParentSubView">
                        <ui:include src="ParentList.xhtml"/>
                      </f:subview>
                      </rich:modalPanel>
                      



                      I also turned out that the easiest way to change the behavior of ParentList.xhtml when called from the modalPanel was to use ui:param:


                        <ui:include src="ParentList.xhtml">
                           <ui:param name="isModalPanel" value="#{true}"/> 
                        </ui:include> 
                      



                      So I decided to continue with the ui:include approach instead of using iframes, and it is working very well, except for one little problem.


                      Regards,

                      • 8. Re: CRUD is conversational, but seam-gen is not
                        Francisco Jose Peredo Noguez Master

                        Created JBSEAM-3903 to ask for a seam-gen that takes better advantage of the conversational capabilities of Seam (or of the RichFaces controls available to offer a bug-free CRUD experience)

                        • 9. Re: CRUD is conversational, but seam-gen is not
                          Francisco Jose Peredo Noguez Master

                          Solved it using rich:modalPanel and heavy modifying seam-gen templates. But I still think it should be possible to solve this using conversations.