Skip to main content

What JSF should become?

Posted by lamine_ba on November 27, 2011 at 6:03 AM PST

Perfection is achieved through times.
Anonymous

Introduction

How someone can improve if he has no clear vision of what he could become? I'm asking this tough question to myself while reading to the definition of JSF. As it is written in its specification, JavaServer Faces is a user interface framework designed to significantly ease the burden of writing and maintaining applications that run on a java application server and render their UIs back to a target client. Woow! That is really a lovely definition but is it still relevant in 2011 and beyond? Ladies and Gentlemen, are you sure that we don't need more? 

Our standard web framework is built around the greatest design patterns but it definitely lacks the fundamentals. I have read nowhere that JSF has provided any guidance to developers through the form of "development patterns". And we still have the huge pretension to ask you to use a web framework which has no standard development models coming through the form of conventions. Let me now adopt a more professional attitude in order to clarify my position with some concrete examples thus you will better understand what I'm talking about.

Views

Let's begin with this simple question. Where one must store his views? Inside a folder put in the WEB-INF or in the root directory? Shall we name this folder "pages" like Steve or "views" like Mike? No, let's name it "bobmarley" like Crazy Joe. And with this lack of convention, we have lost one possibility to have some nice automation to ease the development and to make our JSF applications homogeneous. And when someone has the requirement to move to another project to work with another team, he must always take the time to learn first their own conventions. Isn't it a waste of time and frankly does one understand the meaning of a knowledge if it cannot be shared? 

Client Side Request Forgery Protection (CSRF)

This feature is mostly specified and it will come with JSF 2.2. That is an standardization of how JSF provides CSRF protections. If you haven't read the proposal yet, here is how it will be implemented. Within the <faces-config-extension> element, a new <protected-views> element will be introduced. This element contains zero or more <url-pattern> elements

  1. <faces-config-extension>
  2.  
  3.         <protected-views>
  4.                 <url-pattern>/views/deleteBlogEntry.xhtml</url-pattern>
  5.                 <url-pattern>/views/deleteComment.xhtml</url-pattern>
  6.         </protected-views>
  7.  
  8. </faces-config-extension>

Any view that matches any of the url-patterns may only be reached from another JSF view in the same web application. And because the runtime is aware of which views are protected, any navigation from an unprotected view to a protected view is automatically subject to protection. That is really a lovely theory but in practice, it hardly means this : If you have 100 views to protect, you have 100 xml lines to write and that is really a lovely annoying stuff made for bureaucrats. I would rather have this convention combined with an url rewriting in order to have this simple automation : Any view stored in the views/protected directory is automatically protected.

And doing so, the API which has been added to the ViewHandler for a support of this feature at runtime will be now full of sense.

  1. public List<String> getProtectedViewsUnmodifiable();
  2.  
  3. public void addProtectedView(String urlPattern);
  4.  
  5. public void removeProtectedView(String urlPattern);
  6.  

Facelets Templating

Ladies and Gentlemen, have you watched "Saving Private Ryan" from Steven Spielberg. I'm using this analogy as a way to undoubtedly say that Facelets has saved the life of JSF. And I'm truly in love with its templating approach but what I hate the most is :

  1. There is no convention about where to store the template. A view can only use one template and it has a huge dependency with it. And if you are so crazy to change its location, prepare yourself for a cascading views update.
      <html xmlns="http://www.w3.org/1999/xhtml"  
         xmlns:h="http://java.sun.com/jsf/html"  
         xmlns:ui="http://java.sun.com/jsf/facelets">  
     
        <body>  
         
        <ui:composition template="/template.xhtml">
         
         </ui:composition>        
                 
        </body>  
     
    </html>
  2. There is no clear separation between the web designer and the developers. They are dependent to each other. Who is waiting for who? Such is the question.
  3. The template and its resources (css, js, images) cannot be externalized, packaged and shared.

Multi-Templating

But these complaints are no longer true with JSF 2.2 and its Multi-Templating system. But don't be too much confused with this feature. It is only an extension of the Facelets templating system for a better modeling of the concept so that :

  1. A view can use more than one template. And with this new abstraction, it cannot even guess the location of the templates. Who knows, maybe they are stored somewhere in the Cloud.
      <html xmlns="http://www.w3.org/1999/xhtml"  
         xmlns:h="http://java.sun.com/jsf/html"  
         xmlns:ui="http://java.sun.com/jsf/facelets">  
     
        <body>  
         
        <ui:composition template="#{template}">
         
         </ui:composition>        
                 
        </body>  
     
    </html>
  2.  The web designer and the developers have no dependency. No one is waiting for no one. 
  3. A template and its resources (css, js, images) can now be externalized, packaged and shared.

To finish, I think it is a well-established knowledge that in a JSF application, a view will always use a template. So I don't see any valuable reason to waste our time by writing this "<ui:composition template="#{template}"> in our views. Don't you agree that once a knowledge is set, things should be automatic? But fortunately, such will be the case for JSF 2.2.

Security Model

I will end up by a feature I'm hardly battling to have. So if you see any value in it, please leave a comment for our spec lead. But take the time to read first the conversation below :

  • Hey template authors, that is very nice to see you designing templates for us but can we delegate more work to you? Can you design the login form for us?
  • Of course, we can design it in the template or in a separate page. And we don't care about if you will use JAAS, Spring Acegi or such. The only thing we need is an authentication model coming through the form of a standard managed bean for the connection with your security logic.
  • Ahh! I understand. You want to have an abstraction like SeamLoginModule....
  1. <h:form id="login">
  2.  
  3.         <h:panelGrid columns="2">
  4.                 <h:outputLabel for="username">Username</h:outputLabel>
  5.                 <h:inputText id="username" value="#{identity.username}"/>
  6.                 <h:outputLabel for="password">Password</h:outputLabel>
  7.                 <h:inputSecret id="password" value="#{identity.password}"/>
  8.         </h:panelGrid>
  9.  
  10. <h:commandButton value="Login" action="#{identity.login}"/>
  11.  
  12. </h:form>
  13.  

And to complete the whole thing, maybe we can add to this, a view-level security in order to prevent non-authenticated users from accessing restricted views. Nonetheless, the decision does not belong to me, but undoubtedly the JSF community has a louder voice. So Ladies and Gentlemen, feel free to contribute and be hard on yourself if you want to improve. Yes, truly I love JSF but today I'm not tender with it...

 

AttachmentSize
views-folder.PNG684 bytes
views-protected-folder.PNG1.14 KB
Related Topics >>

Comments

Hello Lamine, Reading your 20120410 post, I had cause ...

Hello Lamine,

Reading your 20120410 post, I had cause to re-read your 20111127 post
and I think it's appropriate to reply first to 20111127 and then to
20120410.

First, let's look at the convention for where to put your Facelet pages.
Aside from establishing a project format convention, which is arguably
the most valuable thing maven has brought to the world, what value would
it add?  In order to make it worth doing this, there would have to be
some value over and above just establishing a convention.  For example,
let's say that we add an item to the list of conditions that cause the
FacesServlet to be automatically mapped, as shown in JSF 2.1 [1].  The
existing list is this:

    A faces-config.xml file is found in WEB-INF

    A faces-config.xml file is found in the META-INF directory of a jar
    in the application's classpath.

    A filename ending in .faces-config.xml is found in the META-INF
    directory of a jar in the application's classpath.

    The javax.faces.CONFIG_FILES context param is declared in web.xml or
    web-fragment.xml.

    The Set of classes passed to the onStartup() method of the
    ServletContainerInitializer implementation is not empty.

We can add this one

    There exists a non-empty "views" subdirectory of the web app root.

In this case, we have both created a convention and introduced a feature
that leverages that convention.  Is that sufficient value?  I'm not
sure.

Now let's look at your CSRF proposal.

This one is clearly valuable.  And, in your proposal, it depends on the
creation of a "views" concept.

On to Multi-templating.

I think the naming convention I started out my response with falls
neatly under this feature.

As far as login, yes, we certainly need to do this.

Thanks,

Ed

[1] https://maven.java.net/service/local/repositories/releases/archive/javax/faces/javax.faces-api/2.1/javax.faces-api-2.1-javadoc.jar/!/javax/faces/webapp/FacesServlet.html

Hello Ed First of all, you have to forget most of the ideas ...

Hello Ed

First of all, you have to forget most of the ideas I have shared here and you have to keep only this one : Storing the views in a "views" directory. Now the problem is how to add this feature in JSF 2.2 without breaking the backward compatibility stuff. Here is the solution, give only the behavior below to the default Facelets Resolver :

public class ViewResolver extends DefaultResourceResolver{
public URL resolveUrl(String path){
          URL url=super.resolveUrl("/views"+path);
  return url!=null?url:super.resolveUrl(path);
        }

If the user send this request : http://localhost:8080/faces/index.html. The view resolver will first try to resolve index.html in the views directory by appending "/views to the path (/index.xhtml). And if we have nothing, we come back to the original behavior with the original path....

Hi Ba, it would be great for sure!&nbsp;What about new ...

Hi Ba,

it would be great for sure! What about new versions for Spring Roo, soon supporting JSF 2.0 and Primefaces? I think it will fill some of this needs.

Check this out java.dzone.com/articles/jsf-20-spring-roo

Thanks for this great post!

Hi axcdnt, Thank you very much for this nice and clever ...

Hi axcdnt,

Thank you very much for this nice and clever comment. In this blog post, I did not write this time a conclusion because my goal was to let you discover by yourselves what JSF could be. The next step for a web user interface framework is to become a tiny web application framework that one can extend. And no framework can reach this level without having conventions. And once those standard development patterns are established, its community will better see the value and the power of app generators like Spring Roo. Yes its next versions will rock and I can't wait the one which will come with this right combination:

JSF 2.2 + Primefaces (views) + Multi-Templating (templates) + Tasks Flows (modules) + Security Model

A Tasks Flow is a module written by a web developer and like for a template, it is shareable but it would be nice if we can write its business logic with scripting languages so that we can customize it.

We are also coming soon with an integration model with JAX-RS 2.0, so be ready to add it to the stack.
 

Regards,
Lamine

 

Hi Ba! nice blog again! The concept &quot;Convention over ...

Hi Ba! nice blog again!
The concept "Convention over Configuration" than you want to adopt with JSF, will ease the web development and improve the maintainability in Java EE. I don't see any constraints to block the community in adopting these conventions quickly. The goal is to facilitate and improve the development (The Time-to-market).
Continue at this way, with some guys like you, JSF will become a great web framework.

Regards

Pape S. Diop

Hi Diop! Thanks for the nice comment. I really appreciate ...

Hi Diop!

Thanks for the nice comment. I really appreciate it. Yes with conventions, things will become more easy. JSF is already a great web framework but it could be more..

Regards

Lamine