Tuesday, April 21, 2009

Starting with front-end in grails application

[From the series - creating software books reviews grails web application]

In the previous post I have explained how to create grails application and some general aspects of the grails application. If you are expert for the web front-end you can probably jump into domain logic but if you are like me, front-end is probably harder part of the web application development. As it is generally advised to start with the more complex parts of the application I am usually setting up at least general aspects of the user interface. So let us see how is solved front-end of the grails application.

View technology of the grails application is groovy server pages or shorter gsp while sitemesh is used as main templating mechanism. To gain knowledge of the existing gsp tags visit grails documentation. There is description and short example for each tag. If you don't know site mesh don't worry because I don't know it either. The main usage is very easy and does not require knowledge of the sitemesh.

First interesting file to notice is main.gsp that is located in the grails-app/views/layouts. This file is template for other pages of the application. Just to notice, you can have any number of "main.gsp" files in your grails application. One for each different situation you need. E.g. one for pages with three columns, one for pages with two columns and so on.

The most important part of the main.gsp file is:

<g:layoutBody />

When some page as template uses main.gsp, the whole content of the main.gsp page will be displayed and the <g:layoutBody /> will be replaced with the body element of the mentioned page. To specify which template should be used for the gsp page, put following construct in the <head> element of the page.

<meta name="layout" content="NAME_OF_TEMPLATE_FILE" />

and replace the NAME_OF_TEMPLATE_FILE with the name of template without gsp extension.

So if you have page like this one:

<html>
<head>
<meta name="layout" content="main" />
</head>
<body>
<p>Hello World</p>
</body>
</html>

the main.gsp will be displayed an the element <g:layoutBody /> will be replaced with <p>Hello World</p>. I am not sure that this is 100% correct but this is generally how it behaves.

If this is still confusing let try to make some simple example. Assume that we have two template files: main1.gsp and main2.gsp that are of course placed in the grails-app/views/layouts directory.

// main1.gsp
<html>
<head>
<title><g:layoutTitle default="Grails" /></title>
<g:layoutHead />
</head>
<body>
<h1>Hello World</h1>
<g:layoutBody />
</body>
</html>



//main2.gsp
<html>
<head>
<title><g:layoutTitle default="Grails" /></title>
<g:layoutHead />
</head>
<body>
<g:layoutBody />
<h1>Hello World</h1>
</body>
</html>

And if we create following two gsp pages

// test1.gsp that uses main1.gsp as a template
<html>
<head>
<meta name="layout" content="main1" />
</head>
<body>
<p>Page 1</p>
</body>
</html>



// test2.gsp that uses main2.gsp as a template
<html>
<head>
<meta name="layout" content="main2" />
</head>
<body>
<p>Page 2</p>
</body>
</html>

test1.gsp will be displayed as:

Hello World
Page 1

while test2.gsp will be displayed as:

Page 2
Hello World

This way you have very powerful tool to create set of pages that look the same and you are just changing the business content of the page. The "same" part should be located in the template file while the "business content" should be located in the page. If for some set of pages you need different layout just create new common template for them. All this magic is possible because grails in the background uses sitemesh for this.

Now when there is basic understanding how front-end works in the grails application we are ready to create our home page. And this will be topic of my next post. I will create dummy home page, admin page from the index.gsp and redirect application to the home page.

P.S. Don't forget to write some review or post summary on the software books reviews.

4 comments:

Unknown said...

Thanks for the explanation! I'm currently developing an application with some friends at the university - a game using twitter as a plataform, and you just saved my day!

Ps.: My english is pretty bad (i'm from brazil) - sorry!

Jason Blum said...

Thanks for a very helpful blog.

...wonder if you could answer a question: I'd like to output some application stats in kind of a mini-dashboard on the right-hand side of my main.gsp (so that these stats appear on every page).

In other templates, I'd have the associated controller pass a model to the view to output. But main.gsp is just a wrapper around views and has no controller of its own. Any idea how to do this?

Thanks!

jan said...

@phenotypical
Part of the answer is in my blog post about grails templates and tags..

In short:
- create template that displays some information provided from model (standard behavior for all templates)
- create custom tag that will read necessary data from database (session, file...) and display template.

This way you don't need any controller to display those kind of data.

Jason Blum said...

Thanks Jan - I tried that approach too and completely forgot that I was forgetting to specify the package to my domain classes. All three approaches work as you describe once you get past rookie mistakes like that :) Thanks!