Grails is a dynamic web development framework on the Java platform for rapid application development. It has taken the coding by convention approach popularized by Ruby on Rails, and applied it as a wrapper over long established open source Java frameworks such as Hibernate and Spring. It uses the flexibility of Groovy to provide a Domain-Specific Language (DSL) for web development.
The goal is to be able to develop web applications with the minimum amount of effort without having to repeat yourself. Grails provides a consistent and reliable environment between all your projects.
We are going to create a web application that will allow members of a team to communicate with one another. We will need to be able to make each of the team members a user of the application, so that in future iterations they can log in and collaborate. In this chapter, we will create a domain class to represent a user and a role in the application. We will add constraints to these domain classes to enforce the integrity of the data that is entered. By the end of this chapter, we will use Grails scaffolding to generate a user interface that allows users and roles to be managed within the application.
You have used Grails scaffolding to create some skeleton pages that manage users and roles. You will now learn the basics of web application development in Grails and implement the first of our user's goals, to post messages.
The first user story could go something like this. As a team member, I want to be able to send a message to the rest of my team, so that I can share important information with my teammates...
The application is at the point now where you need to start getting your hands dirty by writing some of the logic behind it. Before going any further you should take some time to investigate and understand the Groovy language a bit more. A large majority of the code you will write under Grails will be Groovy, so taking the time to understand the contents of this chapter will be well worth it. You will cover the following areas of the Groovy language:
The similarities to Java How to install and run Groovy Groovy data structures Closures Plain old Groovy objects Metaprogramming Builders
This chapter is not intended to be a complete guide to the Groovy language, but is merely an introduction to what you'll need to complete the example application.
Now that you have a decent understanding of Groovy, you can carry on building the application. You currently have user administration screens that are being handled by Grails scaffolding, and users can create messages that are visible on the home page. Before adding any new features, you will learn how to leverage Grails plug-ins to add new behavior to your application. You will use a security plug-in to secure the application, so that only the authenticated users can post and view messages, and only the administrators are able to manage users.
We have seen enough of the basics of web development with Grails for now. Before continuing any further, we should take a look at automated testing in the Grails world. We will discuss unit testing and some guidelines to writing good unit tests. After unit tests we will cover the difference between integration testing and unit testing and how Grails supports both approaches. Finally, we will talk about why automated functional testing can cause so many problems and investigate a plug-in called Grails Functional Testing that takes the pain out of functional testing.
As well as posting messages our users want to be able to upload files to share with other members of their team. Sounds good. But wait a minute, isn’t file uploading a bit of a pain. First of all, we need to read the binary file data off the request and then we need to figure out where to put the file. Do we store it on the file system, or in a database? Well, let's take a look.
In this chapter we will see how easy it is to manage file upload and download in a Grails application.
Now imagine, flushed with the success of how easily we implemented file upload, we decide to put our application in front of some users. It all starts well; our test users post some messages and upload a few files. They start uploading different versions of a sales pitch. Suddenly someone pipes up: “How about if we could group the different versions of this document? We go through a number of revisions and it would be useful to be able to see the changes all together.”
Being the pragmatic user-centered people that we are, and given how simple it was to get basic file uploading working, we decide to get right on it! The first step is… You guessed it: domain modeling.
In the last two chapters we allowed the users to post new files to the application, and also keep a version history of files. Unfortunately, as a result of these changes, we have accrued a certain amount of technical debt in the FileController class. This class is no longer just handling the flow of the application; it is now responsible for managing the logic to enable version history for files. We need to remove this logic from the controller so it can get back to controlling the flow of our application.
Over the last few chapters we added the ability for users to upload and share files with their teammates. As with messages, files are displayed on the home page in the order they are added to the system. Currently all messages and files are displayed on the home page. Over time, our home page is going to become rather large and unwieldy. We need a users home page to show only the files and messages that they are interested in. To do this, users need to be able to tag their content.
We will implement a simple tagging solution, restructure the home page and then add some new pages to the application for viewing all messages and files.
The new Grails concepts that will be introduced in this chapter are:
Working with inheritance in the domain classes, and which strategies GORM supports for persistence. Using polymorphic queries over a domain inheritance hierarchy. Encapsulating view-rendering logic in GSP templates. How to manipulate collections with the Groovy methods collect and sort.
We are going to enhance the user experience of our application using AJAX and Rich Internet Application (RIA) frameworks. We will see how Grails provides built-in support for AJAX, and then introduce a plug-in that provides a number of components to leverage popular user interface design patterns. The enhancements we will implement in this chapter are:
Allow tags to be updated through AJAX. Automatically suggest existing tags when a user is tagging content. Use a tag cloud to filter content by tags.
After our last increment of providing editable in-line tagging, the users have been making good use of the application. There are now hundreds of posts and quite a few files in our application. Sometimes activity has been so fast that users have reported their messages are getting lost and people aren't seeing the information they need.
It is great news that our application is being used so much, but we need to address some new user goals that have arisen due to the usage of the application. Namely, to easily search for past messages and keep up-to-date with the increased levels of activity.
It sounds like our users need to be able to search the content of the application, and given the high frequency of messages they would probably benefit from some sort of unobtrusive notification system for new content: an RSS feed springs to mind.
We have also received some requests to send messages into the application via email. Who knows where else we will need to receive data from in the future? We had better put some web services onto the application to allow other applications to add content in the future.
Now that you have finished the implementation of your application it is time to look at the code and see what can be pulled out into a separate component for reuse on future projects. The feature that stands out as being most reusable is tagging. This feature will be useful on many different projects. Simplifying the implementation of tagging for future projects by using a plug-in will be a great benefit. In this chapter you will see how to:
Create and package your own plug-in Enhance the plug-in using dynamic method support in Groovy and Grails
The final stage in the delivery of your Grails application is to deploy it to a stable production environment, running in a hosted servlet container and against a permanent database that will not be cleared out every time you restart or re-deploy the application. You will see just how simple it is to package a Grails project into a deliverable and set up the Grails configuration for a production environment.
Once the application is up and running in a production environment we will briefly introduce some next steps that may worth investigating to learn more about working with Grails.