1 2 Previous Next 27 Replies Latest reply on Dec 14, 2011 10:50 PM by Lewis Gass

    Groovy + Facelets (Gracelets)

    Lewis Gass Newbie

      I have built a groovy builder that can build part of the jsf component tree in a request and take advantage of existing components in facelets including user tag libraries. You could do something like this:


      
      u.component (rendered: "#{el}") {
      
        h.form {
      
          (0..10).each { idx ->
      
            h.inputText (value: "#{bean.map[idx]}")
      
          }
      
        }
      
      }
      
      



      It uses a servlet context based script engine pointing to a tmp dir in order to have a compile on change method for speed.


      I really think it would be a good addition to the seam framework and wanted to see if I could get any feed back.

        • 1. Re: Groovy + Facelets (Gracelets)
          Przemyslaw Jaskierski Newbie

          Looks very, very interesting... This could help in constructing some large and complex layouts, where Facelets are sometimes quite cumbersome... Conditional building of large components tree could be very efficient here. Mikchail Grushinskiy might be happy with this :).


          Is this only an experiment? I think if you could implement a non-toy example application (or better a real, working deployment) to proof stability, resource-wise processing and performance gains (if any) your idea would gain well-deserved attention.


          Good work! Keep informing us, please!

          • 2. Re: Groovy + Facelets (Gracelets)
            Lewis Gass Newbie

            I have a working deployable toy-like app that does nothing but show some possibilities. I am using this already to run a few pages on a professional site, I cannot mention its name here. Any ideas on a non-toy example application? I can make it, but ideas on what people would want to see escape me.

            • 3. Re: Groovy + Facelets (Gracelets)
              Gavin King Master

              Very nice, but what I would like to see done differently is Groovy closures instead of Unified EL expressions. This would require you to be able to transparently wrap up a closure as a unified EL MethodExpression or ValueExpression, but that should be totally doable, I suppose.

              • 4. Re: Groovy + Facelets (Gracelets)
                Lewis Gass Newbie

                Do you mean something like this:


                
                h.form {
                
                
                  h.commandButton("Click Here", action: { someMethod(); })
                
                
                  div {
                
                    b({ return "I want this printed"; })
                
                  }
                
                
                }
                
                
                def someMethod () {
                
                  // Code would go here for the action when invoked
                
                }
                
                



                That just might be plausible... not sure how transparent it would be, but I will look into. Maybe I could call it GEL.

                • 5. Re: Groovy + Facelets (Gracelets)
                  Lewis Gass Newbie

                  Not sure about it after initial prototyping and investigation, may need to get some help from someone that is more proficient with making ELResolvers and or coming up with some other solution.


                  The only thing plausible that I could come up with in a simple ELResolver is the following concept (say we are on a page called index.jsf):


                  
                  h.form {
                  
                    h.commandButton("Click Here", action: "#{index.someMethod}")
                  
                  }
                  
                  
                  def someMethod () {
                  
                    // action method code
                  
                  }
                  
                  

                  • 6. Re: Groovy + Facelets (Gracelets)
                    Lewis Gass Newbie

                    A couple of other things I have in this is 1) a seam map, and 2) an entity query language wrapper.


                    If you need a seam component you can do this:


                    
                      def mycomp = seam.mycomponentName
                    
                    



                    If you want to outject


                    
                      seam.mycomponentName = []
                    
                    



                    You can even outject a datamodel:


                    
                      def array = []
                    
                      (1..100).each { array.add("Item $it") }
                    
                      seam.setDataModel("myDataModel", array)
                    
                    



                    Now similiar to the Sql() for normal groovy, if you have your entity manager bound to jndi in the persistence.xml, you can reference it and do something like this:


                    
                      def q = new Eql("java:/EMBoundName")
                    
                      
                    
                      h.html {
                    
                        body {
                    
                          h.dataTable("#{myDataModel}", var: "row") {
                    
                            h.column("#{row}")
                    
                          }
                    
                    
                          table {
                    
                            caption("EQL Results")
                    
                            q.eachRow("SELECT e FROM Entity e") { entity ->
                    
                    
                              tr{
                    
                                td(entity.field1)
                    
                                td(entity.field2)
                    
                                td(entity.field3)
                    
                              }
                    
                    
                            }
                    
                          }
                    
                        }
                    
                      }
                    
                    

                    • 7. Re: Groovy + Facelets (Gracelets)
                      Lewis Gass Newbie

                      Just to make sure we are on the same note... the purpose of what I have made is to work ontop of facelets and really hide it, when you do want to see all that xml. Not to complement facelets directly.


                      In other words, what you mentioned about closures may have been more towards something like this:


                      
                      <html:commandButton action="{groovy expression}"/>
                      
                      



                      When in reality what I am proposing here is this:


                      
                      <gracelets:page viewOnly="false">
                      
                      ...groovy/gracelet code...
                      
                      </gracelets:page>
                      
                      



                      In other words, the whole page would be groovy building the entrie facelet handler tree and allowing arbitrary groovy code to execute along side it. Anyways, thought I should mention more clearly the purpose and objective of what I have created which may not be entirely clear from the original posts.


                      • 8. Re: Groovy + Facelets (Gracelets)
                        Gavin King Master

                        No, you won't be able to do it with an ELResolver, you'll need to actually create you own impl of MethodExpression that just calls the closure. Don't use EL at all.

                        • 9. Re: Groovy + Facelets (Gracelets)
                          Lewis Gass Newbie

                          I admit I am not an expert in how everything is linked together in JSF but my first attempts reveal that I have to make a decision. In order to have the benefit of using existing facelet libraries I have to do one of 2 things:


                          1. Work in conjunction with the DefaultFaceletFactory as
                              I am doing currently.


                          2. Re-write (basically cut and paste and modify) the
                              whole facelet factory code and compile my own facelets
                              jar (not very practical) but would allow me to truly
                              intercept things correctly.


                          The drawback to option 1 is that because of how things chain up even though I create my own MethodExpression via a custom wrapper ExpressionFactory the default facelet context gets in the way and does not propogate it down, and with old JSF 1.1 code(which still seems to be used in JSF 1.2) the action source does not seem to care what MethodExpression was used, it simply extracts the expression string and fails horribly. If someone more expirienced has a better idea on how to get the MethodExpression implementation to be used by all parts of JSF then I am open to suggestions.


                          In any case, I am at my wits end on how to get facelets and thus JSF to use the MethodExpression or ValueExpression implementations I have made. Maybe I am approaching it from the wrong angle, but I probably need to get with someone more familiar with the whole EL technology in order to have a chance at making this work.

                          • 10. Re: Groovy + Facelets (Gracelets)
                            Lewis Gass Newbie

                            Well, I think I have finally figured it out. I am now able to create groovy method and value expression implementations and have them propogated down so that the jsf components use it transparently.


                            I have also made some more advancements. Instead of using a temp directory I have writting a wrapper ViewHandler for the FaceletViewHandler implementation. It allows the view id's to be regular groovy files, and I have a GraceletCompiler that intercepts groovy view id's. This has the benefit of editing with normaly groovy editors and also being able to debug the gracelet page.


                            I think this is moving in a better direction than I had originally thought, of course it needs alot of testing for stability and efficiency purposes, but things look very hopeful.

                            • 11. Re: Groovy + Facelets (Gracelets)
                              Lewis Gass Newbie

                              In addition to what I have above in respone to Gavin, I have a new feature called a g component. What it allows you to do is provide a closure that gets ran at RENDER time instead of TREE creation time, and practically becomes a custom component. It comes with a MarkupBuilder wrapped around the ResponseWriter for the faces context. So you could do something like this (x is the automatically provided markup builder for the closure, and the call is passed the current faces context and the custom component, the closure for the tag builder will also add children to the custom component which can be rendered as a string with comp.renderChildren()):


                              
                                u.component {
                              
                              
                                  g({ ctx, comp ->
                              
                                    x.table {
                              
                                      (0..10).each { row ->
                              
                                      x.tr {
                              
                                        x.td("Column 1")
                              
                                        x.td(comp.renderChildren())
                              
                                      }
                              
                                      }
                              
                                    }
                              
                                  }) {
                              
                                    h.outputText("This will be rendered over and over at
                              
                                                  render time by the g component")
                              
                                  }
                              
                              
                                }
                              
                              

                              • 12. Re: Groovy + Facelets (Gracelets)
                                Kito Mann Newbie

                                Lewis,


                                I think you're definitely on to something here, and it's something that's useful for JSF as a whole. Is the code specifically tied to Seam in any way?


                                I'm doing a session at JSFDays in a couple of weeks about Scrpiting in JSF, and I'd love to see some of your work. Please drop me a line either here or personally when you get the chance.


                                ---

                                Kito D. Mann - JSF EG memeber, Author, JavaServer Faces in Action

                                http://www.virtua.com - JSF/Java EE consulting, training, and mentoring

                                http://www.JSFCentral.com - JavaServer Faces FAQ, news, and info




                                • 13. Re: Groovy + Facelets (Gracelets)
                                  Lewis Gass Newbie

                                  Kito Mann,


                                  In reality the stuff I am developing is not directly related to Seam, but we are heavy seam users and thought this was a great forum to bring the idea out on the table and get some feedback. We have had the experience that the seam forum is very responsive in comparison to other places that have not seemed to pay much attention to our posts.


                                  Also we would like to see it form part of the seam framework if it is deemed worthy and makes sense to the seam team.


                                  Lewis

                                  • 14. Re: Groovy + Facelets (Gracelets)
                                    Rogério Araújo Newbie

                                    Congratulations! Very good idea! I love it!

                                    1 2 Previous Next