Showing posts with label Design. Show all posts
Showing posts with label Design. Show all posts

Monday, January 20, 2014

RichFaces 4.3.x Tip of the Day: Complex RichFaces Data Tables

Introduction

I have been working on JSF tables for the various projects I have been involved with over the years. Starting in 2012, I began looking at RichFaces <rich:dataTable /> for some projects at my day job. The research into how to handle a number of complex situations has been enlightening to say the least.

The table is the most complex component in HTML. It is seemingly boundless in its extensibility. You can have multi-column headers that span multiple rows, you can multi-row cells, or multi-column cells. Tables can be displayed left-to-right, or right-to-left, top-to-bottom and vice-versa. As a result, when developing components for JSF, or any component framework, decisions must be made on how to generate them.

A couple of the component frameworks like PrimeFaces, and RichFaces allow developers to create more complex tables with more ease. However there are limitations with each of these frameworks. We trade flexibility for consistency, and this is fine in most cases.

The demonstration code in this post is about getting some of the flexibility back, or taking advantage of the flexibility that comes with a framework like RichFaces. We will gain the flexibility back, but it is a function of complexity. The examples will show you techniques for doing the "same thing" in multiple ways. For example, sorting can be done on the server, client, or a combination of both.

The question is where we put the complex bits. The answer to that question depends on you as a developer. You need to examine the problem domain, and understand the limits to the techniques presented.

Solutions

Please let me confess something. I like building HTML objects programmatically. There I said it. In this case I am trading the ease of development for flexibility. The solutions below will demonstrate the different techniques for accomplishing the same functionality. Please examine the code carefully before discounting it. I spent a lot of time playing with it to make it look simple.

The code for this project was developed using NetBeans and Apache Maven. The code was tested on GlassFish 3.1.2.2 and 4.0. It should work on other application servers, but I have not tested it on other servers. This project assumes you are using NetBeans which includes a sample database that these examples require. If you are not using NetBeans, you will need to create your own database with sample data to display some of the tables.

The code can be downloaded from Bitbucket at the link below, or in the references section at the end of the post.

richfaces-tables-poc

Dynamic Data Table with Sorting

Dynamic Table with Sorting
This example uses the binding attribute of the <rich:dataTable /> to bind our table to a CDI @ManagedBean. The bean is responsible for generating the table programmatically, and returning it back to the page. The data is sortable by column.
As you can see the page is very simple. In fact, most of the page is plumbing and navigation. The <rich:dataTable /> is the smallest part of the page. The code to generate the table is much more complex.
As you can see we have traded simplicity in the page for complexity in the @ManagedBean. If you are satisfied with this technique, lets take a look at another one.

Dynamic Data Table with Sorting Revisited

Dynamic Table
This table uses the same dynamic binding as the example above on the JSF page, but uses helper utilities to create JSF components dynamically from a library that I have written. It is a separate project that you can download (Please see references). This reduces the chances for errors creating common components, but it is still a lot of code. To check our sorting, I have made a "random" data generator for the table data for the code to sort.
The more simplified code in the @ManagedBean is shown below.
The code above was written before I added more functionality to my jsf-utils project. The new methods would shorten this considerably, but it would still be fairly complex.

Dynamic Table using JSP/JSTL Tags with JSF

JSF/JSTL Dynamic Table
Let me start this example with a warning. If you are using JSP/JSTL tags in your JSF pages, you may encounter very bad behavior. This technique should only be used as a last resort. I will not labor a point. If you don't understand why this is a bad idea, take a look at this post for links: JSF 2.x Tip of the Day: Great Blog Posts Explaining JSTL vs. JSF.
In this example, I will generate the rows and columns using <c:forEach />. This transfers a lot of the complexity to the page and away from the @ManagedBean. Since we are using <c:forEach />, our mechanism for sorting has to change. I used Query jquery.tablesorter.js to allow sorting of the headers.
As you can see we have much simpler code in the page bean. It looks like what you would expect for a normal JSF data table.

Complex Data Table Design

Complex Table Design
This table has a lot of really cool features, but the code is complex in the page, and the page bean is relatively simple.

Conclusion

RichFaces supports complex table designs, and produces nice results. The amount of work required to create dynamic data tables depends on the technique chosen, and limitations on the data being presented. There is no "one good way" to create data tables. Suffice to say that the easiest path should be chosen.

References

Saturday, January 18, 2014

HOWTO: Adding SyntaxHighlighter to Blogger

If you want to use SyntaxHighlighter in your blog, you can simply add the code below to the <head /> element in the template for your Blogger blog.

Thursday, November 15, 2012

Annoying IE9 CSS Hover and Overflow Issue

Case

I have a <table/> which is surrounded by a <div/> which has the attribute style="overflow:auto". The table has a hover attribute to highlight table rows on mouseover. Additionally, There are some checkboxes arranged in a table below it, but it could be another element. When you mouseover the table in the div, the checkboxes start moving the the bottom of the page.

Resolution

I found the following bug posted on the jQuery bug tracker: Problem with .hover() and IE9 that describes the behavior. Brian Richards, who is linked to in the bug, has a simple bug elegant fix that worked for me.In his blog post, IE9 Hover Bug Workaround, he simply added min-height:0% to the style.

I hope that the solution works for others who may encounter the problem. I also found another blog to put on my blog roll to keep an eye on. Thanks for blogging Richard.

Wednesday, July 04, 2012

Tip of the Day: Code Review Checklist

Over the last few days,  I have published some code review tips of the day. This post actually contains a link to a Microsoft Word Document with those tips in checklist format.

Code Review Checklist.docx

Tip of the Day: Performance Code Review

Performance

Here are some general best practices to consider around performance code review.

These tips are by no means definitive, but serve as reminders to developers what they should consider in a checklist.

Note: performance code reviews are really not separate processes from a general code review.
  • Objects are duplicated only when necessary. If you must duplicate objects, consider implementing Clone and decide if deep cloning is necessary.
  • No busy-wait loops instead of proper thread synchronization methods. For example, avoid while(true){ ... sleep(10);...}
  • Avoid large objects in memory, or using String to hold large documents which should be handled with better tools. For example, don't read a large XML document into a String, or DOM.
  • Do not leave debugging code in production code.
  • Avoid System.out.println(); statements in code, or wrap them in a boolean condition statement like if(DEBUG) {...}
  • "Optimization that makes code harder to read should only be implemented if a profiler or other tool has indicated that the routine stands to gain from optimization. These kinds of optimizations should be well documented and code that performs the same task should be preserved." - UNKNOWN.

    Note: I found this gem a few years ago, but it is so true. If anyone knows who said this, please comment.

Tuesday, July 03, 2012

Tip of the Day: Error Handling Code Review

Error Handling

Here are some general best practices to consider around error handling code review.

These tips are by no means definitive, but serve as reminders to developers what they should consider in a checklist.

Note: error handling and general code reviews are really not separate processes.
  • Invalid parameter values are handled properly early in methods (Fast Fail).
  • NullPointerException conditions from method invocations are checked.
  • Consider using a general error handler to handle known error conditions.
  • An Error handler must clean up state and resources no matter where an error occurs.
  • Avoid using RuntimeException, or sub-classes to avoid making code changes to implement correct error handling.
  • Define and create custom Exception sub-classes to match your specific exception conditions. Document the exception in detail with example conditions so the developer understands the conditions for the exception.
  • (JDK 7+) Use try-with-resources. (JDK < 7) check to make sure resources are closed.
  • Don't pass the buck! Don't create classes which throw Exception rather than dealing with exception condition.
  • Don't swallow exceptions! For example catch(Exception ignored) {}. It should at least log the exception.

Monday, July 02, 2012

Tip of the Day: Unit Testing Code Review

Testing

Here are some general best practices to consider around unit test code review.


These tips are by no means definitive, but serve as reminders to developers what they should consider in a checklist.

Note: unit testing and code reviews are really not separate processes.
  • Unit tests are added for each code path, and behavior. This can be facilitated by tools like Sonar, and Cobertura.
  • Unit tests must cover error conditions and invalid parameter cases.
  • Unit tests for standard algorithms should be examined against the standard for expected results.
  • Check for possible null pointers are always checked before use.
  • Array indices are always checked to avoid ArrayIndexOfBounds exceptions.
  • Do not write a new algorithm for code that is already implemented in an existing public framework API, and tested.
  • Ensure that the code fixes the issue, or implements the requirement, and that the unit test confirms it. If the unit test confirms a fix for issue, add the issue number to the documentation.

Sunday, July 01, 2012

Tip of the Day: Documentation Code Review

Documentation

Here are some general best practices to consider around documentation code review.

These tips are by no means definitive, but serve as reminders to developers what they should consider in a checklist.

Note: documentation and code reviews are really not separate processes.
  • All methods are commented in clear language. If it is unclear to the reader, it is unclear to the user.
  • All source code contains @author for all authors.
  • @version should be included as required.
  • All class, variable, and method modifiers should be examined for correctness.
  • Describe behavior for known input corner-cases.
  • Complex algorithms should be explained with references. For example,  document the reference that identifies the equation, formula, or pattern. In all cases, examine the algorithm and determine if it can be simplified.
  • Code that depends on non-obvious behavior in external frameworks is documented with reference to external documentation. 
  • Confirm that the code does not depend on a bug in an external framework which may be fixed later, and result in an error condition. If you find a bug in an external library, open an issue, and document it in the code as necessary.
  • Units of measurement are documented for numeric values.
  • Incomplete code is marked with //TODO or //FIXME markers.
  • All public and private APIs are examined for updates.

Thursday, August 25, 2011

Type Safe Collection Conversion

I was reading a great article by a friend of mine Checking an Unchecked Cast in Java 5 or Later where he refers to some of the rules from Josh Bloch about making type safe conversions. It was interesting. Glen also provides a good code example of how he does a type safe conversion. I thought I would provide a couple of examples using a List converter. I have heard that a number of folks do not like returning <T> from a method which has a collection associated with it. However like any tool, it is up to the person using it not to hurt themselves (i.e. a screwdriver is not a hammer). In this example I have a couple of methods which do type safe conversion of a List of something. We need to know in advance what we expect that something to be. This is just one example of how you can do a conversion on a collection. I would like to note that there are methods on the Collections class which returns a checked collection. This ensures that any object added to a collection is of particular type. As the API notes, this is for the addition of classes after the collection has been turned into a checked collection. It does not check the Collection for previously added objects. The code below checks all of the object types before doing the conversion, and fails if it encounters the wrong type.

Sunday, November 02, 2008

Effective Tools and Techniques for the Java Developer - InformIT white paper

I just finished reading a white paper from InformIT. It is essentially excerpts from a number of books from well know authors like Joshua Bloch, and Kent Beck. The sections they included were good, but like all good things...they must come to an end.

The sections did not cover the topics in their entirety, and in most cases ended in the middle of a topic. It is a taste teaser. I will note that although you really can't accomplish much from the excerpts, it does give you a good feel for the books and authors.

Saturday, December 15, 2007

Release It! Review

I just completed reading Release It! by Michael T. Nyggard (Pragmatic Bookshelf 2007). It is part of The Pragmatic Programmers series. I have read the book cover to cover twice. At first, I thought that the book was just another book on how to manage projects. So What! The ideas presented in the book were common sense. I have been doing these same things for many years.

Then one day I was working on a project, and was trying to figure out how to handle a problem. I remembered what I read in Release It! about the topic. I grabbed the book off the bookshelf and looked it up; logging. The ideas presented are common sense, but how often have we missed to boat. The ideas presented in the book I implemented much to my own joy. The result was a customized deployment of the Java Logging system which is simple to maintain and does not require external libraries.

It was at that point I realized the brilliance of the book and the pragmatic side of things. I re-read the book. As an architect, project manager, developer, and maintainer of complex software ecosystems, the ideas in the book provide a "pragmatic" common sense approach to handling situations. The book is a learning tool, one person's personal perspective on software design and deployment, and a reference. It is an all-in-one book.

This book provides a great tutorial on how to manage complex projects for the novice, and a gentle practical reminder to the seasoned architect/project manager.

The book is divided into 4 major sections: Stability, Capacity, General Design Issues, and Operations. The first two sections provide the basis for the remainder of the book. The Stability and Capacity sections have divided the topic into an explanation, followed by general design patterns and anti-patterns. It explains in enough detail how to implement good patterns and recognize bad ones.

The section on General Design covers items like Administration and Security. There is nothing earth shattering in these sections, but they do provide a basis for a "check list" of items to make sure you consider in your designs.

The final section on Operations is the one where you will make friends with your administrators and keep your sanity. The portions on designing for monitoring including logging will be your savior at 2:00 AM in the middle of a blizzard. The discussion on designing for the future does not get enough attention in our modern get it out the door now world. This may be the push you need to think about it.

This is a book to have on your bookshelf. Mine is full of tabs and post-it notes.

Popular Posts