Generic controllers and model builders

In a typical web application you often find yourself writing the same Java code in your controllers over and over again. A very common use-case is to take some request parameters, incorporate them into a database query, execute it and pass the result on to the view.

To reduce boilerplate code Riot introduces the ModelBuilder interface that encapsulates the building of a model map. Even more useful are the concrete implementations, namely the HqlModelBuilder and HqlListModelBuilder which allow you to perform Hibernate queries without writing a single line of Java code.

Here's a slightly modified example taken from the riot-blog project:

<generic:controller id="postDetail" name="/post-@{id:Long}.html"
        view-name="/inc/post-detail.ftl">
    <generic:hql hql="from Post p where p.id = :id" />
</generic:controller>

Assumed that you use the AdvancedBeanNameHandlerMapping (or PageHandlerMapping), a request to /post-42.html will load the the Post entity with id 42.

You can not only load single entities but also display lists of objects:

<generic:controller name="/all-posts.html">
    <generic:hql-list hql="from Post p order by p.date desc" />
</generic:controller>

... or even a paged list:

<generic:controller name="/all-posts.html">
    <generic:hql-paged-list hql="from Post p order by p.date desc"
        page-size="10" />
</generic:controller>

Besides the actual list of entities, the ModelBuilder will also provide a Pager object, that makes it easy to render pagination links.

Static Models

Since Riot 7.0.1 the generic: namespace also allows you to define static models. This can be useful if you want to use the same view with different pre-configured data.

<generic:controller name="/foo.html">
  <generic:model>
    <entry key="bar" value="baz" />
  </generic:model>
</generic:controller>