Hobione's Weblog

Living & Breathing in Web 2.0 Era

JSF @ UCO

I was honored to give a presentation at the University of Central Oklahoma Computer Science department on Java Server Faces. I was invited by Dr. Sung who teaches Java Server Programming and also he is my java guru.  I took my first java class with him 10 years ago (man I am getting old …) while I was finishing up my degree.   Anyway, it was a great experience.  I was little nervous standing front of a class specially front of Dr. Sung and preach about a java framework.  It went really well, I believe.  Dr. Sung and along with students seemed to enjoy the presentations and I was happy to deliver my materials as well.

April 16, 2010 Posted by | Java Server Faces | 1 Comment

dataTable and radio button in JSF

Scenerio: Wanted to render the same radio button group for all rows in the table so that only one button can be selected at a time.  There seem to be no easy solution to that simple problem!

DataTable and RadioButton

Reason: The above plan apparently doesn’t work, because <h:selectOneRadio> renders an HTML “table” by itself, and that “messes up” the other “table” that the <h:dataTable> tag renders.

Solution:  One work around would be to use TomaHawk but instead of mixing two JSF implementations I went ahead to use command link.

Commnad Link2nd SoulutionThe key to getting this to work is to define the selectOneRadio component outside of the table. Then by setting the layout attribute to spread and using the ice:radio components inside the dataTable it gives you the rough layout/functionality.


<h2>Main Page</h2>
<ice:form>
 <ice:panelGroup id="tablePanel">

 <ice:selectOneRadio id="trainingClassRadio"
 value="#{testBean.selectedClass}"
 partialSubmit="true"
 valueChangeListener="#{testBean.radioChanged}"
 layout="spread">
 <f:selectItems value="#{testBean.radioItems}"/>
 </ice:selectOneRadio>

 <ice:dataTable var="class" value="#{testBean.trainingClassList}"
 varStatus="classStatus">
 <ice:column>
 <f:facet name="header">
 <ice:outputText value=""/>
 </f:facet>
 <ice:radio for="trainingClassRadio"
 index="#{classStatus.index}"/>
 </ice:column>

 <ice:column>
 <f:facet name="header">
 <ice:outputText value="Class Name"/>
 </f:facet>
 <ice:outputText value="#{class.className}"/>
 </ice:column>
 <ice:column>
 <f:facet name="header">
 <ice:outputText value="Class Number"/>
 </f:facet>
 <ice:outputText value="#{class.classNum}"/>
 </ice:column>
 <ice:column>
 <f:facet name="header">
 <ice:outputText value="Class Description"/>
 </f:facet>
 <ice:outputText value="#{class.classDesc}"/>
 </ice:column>
 </ice:dataTable>
 </ice:panelGroup>

 <ice:panelGrid columns="2">
 <ice:outputText value="Selected Row - Class Name:"/>
 <ice:outputText value="#{testBean.selectedTraining.className}"/>
 <ice:outputText value="Selected Row - Class Number:"/>
 <ice:outputText value="#{testBean.selectedTraining.classNum}"/>
 <ice:outputText value="Selected Row - Class Description"/>
 <ice:outputText value="#{testBean.selectedTraining.classDesc}"/>
 </ice:panelGrid>

 </ice:form>

May 29, 2009 Posted by | Java Server Faces | 13 Comments

JSF: f:selectItem vs. javax.faces.model.SelectItem

Let me explain what works and then I will tell you what not works. ListModel has a list type of javax.faces.model.SelectItem:


public class TrainingSessionsListModel extends ListModel{

 private List<SelectItem> availableSlotSelectItems;

 public List<SelectItem> getSessionNumberSelectItems() {

 if (this.sessionNumberSelectItems == null){
    sessionNumberSelectItems = new ArrayList();
    for(int i = 100; i < 1000; i++){
       SelectItem selectItem = new SelectItem(i,Integer.toString(i));
       sessionNumberSelectItems.add(selectItem);
    }
 }
 return sessionNumberSelectItems;
 }
 }

&#91;/sourcecode&#93;
<p style="margin-bottom:12pt;">xhtml now referring to the above list model class to get the list and set the value to TrainingSessionsDTO.sessionNumber property:</p>


<td>
 <ice:selectOneMenu id="sessionNumber" partialSubmit="true" value="#{
trainingSessionsListModel.TrainingSessionsDTO.sessionNumber}" required="true">

<f:selectItem itemLabel="#{msgs.select}" itemValue="" />
 <f:selectItems value="#{trainingSessionsListModel.sessionNumberSelectItems}"/>

 </ice:selectOneMenu></td>

Here is the transfer object with getter and setter.

 public class TrainingSessionsDTO extends TransferSupport implements Transfer,
 Serializable {

 String sessionNumber;

 //getter and setter .......

 }

sessionNumber

The above works fine, no problem but if I change the xhtml to these it wont work.

<ice:selectOneMenu id="sessionNumber" partialSubmit="true" value="#{
trainingSessionsListModel.TrainingSessionsDTO.sessionNumber}" required="true">
 <f:selectItem itemLabel="#{msgs.select}" itemValue="" />

 <f:selectItem itemLabel="100" value="100" />
 <f:selectItem itemLabel="200" value="200" />
 <f:selectItem itemLabel="300" value="300" />
 </ice:selectOneMenu></td>

Exception:
java.lang.String cannot be cast to javax.faces.model.SelectItem

Solution:

<f:selectItem itemLabel="100" itemValue="100" />
<f:selectItem itemLabel="200" itemValue="200" />
<f:selectItem itemLabel="300" itemValue="300" />

The value is meant to send in a SelectItem object and not a String. This should eliminate the exception you are seeing. Here is my beautiful finished work (form and datatable):
trainingsessionform

May 1, 2009 Posted by | Java Server Faces | 4 Comments

JSF @PostConstruct

Scenario:  I needed to get some data for datatable when the bean get initiated.
So, I have tried these following code.

public TrainingClassForm() {  //constructor
        this.trainingListModel.getAllTrainingClasses();
    }

Error:

me:  javax.faces.FacesException: Problem in renderResponse: javax.faces.FacesException: Cant instantiate class: gov.faa.amc.nas.hrtrainingview.bean.backing.TrainingClassForm.. null

Issue: Banging my head after few hours, then I have discussed with JSF Expert, Jason Lee who helped me to sort this out.   I was calling trainingListModel before it get initiated/born.  So I was getting a null pointer in TrainingListModel class.

Lesson to learn:  Use @PostConstruct instead.

1. If the bean has request scope, @PostConstruct will get executed every time.  It will be called after the managed bean is instantiated, but before the bean is placed in scope.   Such a method take no arguments, return void, and may not declare a checked exception to be thrown.  Method may be public, protected, private, or package private.  If the method throws an unchecked exception, the JSF implementation must not put the managed bean into service and no further menthods on that managed bean instance will be called.

// Constructor
    public TrainingClassForm() {

    }
  @PostConstruct
   public void init() {
       if (this.trainingListModel.getListDataModel() != null) {
          this.trainingListModel.getAllTrainingClasses();
       } 

    }

2. @PreDestroy:Any scoped managed bean menthod annotated with @PreDestroy will be called before the bean is removed from the scope or before the scope in which the bean resides is destroyed, whichever comes first.  The constraints placed on the method are the same as with @PostConstruct.

Ref Book: The Complete Reference – JavaServerFaces  by Chris Schalk & Ed Burns

April 22, 2009 Posted by | Java Server Faces | 3 Comments

Dependency Injection in JSF and ‘new’ is a dirty word

I am going to write some explanation that I have learned from training and discussed with my cohort. Please go get a cup of coffee before you start this journey. Yes, using ‘new’ is a dirty word in a sense that in this example, you wont see using ‘new’ to instantiate an object instead use the injection capability in the faces-config.xml file.  Please read these articles before proceed.  Spring into JavaServer Faces and JSF-Spring


1. What does this following code mean?

<managed-bean>
        <managed-bean-name>applicantEditor</managed-bean-name>
        <managed-bean-class>training.jobapplication.bean.backing.ApplicantEditor</managed-bean-class>
        <managed-bean-scope>request</managed-bean-scope>

    </managed-bean>

It means to create an instance of ApplicantEditor.java and make it available in request scope.

ApplicantEditor applicantEditor = new ApplicantEditor();

Here the ApplicantEditor.java looks like.

public class ApplicantEditor {

	private boolean formRendered = false;

	public boolean isFormRendered() {
		return formRendered;
	}

	public void setFormRendered(boolean formRendered) {
		this.formRendered = formRendered;
	}
}

2. Let me explain these following code snippets

<managed-bean>
		<managed-bean-name>applicantList</managed-bean-name>
		<managed-bean-class>training.jobapplication.bean.backing.ApplicantList</managed-bean-class>
		<managed-bean-scope>request</managed-bean-scope>
		<managed-property>
<property-name>applicantEditor</property-name>
			<value>#{applicantEditor}</value>
		</managed-property>
		<managed-property>
<property-name>applicantListModel</property-name>
			<value>#{applicantListModel}</value>
		</managed-property>
	</managed-bean>

First of all, an instance has been created for ApplicantList in a request scope. Now, by looking at the line 6, I can tell that ApplicantList.java has a property/instance variable name applicantEditor <property-name> (it is a type of ApplicantEditor.java). Line 7, it’s calling setApplicantEditor() to set the value <#value>. Also same things are happening in line 10 and 11 for applicantListModel.  Declare the property name using this tag <property-name>, and set the value by using this value tag <value> .  ApplicantList contains a ‘has-a’ relationship of ApplicantEditor type.  Easy, piece of cake and here is the proof:

package training.jobapplication.bean.backing;

import training.jobapplication.bean.model.ApplicantListModel;

import training.jobapplication.transfer.Applicant;

import javax.faces.component.UICommand;
import javax.faces.event.ActionEvent;

public class ApplicantList {

	private ApplicantForm applicantForm;
	private ApplicantEditor applicantEditor;
	private ApplicantListModel applicantListModel;

	public ApplicantForm getApplicantForm() {
		return applicantForm;
	}

	public void setApplicantForm(ApplicantForm applicantForm) {
		this.applicantForm = applicantForm;
	}

	public ApplicantListModel getApplicantListModel() {
		return applicantListModel;
	}

	public void setApplicantListModel(ApplicantListModel applicantListModel) {
		this.applicantListModel = applicantListModel;
	}

	public void checkAll(ActionEvent actionEvent) {
		getApplicantListModel().checkAll();
	}

	public void create(ActionEvent actionEvent) {
		getApplicantListModel().setSelectedAsNew();
		getApplicantEditor().setFormRendered(true);
	}

	public void deleteChecked(ActionEvent actionEvent) {
		getApplicantListModel().deleteChecked();
	}

	public void edit(ActionEvent actionEvent) {
		UICommand uiCommand = (UICommand)actionEvent.getComponent();
		Applicant applicant = (Applicant)uiCommand.getValue();
		getApplicantListModel().setSelected(applicant);
		getApplicantEditor().setFormRendered(true);
	}

	public void uncheckAll(ActionEvent actionEvent) {
		getApplicantListModel().uncheckAll();
	}

	public ApplicantEditor getApplicantEditor() {
		return applicantEditor;
	}

	public void setApplicantEditor(ApplicantEditor applicantEditor) {
		this.applicantEditor = applicantEditor;
	}
}

3. These snippets are the most confusing to me:

<managed-bean>
		<managed-bean-name>applicantListModel</managed-bean-name>
		<managed-bean-class>training.jobapplication.bean.model.ApplicantLazyListModel</managed-bean-class>
		<managed-bean-scope>session</managed-bean-scope>
		<managed-property>
<property-name>applicantService</property-name>
			<value>#{applicantService}</value>
		</managed-property>
		<managed-property>
<property-name>rowsPerPage</property-name>
			<value>#{userPreferences.rowsPerPage}</value>
		</managed-property>
	</managed-bean>

I try my best to explain.  First of all, here’re some basic java polymorphism code.

Car car = new BMW();
car.go(); --> it calls BMW go() method
super.go() --> it calls Car go() method.

We have to use our polymorphic power to understand this part. This is what’s happening in line 2 and 3 in above xml.

ApplicantListModel applicantListModel = new ApplicantLazyListModel();
or,
ListModel applicantListModel = new ApplicantLazyListModel();
or,
ApplicantLazyListModel applicantListModel = new ApplicantLazyListModel();

We dont know what ApplicantLazyListModel will rertun in run time.  You may have noticed that applicantListModel is not the exact same object type as ApplicantLazyListModel.java  but ApplicantLazyListModel.java extends ApplicantListModel.java.  So there is an ‘is-a’ relationship going on. But Line 6, there is no guarantee that applicantService will be an instance variable (property) of ApplicantLazyListModel.java.  Since ApplicantLazyListModel extends ApplicantListModel, we assume applicantService is a member of ApplicantListModel.java not ApplicantLazyListModel.
Okay, got that, if you dont just pretend you do, it will get clear after you see these following code. Now, here is the another fun part.

<managed-property>
<property-name>rowsPerPage</property-name>
			<value>#{userPreferences.rowsPerPage}</value>
		</managed-property>

I cant not find the property, rowsPerPage nor in ApplicantLazyListModel or ApplicantListModel, where it can be?  ApplicantListModel also extends ListModel. So, rowPerPage is a member of ListModel.java. rowPerPage is also a proerty of UserPreferences.java.  In the above xml,  I’d read like this.  rowPerPage is a property of applicantListModel which value has been set by calling get method, userPreferences.rowPerPage. Objects hierarchies are as follows.

UML

public class ApplicantLazyListModel extends ApplicantListModel {
.....
}
public class ApplicantListModel extends ListModel {

private ApplicantService applicantService;
...
}
public abstract class ListModel {
private int rowsPerPage = -1;
...
}
package training.jobapplication.bean.util;

public class UserPreferences {

	private int rowsPerPage = 5;
	private int maxPageNumberNavControls = 3;
	private boolean pageNumberNavControlsShown = true;

	public int getRowsPerPage() {
		return rowsPerPage;
	}
	public void setRowsPerPage(int rowsPerPage) {
		this.rowsPerPage = rowsPerPage;
	}
	public int getMaxPageNumberNavControls() {
		return maxPageNumberNavControls;
	}
	public void setMaxPageNumberNavControls(int maxPageNumberNavControls) {
		this.maxPageNumberNavControls = maxPageNumberNavControls;
	}
	public boolean isPageNumberNavControlsShown() {
		return pageNumberNavControlsShown;
	}
	public void setPageNumberNavControlsShown(boolean pageNumberNavControlsShown) {
		this.pageNumberNavControlsShown = pageNumberNavControlsShown;
	}

}

Man, now my brain hurts to think all these object relations.  Feel free to write comments and more details in concept wise, visit my cohort David Wilson-Burns blog. He explains why we need Injection instantiation vs. using ‘new’ to create an object reference in Java. Here is the full faces-config.xml

<?xml version="1.0" encoding="UTF-8"?>

<!DOCTYPE faces-config PUBLIC "-//Sun Microsystems, Inc.//DTD JavaServer Faces Config 1.1//EN" "http://java.sun.com/dtd/web-facesconfig_1_1.dtd">
<faces-config>
	<application>
		<message-bundle>JSF-override</message-bundle>
		<view-handler>com.icesoft.faces.facelets.D2DFaceletViewHandler</view-handler>
		<variable-resolver>org.springframework.web.jsf.DelegatingVariableResolver</variable-resolver>
	</application>
	<!--
	<lifecycle>
<phase-listener>training.jobapplication.lifecycle.LoggingPhaseListener</phase-listener> </lifecycle>
	-->
	<converter>
		<converter-id> provinceIdConverter </converter-id>
		<converter-class> training.jobapplication.converter.ProvinceIdConverter </converter-class>
	</converter>
	<managed-bean>
		<managed-bean-name>applicantEditor</managed-bean-name>
		<managed-bean-class>training.jobapplication.bean.backing.ApplicantEditor</managed-bean-class>
		<managed-bean-scope>request</managed-bean-scope>
	</managed-bean>

	<managed-bean>
		<managed-bean-name>applicantList</managed-bean-name>
		<managed-bean-class>training.jobapplication.bean.backing.ApplicantList</managed-bean-class>
		<managed-bean-scope>request</managed-bean-scope>
		<managed-property>
<property-name>applicantEditor</property-name>
			<value>#{applicantEditor}</value>
		</managed-property>
		<managed-property>
<property-name>applicantListModel</property-name>
			<value>#{applicantListModel}</value>
		</managed-property>
	</managed-bean>

	<managed-bean>
		<managed-bean-name>applicantForm</managed-bean-name>
		<managed-bean-class>training.jobapplication.bean.backing.ApplicantForm</managed-bean-class>
		<managed-bean-scope>request</managed-bean-scope>
		<managed-property>
<property-name>applicantEditor</property-name>
			<value>#{applicantEditor}</value>
		</managed-property>
		<managed-property>
<property-name>applicantListModel</property-name>
			<value>#{applicantListModel}</value>
		</managed-property>
		<managed-property>
<property-name>citySupport</property-name>
			<value>#{citySupport}</value>
		</managed-property>
	</managed-bean>
	<managed-bean>
		<managed-bean-name>provinceSupport</managed-bean-name>
		<managed-bean-class>training.jobapplication.bean.support.ProvinceSupport</managed-bean-class>
		<managed-bean-scope>request</managed-bean-scope>
		<managed-property>
<property-name>provinceService</property-name>
			<value>#{provinceService}</value>
		</managed-property>
	</managed-bean>
	<managed-bean>
		<managed-bean-name>citySupport</managed-bean-name>
		<managed-bean-class>training.jobapplication.bean.support.CitySupport</managed-bean-class>
		<managed-bean-scope>request</managed-bean-scope>
		<managed-property>
<property-name>cityService</property-name>
			<value>#{cityService}</value>
		</managed-property>
	</managed-bean>

	<managed-bean>
		<managed-bean-name>applicantListModel</managed-bean-name>
		<managed-bean-class>training.jobapplication.bean.model.ApplicantLazyListModel</managed-bean-class>
		<managed-bean-scope>session</managed-bean-scope>
		<managed-property>
<property-name>applicantService</property-name>
			<value>#{applicantService}</value>
		</managed-property>
		<managed-property>
<property-name>rowsPerPage</property-name>
			<value>#{userPreferences.rowsPerPage}</value>
		</managed-property>
	</managed-bean>

	<managed-bean>
		<managed-bean-name>userPreferences</managed-bean-name>
		<managed-bean-class>training.jobapplication.bean.util.UserPreferences</managed-bean-class>
		<managed-bean-scope>session</managed-bean-scope>
	</managed-bean>
	<navigation-rule>
		<from-view-id>/applicantList.xhtml</from-view-id>
		<navigation-case>
			<to-view-id>/applicantForm.xhtml</to-view-id>
		</navigation-case>
	</navigation-rule>
	<navigation-rule>
		<from-view-id>/applicantForm.xhtml</from-view-id>
		<navigation-case>
			<to-view-id>/applicantList.xhtml</to-view-id>
		</navigation-case>
	</navigation-rule>
</faces-config>

Related Topics: What is Dependency Injection (DI) / Inversion of Control (IoC):  “Hollywood Principle”—”don’t call us, we will call you”. – Wiki’s definition

Pros: The dependency injection approach offers more flexibility because it becomes easier to create alternative implementations of a given service type, and then to specify which implementation is to be used via a configuration file, without any change to the objects that use the service. This is especially useful in unit testing, because it is easy to inject a mock implementation of a service into the object being tested.

Cons: The price paid for that additional flexibility is greatly increased complexity and the fact that the program is no longer deterministic: it’s no longer possible to tell what functions will be called just by looking at the code.

January 16, 2009 Posted by | Java Server Faces, Spring Framework | 1 Comment

ICEFaces effect

I was trying to make ICEfaces effect using <ice:effect> tag.  But apprently it did not work without <ice:panelGroup>

http://www.icefaces.org/JForum/posts/list/0/8161.page#40290

Thanks

September 5, 2008 Posted by | ICEfaces, Java Server Faces | | 1 Comment

ICEFaces tree, data load

How do I load first tree node data set by default?  Here is an screen shot when the application gets initialized.

EPF Tree

EPF Tree

Now, if I click “EPF Work Group”, I get this following data

EPF Tree 2

EPF Tree 2

But, I’d like to see this screen without clicking “EPF Work Group” tree node or when application gets initialized.  I assume, I have to do it in backing bean, fire up an Action Event or so on.

Solution: http://www.icefaces.org/JForum/posts/list/9588.page

August 25, 2008 Posted by | ICEfaces, Java Server Faces | 2 Comments

Read query string from backing bean – 2 ways

I needed to read a parameter from query string in JSF backing bean. http://atowus/epf?packageId=17169

Here how it works:

 FacesContext context = FacesContext.getCurrentInstance();
 Map<String, String> params = context.getExternalContext().getRequestParameterMap();
 String pID = params.get("packageId");
 

Now pID should have the value 17169

OR:

In faces-config.xml:
<managed-bean>
 <description>Backing bean for tree example. </description>
 <managed-bean-name>tree</managed-bean-name>
 <managed-bean-class>gov.faa.amc.nas.epf.TreeBean</managed-bean-class>
 <managed-bean-scope>request</managed-bean-scope>
 <managed-property>
<property-name>packageId</property-name>
 <value>#{param.packageId}</value> <!--JSF injects query string value from request parameter -->
 </managed-property>
 </managed-bean>

In TreeBean.java, I have a instance variable and getter and setter


private String packageId;

Caution: Bean scope has to be request otherwise you get a nasty error like this.

javax.faces.FacesException: Problem in renderResponse: Unable to create managed
bean tree. The following problems were found:
- The scope of the object referenced by expression #{param.packageId}, request, is shorter than the
referring managed beans (tree) scope of session note

June 4, 2008 Posted by | Java Server Faces | | 1 Comment

!include vs. #include

Ken Paulsen‘s Reply:
#include staticly includes a file into your page.

<!include> (or <ui:include> in the facelets syntax) dynamically includes a file into your page. Also <!include> supports passing in parameters to the included page. For example:

test.jsf:
   <!include src="foo.jsf" foo='bar' />

foo.jsf:
“The value of foo: #{foo}

Try that.

The pro’s for #include… from JSFT’s perspective it is only 1 file and therfor id’s are never a problem. It’s also fast and efficient (the other way isn’t bad, but this one is faster).

The pro’s for <!include>, it’s dynamic so you can use #{} to determine the template name and you can pass in values. The big advantage comes from the closely related tag: <!composition> which allows you to use <!define> to pass values to a template. This is very powerful.

Let me know if you need more details.

Thanks,

Ken

April 16, 2008 Posted by | Java Server Faces | Leave a comment

RichFaces, JPA trial and error

Issue # 1. I wanted to use RichFaces Modal Panel to pop up a login screen and I got an error. Instead of going to login.xhtml, it was giving me file download error like this.
idmserror.jpg

Solution: In my web.xml file I added <welcome-file>index.xhtml</welcome-file>. I had to change index.xhtml to index.html to make it work. I guess application initialization it does not know what is xhtml. Once application get initialized, then it recognizes the xhtml extension.

Issue with Persistence Model: Exception occured in J2EEC Phase
com.sun.enterprise.deployment.backend.IASDeploymentException: Deployment Error — The persistence-context-ref-name [persistence/LogicalName] in module [C:\buildLocal\WebDMS\build\web] resolves to a persistence unit called [WebDMSModelPU] which is of type RESOURCE_LOCAL. Only persistence units with transaction type JTA can be used as a container managed entity manager. Please verify your application.

Jason: Drop the type=”” (?) decl from your persistence declaration, or change it to JTA
OR stop using injection to get your EntityManager

Jason: <persistence-unit name=”WebDMSModelPU” transaction-type=”JTA”> or <persistence-unit name=”WebDMSModelPU”>
JTA is the default. if you have “RESOURCE_LOCAL”, that tells JPA that you will handle txn mgmt yourself. a container-managed EM can’t work in that… mode

So here is my workable persistence.xml looks like:

<persistence version="1.0" xmlns="http://java.sun.com/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_1_0.xsd">
<persistence-unit name="WebDMSModelPU" transaction-type="JTA">
<provider>oracle.toplink.essentials.PersistenceProvider</provider>
<jta-data-source>jdbc/dms</jta-data-source>
<class>webdmsmodel.model.Project</class>
<class>webdmsmodel.model.ProjEpf</class>
<class>webdmsmodel.model.ProjType</class>
</persistence-unit>
</persistence>

More details on this issue: David’s blog, JSF ForumIssue 3: This was very weired. My accordion image was not showing up when I did a hot deployment to the development server from my local machine. But it worked on the local machine.
noimg.jpg
Solution: It worked after spent couple hours. I had to re start our development application server
SJSAS 9.1 UR 1) to see the change.withimg.jpgIssue # 4: Scrollable Data Table wont render data.

<rich:scrollableDataTable  id="projectTable" var="project" value="#{controller.projectList}" first="0" rows="20">

Solution: I was returning a DataModel instead of List. I assume, scrollable data table does not work with DataModel.2 cents from Jason: I’ve never used DataModel, always using a List. Internally, dataTable will convert a List to a ListDataModel, for what that’s worth. Apparently, I lose some things by not using a DataModel, but I’m not sure what that is yet. :)HH: I must say that RichFaces is such a sweet JSF component libraries to work with. Awesome. Full credit goes to Jason Lee, who introduced me with it. I have tried Sun’s Woodstock and few other libraries, but RichFaces has the best documentations, it is very easy to use and more frequently version updates.

March 20, 2008 Posted by | Java Persistence API, Java Server Faces, Jboss RichFaces (Ajax4JSF) | Leave a comment