TOC PREV NEXT INDEX

Enhancing the TimeZoneBean


Now that we have integrated ICEfaces, the work to show the clocks tick is done in the bean. No actual work is done to make the clocks tick because the system time updates automatically for us. Rather, at some interval, the components that display the clock times must be rendered, and those updates must be sent to the web browser. For this, we will use the ICEfaces specific RenderManager facilities to manage a JSF render pass. For timezone3, the following changes are made to the TimeZoneBean.java file.

1. First we add some imports to support the new ICEfaces features:
import com.icesoft.faces.async.render.IntervalRenderer;
 
import com.icesoft.faces.async.render.RenderManager;
 
import com.icesoft.faces.async.render.Renderable;
 
import com.icesoft.faces.webapp.xmlhttp.PersistentFacesState;
 
import com.icesoft.faces.webapp.xmlhttp.RenderingException;
 
import com.icesoft.faces.webapp.xmlhttp.FatalRenderingException; 
 
import com.icesoft.faces.context.DisposableBean;
 
import org.apache.commons.logging.Log;
 
import org.apache.commons.logging.LogFactory;
 

 
2. Then we make the bean implement com.icesoft.faces.async.render.Renderable, so we can use it with the RenderManager facilities:
public class TimeZoneBean implements Renderable {
 
3. A rendering interval is added as a bean property:
private final int renderInterval = 1000;
 
4. Add helper objects for maintaining the rendering state and managing the threading issues:
private PersistentFacesState state;
 
private IntervalRenderer clock;
 

 
5. Initialize the rendering state:
private void init() {
 
		...
 
		state = PersistentFacesState.getInstance();
 
}
 
6. Provide a callback method to use the RenderManager to set up the interval rendering:
public void setRenderManager(RenderManager renderManager) {
 
		clock = renderManager.getIntervalRenderer("clock"); 
 
		clock.setInterval(renderInterval); 
 
		clock.add(this); 
 
		clock.requestRender();
 
}
 
7. Allow the RenderManager facilities to access the rendering state:
public PersistentFacesState getState() {
 
		return state;
 
}
 
8. Provide a callback method to allow notification of rendering problems. An example of an expected invocation would be when the user has closed the web browser, and there is no target to render to:
public void renderingException(RenderingException renderingException) {
 
	if (log.isDebugEnabled()) {
 
		log.debug("Rendering exception:  " + renderingException);
 
	}
 
	if (renderingException instanceof FatalRenderingException) { 
 
		performCleanup();
 
	}
 
}
 

 
protected boolean performCleanup() {
 
	try {
 
		if (clock != null) {	
 
			clock.remove(this);
 
			 if (clock.isEmpty() ) { 
 
				clock.dispose();
 
			}
 
			clock = null;
 
		}
 
		return true;
 
	} catch (Exception failedCleanup) {
 
		if (log.isErrorEnabled()) {
 
			log.error("Failed to cleanup a clock bean", failedCleanup);
 
		}
 
	}
 
	return false;
 
}
 

 
9. To enable use of the RenderManager requires adding it as a managed application scoped bean, and having the application server tie it to our timeZoneBean's renderManager property. This is accommodated by making the following changes to the faces-config.xml file.
<managed-bean>
 
	<managed-bean-name>renderManager</managed-bean-name>
 
	<managed-bean-class>
 
			com.icesoft.faces.async.render.RenderManager
 
	</managed-bean-class>
 
	<managed-bean-scope>application</managed-bean-scope>
 
</managed-bean>
 
<managed-bean>
 
	<managed-bean-name>timeZoneBean</managed-bean-name>
 
	<managed-bean-class>com.icesoft.tutorial.TimeZoneBean</managed-bean-class>
 
	<managed-bean-scope>request</managed-bean-scope>
 
	<managed-property>
 
			<property-name>renderManager</property-name>
 
			<value>#{renderManager}</value>
 
	</managed-property>
 
</managed-bean>
 
10. The RenderManager needs to know about the context and session lifecycles. To provide the appropriate information, the ICEfaces application needs to publish its Context events. This is achieved by adding the following code snippet to the web.xml file:
<listener>
 
	<listener-class>
 
			com.icesoft.faces.util.event.servlet.ContextEventRepeater
 
	</listener-class>
 
</listener>
 
11. Implement the DisposableBean method by adding the following code snippet to the TimeZoneBean file:
public void dispose() throws Exception {
 
        if (log.isInfoEnabled()) {
 
            log.info("Dispose TimeZoneBean for a user - cleaning up");
 
        }
 
        performCleanup();
 
    }
 

 


Copyright 2005-2009. ICEsoft Technologies, Inc.
TOC PREV NEXT INDEX