Chapter 4. Spring

Grails is a metaframework in that it ties together several other frameworks, and none is more pervasive in Grails than the Spring Framework. Grails uses a significant amount of Spring core functionality and optional modules including managing artifacts and many classes as Spring beans (using Spring’s dependency injection to manage the graph of dependencies), its datastore integration features (by default using its Hibernate integration), support for proxies and AOP to enable transparent transactions (and caching and security via plugins), internationalization, resource management, and a lot more.

In addition, there are many Spring extensions (both official and third party) that are readily usable in a Grails application. Many are already exposed via plugins (e.g., Spring Security), but if not, you can use an extension like you would in any Spring-based application. You can use annotated bean classes or the newer Java configuration, or copy bean definitions into grails-app/conf/spring/resources.xml (this isn’t created by default so you need to create it yourself) or convert them to Groovy syntax in resources.groovy. Register any dependencies in BuildConfig.groovy, and you’re ready to go.

Inversion of Control and Dependency Injection

One of the central ideas of Spring that Grails uses heavily is Inversion of Control (IoC), also known as Dependency Injection (DI). This reverses the direction of managing object dependencies from the older style of creating them directly or pulling them in from a repository (e.g., JNDI) to a style where beans don’t know how to retrieve their dependencies, but have setter methods and constructors that are used to push dependencies in. This obviously changes everything and opens up many possibilities for much more dynamic and loosely coupled code, and fits the Grails model very well.

In older versions of Spring dependency injection, you would use XML configuration files, but now it’s as simple as using the @Autowired annotation. In Grails, it’s even simpler; any Spring bean written in Groovy (this includes all of the standard artifacts such as controllers, services, and taglibs) can inject the userService bean by adding the line:

def userService

as a class-scope field. You can specify the type of the field if you want (this can help IDE autocompletion), but it’s not necessary.

This seems quite magical but, like most things in Grails (and Groovy), it’s actually very simple. It makes a lot more sense if you recall that fields in Groovy classes that don’t have a scope modifier are, by default, public, and the Groovy compiler converts them to a private field and a getter and setter (unless you have already created the getter or setter—it won’t replace yours). This means that this field is actually implemented as if you had this code:

private Object userService

void setUserService(Object userService) {
   this.userService = userService
}

Object getUserService() {
   return userService
}

For our purposes, the getter isn’t very useful, but the setter is. That’s because, by default, Grails creates its beans with autowiring enabled, and is set to “by name” mode. So, as Spring is building its ApplicationContext and wiring together the various dependencies, if it sees a setter whose property name matches a bean name, it will call the setter to inject that bean. So, even though Spring doesn’t know anything about Groovy, because it sees the public setter that the Groovy compiler created, it injects the userService bean into your bean as if you had created the setter for that purpose.

Therefore, it should be clear why adding def beanName inside a method doesn’t work: it’s just a local variable and not a candidate for dependency injection.

Complex Dependency Configuration Using Spring SpEL

In general, setting bean dependencies in resources.groovy is done with either other beans or properties that are numbers, strings, Booleans, etc. But you can use Spring Expression Language (SpEL) in property value strings to access other beans’ properties and even call their methods. For example, if the Bar class has a name property (or getName method), you can access it to configure the foo bean:

beans = {
   bar(Bar)

   foo(Foo) {
      name = '#{bar.name}'
   }
}

Or, if you want to leave the logic for how to resolve the property in the Foo class, you can call a method instead:

beans = {
   bar(Bar)

   foo(Foo) {
      name = '#{bar.resourceName()}'
   }
}

For more information, see the relevant section in the Spring documentation, Expression support for defining bean definitions.

Manually Injecting Dependencies at Runtime

If you manually instantiate classes that aren’t Spring beans, but would like to conveniently inject Spring bean dependencies into them (e.g., classes in src/groovy and src/java), you can do this if you have access to the Spring ApplicationContext. This is simple if you dependency-inject the grailsApplication bean into the artifact class (e.g., a controller or a service) that is creating the instance:

def grailsApplication

and then you can autowire properties by name with this:

import org.springframework.beans.factory.config.AutowireCapableBeanFactory
...

def instance = new XXX(...)

def ctx = grailsApplication.mainContext
ctx.beanFactory.autowireBeanProperties(instance,
      AutowireCapableBeanFactory.AUTOWIRE_BY_NAME, false)

Just as in Spring bean classes or Grails artifact classes, any public property or setter method that corresponds to a bean name in the ApplicationContext will be set with that bean.

Bean Scopes

By default, Spring beans are singletons: only one instance is created, and each time you get the bean from the ApplicationContext (either directly or via dependency injection), you’ll get the same instance. This is a sensible default, because beans often have no mutable state, so they’re safe to share between collaborators and between threads. They can have state, in particular injected dependencies, but as long as this state is initialized early and not changed, it’s not a thread-safety concern. Spring manages creating the instances and wiring dependencies, but without the problems associated with traditional singletons. Of course there are plenty of reasons why a particular bean cannot be a singleton, so beans can have a “scope.”

To receive a new instance from the ApplicationContext each time, set the scope of the bean to prototype. It will still have dependencies injected like singleton beans, but now it can have mutable state, because each caller gets its own copy. Grails controllers are an example of prototype beans; this is to support a rarely used feature inspired by Rails controllers where the controller itself is used as the GSP model when none is specified. Often, when a GSP is used to render a response, the last statement of a controller action is a Map containing the model data to use in the GSP; if you don’t return anything (and don’t call redirect, forward, or chain), then the controller’s fields are used as the model data.

Another supported scope is session. You could use this for shopping carts and other similar patterns, much like a stateful EJB session bean. The first time the bean is requested from the ApplicationContext, it is created and stored in the HTTP session, and subsequent requests return this instance until the session times out or is explicitly invalidated. Separate sessions each get their own instance. A similar scope is request; these are created per request instead of per session, so they’re much shorter lived.

You can also define your own scope by implementing the org.springframework.beans.factory.config.Scope interface and registering it in the BeanFactory:

ctx.beanFactory.registerScope 'myScope', new MyScope()

You can use this in a controller or service class with the scope property; for example:

static scope = 'myScope' // or session/prototype/etc.

For Spring beans that you manually wire in resources.groovy, add the property in the bean definition:

myBean(MyBeanClass) { bean ->
   bean.scope = 'myScope' // or session/prototype/etc.
}

Transactional Services

If you follow the convention for Grails services and create a Groovy class in the grails-app/services folder whose name ends in Service, the class will automatically be registered as a service for you. This means that, by default, it is registered as a Spring bean (whose bean name is the class name with a lowercase first letter), the bean scope is singleton, and all public methods will be transactional. That makes the class a great place to put business logic, especially if it involves database persistence.

You can specify the bean scope of a service with the static scope property; this can be any valid value supported by Spring and the most common are singleton and prototype, and to a lesser extent request and session. The default scope (if none is specified) is singleton.

By default, all public methods in a service are transactional. Older versions of Grails included the line static transactional = true in generated services, but that has been removed, because it’s redundant. You should only set the transactional attribute if you’re disabling transactions—for cases where the service manages business logic but doesn’t write to the database.

The transaction isolation is set to Isolation.DEFAULT; that is, the default settings for your database are used instead of explicitly using read-commited, serializable, etc. The propagation level is Propagation.REQUIRED, which means that, if a transaction was already active before calling a service method, it will be joined and not committed after successfully invoking the method, because it was already started; however, if one isn’t active, it will create one and commit it after invoking the method. There is no timeout configured, the transaction won’t be read-only, and the Exception types that trigger an automatic rollback are the defaults; runtime exceptions and errors trigger rollback and checked exceptions (even though Groovy doesn’t make you catch or rethrow checked exceptions) do not cause a rollback. This last point can be confusing for developers without much experience with Spring or JEE transactions. The logic is that in Java, because you must either catch a checked exception or declare it in the throws clause, you have the opportunity to handle the exception and will decide if the exception merits an explicit rollback. But because you don’t have to catch runtime exceptions or errors, it’s assumed that the transaction should be automatically rolled back for you, to keep state from being inconsistent. Because Spring doesn’t know about Groovy’s exception handling rules, the Java rules apply.

@Transactional

You’re not limited to the default transaction settings or forced to use complex configurations to customize services’ transaction behaviors. Customizing is simple; use the org.springframework.transaction.annotation.Transactional annotation. If you have even one @Transactional annotation, Grails assumes that you’re taking the configuration into your own hands and doesn’t configure the default transaction settings for the class. You can put the annotation at the class level, and/or on individual methods, and you can combine class-scope and method-scope annotations to configure default settings at the class level, but configure overrides for individual methods.

In this example, someMethod will be transactional, inheriting the settings from the class annotation, but someOtherMethod requires that an existing transaction be active:

package com.mycompany

import org.springframework.transaction.annotation.Propagation
import org.springframework.transaction.annotation.Transactional

@Transactional
class SomeService {

   def someMethod() {
      ...
   }

   @Transactional(propagation=Propagation.MANDATORY)
   def someOtherMethod() {
      ...
   }
}

Another approach is to omit the annotation at the class level to support nontransactional methods and to annotate methods directly. In this example, someMethod is not transactional (but won’t trigger an exception if it is called during a transaction), someOtherMethod has the default settings, and yetAnotherMethod requires that a transaction be active already:

package com.mycompany

import org.springframework.transaction.annotation.Propagation
import org.springframework.transaction.annotation.Transactional

class SomeOtherService {

   def someMethod() {
      ...
   }

   @Transactional
   def someOtherMethod() {
      ...
   }

   @Transactional(propagation=Propagation.MANDATORY)
   def yetAnotherMethod() {
      ...
   }
}

Transaction Proxies

Whether you use the default Grails configuration or annotations, the transaction management is implemented by Spring with a proxy. Spring uses the CGLIB library to create a subclass of your service, where each proxied method (all public methods when not using annotations or if the class is annotated, annotated public methods otherwise) is intercepted by the proxy to start or join a transaction (or throw an exception if one isn’t allowed) and then call your implementation code. You can see that this is the case by printing the class name of your injected service, (e.g., println userService.getClass().name); it should look something like this:

com.foo.bar.UserService$$EnhancerByCGLIB$$32cb6433

We can see that the proxy is a runtime-generated subclass of the real bean class by printing its superclass:

println userService.getClass().superclass.name

which should print:

com.foo.bar.UserService

Digging further, we can list all of the interfaces implemented by the proxy:

for (iface in ctx.mathService.getClass().interfaces) {
   println iface.name
}

which should print:

org.springframework.aop.SpringProxy
org.springframework.aop.framework.Advised
net.sf.cglib.proxy.Factory

Unintentionally bypassing the bean proxy

Be careful when calling annotated methods within a service when the annotation settings are different. Because you’re “underneath” the proxy, it’s a direct method call, and any checks that the proxy would have done will be bypassed. For example, if you want to store auditing data in the database, but don’t want a failure there to roll back the transaction, you can do that work in a new transaction by setting the propagation to Propagation.REQUIRES_NEW:

@Transactional
void someMethod(...) {

   // do some work ...

   storeAuditData(...)
}

@Transactional(propagation=Propagation.REQUIRES_NEW)
void storeAuditData(...) {
   //
}

Unfortunately, though, the call to storeAuditData won’t trigger the creation of a second transaction, because it’s a direct call. You can fix this by calling the proxy’s method, and that involves getting access to the Spring bean that represents this service. You can’t just add a dependency injection (def fooService), because that would be circular; instead, if you add a dependency injection for the grailsApplication bean, you can access the ApplicationContext easily from there and get the service from it:

def grailsApplication

@Transactional
void someMethod(...) {

   // do some work ...

   def myProxy = grailsApplication.mainContext.fooService
   myProxy.storeAuditData(...)
}

@Transactional(propagation=Propagation.REQUIRES_NEW)
void storeAuditData(...) {
   //
}

Another more traditional option is to implement the org.springframework.context.ApplicationContextAware interface, but that involves more plumbing code.

An even more automatic fix would be to wire up a getMyProxy() method (and therefore a myProxy property) into the metaclass of all services in BootStrap.groovy:

class BootStrap {

   def grailsApplication

   def init = { servletContext ->

      for (sc in grailsApplication.serviceClasses) {
         sc.clazz.metaClass.getMyProxy = { ->
            grailsApplication.mainContext.getBean(sc.propertyName)
         }
      }
   }
}

or in the doWithDynamicMethods callback in a plugin:

def doWithDynamicMethods = { ctx ->
   for (sc in application.serviceClasses) {
      sc.clazz.metaClass.getMyProxy = { ->
         application.mainContext.getBean(sc.propertyName)
      }
   }
}

and then this call would have the expected effect:

@Transactional
void someMethod(...) {

   // do some work ...

   myProxy.storeAuditData(...)
}

@Transactional(propagation=Propagation.REQUIRES_NEW)
void storeAuditData(...) {
   //
}

Transaction Utility Methods

For complex workflows, it can be helpful to have access to information about the current transaction. Ironically, although services are the best place in Grails to do transactional work, the static withTransaction method that’s available in all domain classes is more useful in this regard, because the method signature has an org.springframework.transaction.TransactionStatus variable. But there’s no direct way to access information about the current transaction in a service. That’s easy to fix though—we can add some transaction utility methods to service metaclasses; for example, in BootStrap.groovy:

import org.springframework.transaction.interceptor.TransactionAspectSupport
import org.springframework.transaction.support.TransactionSynchronizationManager

class BootStrap {

   def grailsApplication

   def init = { servletContext ->
      for (sc in grailsApplication.serviceClasses) {
         def metaClass = sc.clazz.metaClass

         // returns boolean
         metaClass.isTransactionActive = { ->
            TransactionSynchronizationManager.isSynchronizationActive()
         }

         // returns TransactionStatus
         metaClass.getCurrentTransactionStatus = { ->
            if (!delegate.isTransactionActive()) {
               return null
            }
            TransactionAspectSupport.currentTransactionStatus()
         }

         // void, throws NoTransactionException
         metaClass.setRollbackOnly = { ->
           TransactionAspectSupport.currentTransactionStatus().setRollbackOnly()
         }

         // returns boolean
         metaClass.isRollbackOnly = { ->
            if (!delegate.isTransactionActive()) {
               return false
            }
            delegate.getCurrentTransactionStatus().isRollbackOnly()
         }
      }
   }
}

Now you can force the transaction to roll back by calling setRollbackOnly() and, in a workflow that has multiple steps, you can call isRollbackOnly() early in each method before doing expensive work that will only be rolled back, to see if that work makes sense to do.

Bean Life Cycles and Interfaces

In addition to wiring up dependencies between beans, the ApplicationContext is responsible for managing the beans’ life cycles. Two important hooks are the initialization and destruction phases. When you register your own Spring beans in resources.groovy, you can use the org.codehaus.groovy.grails.commons.spring.BeanConfiguration instance (typically a org.codehaus.groovy.grails.commons.spring.DefaultBeanConfiguration) that is the argument of the bean definition closure to set the initMethod and/or the destroyMethod names; for example:

authenticationManager(com.mycompany.myapp.LdapAuthenticationManager) { bean ->
   serverUrl = '...'
   password = '...'
   bean.initMethod = 'init'
   bean.destroyMethod = 'destroy'
}

Most of the time, however, the beans that you create are automatically registered for you by Grails. In that case, you can implement the org.springframework.beans.factory.InitializingBean interface and its afterPropertiesSet method to do initialization work after all dependencies and other properties have been set, and the org.springframework.beans.factory.DisposableBean interface and its destroy method to do work during a clean shutdown; for example:

package com.mycompany.myapp

import org.springframework.beans.factory.DisposableBean
import org.springframework.beans.factory.InitializingBean

class LdapAuthenticationManager implements InitializingBean, DisposableBean {

   ...

   void afterPropertiesSet() {
      // initialization work
   }

   void destroy() {
      // shutdown work
   }
}

Note

Whether you use initMethod or InitializingBean.afterPropertiesSet, because Spring is unaware of the various Grails life cycle phases, you are somewhat limited in what you can do in the initialization phases. In particular, because plugins won’t have initialized yet, you cannot use GORM methods. If you find you cannot do some initialization work because of this, you can inject your bean in BootStrap.groovy and do the work there, because by the time bootstrap classes are called, everything has been configured and is ready to use.

In earlier versions of Grails, the log field was added using runtime metaprogramming, but in Grails 2.0 and higher, it’s injected with an AST transformation (compile-time metaprogramming), so you can use logging in either callback method.

Bean Postprocessors

Bean (and BeanFactory and BeanDefinitionRegistry) postprocessors provide a powerful approach to customizing Spring beans. They’re particularly useful to reconfigure beans contributed by third-party JARs or plugins where you can’t (or shouldn’t) edit the code. Instead, you can hook into the construction process and customize one or more beans at runtime, changing or adding properties, the bean implementation class, and other attributes and settings.

The most common interface to use is org.springframework.beans.factory.config.BeanPostProcessor, which has two methods, postProcessBeforeInitialization and postProcessAfterInitialization. You can do what you want with each, but typically postProcessBeforeInitialization works with class metadata like annotations, because the instance has been created but it isn’t fully initialized yet. It’s common to return a proxy for the real instance from postProcessAfterInitialization, although you can also just reconfigure the initialized instance with updated properties.

You can also create an org.springframework.beans.factory.config.BeanFactoryPostProcessor, which has one method, postProcessBeanFactory. This takes a single argument: a ConfigurableListableBeanFactory that you can use to customize a BeanDefinition from its getBeanDefinition method, or loop through all of the beans using the names from the getBeanDefinitionNames method. Your postprocessor will be called after the bean factory is partially initialized but before beans have been instantiated. This gives you a chance to modify the BeanDefinition instances that will be used to define the actual beans. You can add, remove, or change bean properties and even the class that will be instantiated.

The org.springframework.beans.factory.support.BeanDefinitionRegistryPostProcessor interface extends BeanFactoryPostProcessor and has one method, postProcessBeanDefinitionRegistry, where you can add or remove BeanDefinition instances in the BeanDefinitionRegistry.

To add a postprocessor, implement whichever interface(s) you want in a class in src/groovy or src/java and register it as a bean (using any name you want, because it’s not particularly relevant) in resources.groovy. Spring will see that it implements one of the interfaces and will use it as a postprocessor, calling the methods at the appropriate points in the construction of the ApplicationContext:

import com.mycompany.myapp.MyPostProcessor
beans = {
   myPostProcessor(MyPostProcessor)
}

Note

The cloud-foundry and heroku plugins both provide runtime reconfiguration of the JDBC DataSource, NoSQL connection information, and so on, using this approach. This keeps your application highly decoupled from the hosting location, because a bean postprocessor detects the environment variables that Cloud Foundry and Heroku make available, and transparently reconfigures the appropriate Spring beans for you. You can see the source of the shared base class that each plugin extends to provide provider-specific settings discovery here.

A Groovier Way

You can also customize a BeanDefinition in the doWithSpring closure in a plugin. The delegate of the closure is the active grails.spring.BeanBuilder that Grails uses to register beans in the ApplicationContext that are defined by the builder’s DSL. You can use the getBeanDefinition method to retrieve a previously defined bean definition (typically an org.springframework.beans.factory.support.GenericBeanDefinition) and modify its attributes:

def doWithSpring = {
   def beanDef = getBeanDefinition('someBeanName')
   beanDef.beanClass = NewClass
   beanDef.propertyValues.add('order',
   application.config.plugin?.rendering?.order ?: [])
}

Note that because this runs during your plugin’s initialization, plugin loading order is important; the only bean definitions that will be available are those configured by plugins that have already initialized. You can use the loadAfter plugin descriptor attribute to configure this.

Bean Aliases

Spring allows bean aliases where an alternate name is registered in addition to the real name of a bean. You can use this when you have multiple implementations of a bean and choose one via configuration at startup—for example, per-environment or some other rule. This is partially broken in Grails before 2.1 in that, before version 2.1, you could register aliases but only to beans in the same plugin or resources.groovy. As of version 2.1 though, all aliases work regardless of the location of the alias and bean definitions.

This works the same way in a plugin’s doWithSpring as in resources.groovy, because in both cases, the closure’s delegate is the BeanBuilder. You can access the RuntimeSpringConfiguration with the getSpringConfig method and call addAlias on that; for example:

import grails.util.Environment

beans = {

   String realBeanName

   switch (Environment.current) {
      case Environment.TEST:
         realBeanName = 'testCardProcessingService'
         break
      case Environment.PRODUCTION:
         realBeanName = 'productionCardProcessingService'
         break
      default: // Environment.DEVELOPMENT, custom envs
         realBeanName = 'mockCardProcessingService'
         break
   }

   springConfig.addAlias 'cardProcessingService', realBeanName
}

Now, when a controller or other artifact that supports dependency injection injects the cardProcessingService bean, it will get the correct one depending on the current running environment. This has the benefit of centralizing the logic and not polluting the application code with logic to determine in each case which bean to use.

Note

The cache plugin registers the alias cacheOperationSource for the bean that Spring autoregisters as org.springframework.cache.annotation.AnnotationCacheOperationSource#0, which cannot be used with Grails dependency injection using the standard def beanName pattern.

Internationalization

Grails has first-class support for internationalization with the .properties files in the grails-app/i18n folder. All generated controllers, GSPs, and layouts are fully internationalized with no hardcoded strings; instead, strings are resolved from the message bundles defined in the .properties files using the message tag and the current Locale. In addition, domain class validation errors are internationalized the same way, using the i18n message bundles. This can make the code harder to read (especially if the message codes are cryptic or not intuitive), but it makes displaying your site in another language much simpler, because you just need to ensure that all English messages have corresponding translated messages for your supported languages.

This is all enabled under the hood by the use of the messageSource bean, an implementation of the org.springframework.context.MessageSource interface. In a Grails application, this will be a PluginAwareResourceBundleMessageSource that supports loading messages from the application as well as from installed plugins and supports reloading in the development environment. You can work directly with the messageSource bean using dependency injection like with any Spring bean: def messageSource. Often it’s easier to use the message tag because tags can conveniently be called in controllers. But, in services or other classes, where it’s impractical to call a taglib, just use the messageSource bean.

Resources

Spring has an abstraction for low-level resources with its org.springframework.core.io.Resource and org.springframework.core.io.ResourceLoader interfaces. There are several concrete Resource implementations, including UrlResource, ClassPathResource, FileSystemResource, ServletContextResource, InputStreamResource, and ByteArrayResource. It rarely matters what the concrete class is though, because you can use the methods exists(), getInputStream(), getURL(), and so on.

For example, consider a configuration file that you put in the web-app/WEB-INF folder, data.xml. This is safe from public viewing, because the container blocks access to all files in WEB-INF. So how do you read the contents of the file at runtime? A naive approach that works in development mode is:

new File('web-app/WEB-INF/data.xml').text

This won’t work in a deployed WAR for two reasons. One is that there is no web-app folder, and the other is that the WAR may not be expanded onto the filesystem depending on which container you use, so there may be no File access at all even if you “fix” the path. But you certainly wouldn’t want to have brittle logic that computes the file path depending on how the application is running.

This method in ResourceLoader looks promising:

Resource getResource(String location);

So how do we access a ResourceLoader in Grails? The ApplicationContext implements the interface and will usually be the most convenient way to manage resources. Getting access to the ApplicationContext can be done a few different ways; the most convenient is to add a dependency injection for the grailsApplication bean (def grailsApplication) because grailsApplication.mainContext resolves to the ApplicationContext; you can also implement ApplicationContextAware.

Then it’s as simple as executing:

String xml = ctx.getResource('WEB-INF/data.xml').inputStream.text

and there’s no dependence on any particular environment or logic to compute various paths to the file, depending on how the application is being run, because Spring abstracts that away. If you run:

println ctx.getResource('WEB-INF/data.xml').getClass().name

you’ll see that the implementation class is org.springframework.web.context.support.ServletContextResource, and running:

ctx.getResource('WEB-INF/data.xml').file.path

will print something like:

/path/to/appname/web-app/WEB-INF/data.xml

when running under run-app and:

/usr/local/apache-tomcat-7.0.29/webapps/appname/WEB-INF/data.xml

when running as a WAR deployed to Tomcat (assuming Tomcat is configured to explode WARs).

Resource Dependency Injection

A more automatic approach would be to use dependency injection to let Spring inject the resource into one of your beans, rather than explicitly pulling it like we have been. If you move the file from the WEB-INF folder to either grails-app/conf or src/java, it will be copied into the classpath, so we can access it as a classpath resource. Consider this simple class:

package com.mycompany.myapp

import org.springframework.core.io.Resource

class FooManager {

   Resource xmlFile

   // class methods
}

If we wire this class up as a bean in resources.groovy, for example:

import com.mycompany.myapp.FooManager

beans = {

   fooManager(FooManager) {
      xmlFile = 'classpath:data.xml'
   }
}

then the resource will be discovered and injected into the bean. Now it will be an instance of org.springframework.core.io.ClassPathResource, and accessing the content of the file is as simple as:

String xml = xmlFile.inputStream.text

inside any of the methods in FooManager. You can even go further and specify the type as a File:

package com.mycompany.myapp

class FooManager {

   File xmlFile

   // class methods
}

and then the content will be available as:

String xml = xmlFile.text

ResourceLocator

As of Grails 2.0, there is also another option for finding resources: the org.codehaus.groovy.grails.core.io.ResourceLocator interface and its implementations. This has two primary methods: Resource findResourceForURI(String uri) and Resource findResourceForClassName(String className). The advantage of using ResourceLocator over the Spring option is that ResourceLocator implementations are Grails classes and are aware of the structure of application and plugin paths and can also access contents of binary plugins.

To use this, get a reference to the grailsResourceLocator bean, typically using dependency injection (e.g., def grailsResourceLocator). Then you can conveniently access files when running locally using run-app or when deployed as a WAR (e.g., getting the content of a JavaScript file provided by the JQuery plugin, without having to know anything about where the actual file is located):

def resource = grailsResourceLocator.findResourceForURI
    ('js/jquery/jquery-1.8.3.min.js')
String jqueryJs = resource.inputStream.text

or an application file you have placed in the WEB-INF folder:

def resource = grailsResourceLocator.findResourceForURI('WEB-INF/someDataFile.xml')

Data Binding and Validation

Data binding and validation help make integrating HTTP request data with domain classes much easier in Grails. Much of the core implementation is handled by Spring, with Grails adding a layer on top to make the integration more direct and add in special handling.

Data Binding

Spring provides several implementations of JavaBean PropertyEditors to convert Strings (typically from web requests) to numbers, dates, or anything that has a string form that can be converted. These are used by the org.codehaus.groovy.grails.web.binding.GrailsDataBinder, which extends the underlying Spring data binding implementation to add Grails-specific hooks, such as working with the params map in controllers, being aware of the constraints property in domain classes, and guarding against changing properties such as metaClass, id, and version.

Spring and Grails register several property editors, and you can register your own by registering a CustomEditorConfigurer bean (a bean postprocessor), giving it a list of PropertyEditorRegistrar instances referencing your editors. This is somewhat cumbersome though, but in Grails 2.3 the data binding implementation will be heavily refactored to retain the binding features, but add several new ones and significantly simplify the process for adding custom binding approaches.

Validation

In traditional Spring applications, it is common to create validators for the app’s DAOs, and Spring has an org.springframework.validation.Validator interface to standardize the behavior. But there are no concrete implementations of the interface, because validation is very domain-specific. Although you’re probably unaware of it, Grails creates an instance of Validator for each domain class; if you loop through the ApplicationContext beans, you’ll see that for a com.foo.bar.Person domain class there will be a com.foo.bar.PersonValidator bean (an instance of org.codehaus.groovy.grails.orm.hibernate.validation.HibernateDomainClassValidator, if you’re using Hibernate) along with a com.foo.bar.Person bean (a “prototype” bean that is used in the overridden constructor to create instances and support bean autowiring), a com.foo.bar.PersonPersistentClass bean, and a com.foo.bar.PersonDomainClass bean.

Validation problems are represented by the org.springframework.validation.Errors interface, typically a grails.validation.ValidationErrors instance, which extends a Spring implementation that provides most of the functionality. An Errors instance is wired into all domain classes as the errors property, making it very convenient to access after performing validation checks (either directly with the validate method or indirectly with the save method). It will contain information about what went wrong, including the original invalid values and error codes for displayable messages. This gets coupled with the Spring and Grails support for i18n message bundles (under the grails-app/i18n directory) to allow you to display human-readable validation messages and also support localized versions as needed.

Database Persistence

Typically, we use GORM and Hibernate to manage database persistence in a Grails application, although many apps now use NoSQL datastores in addition to or instead of relational databases. Under the hood, the Hibernate integration is managed by Spring, from the org.springframework.orm.hibernate3.LocalSessionFactoryBean factory bean (in Grails, it’s the org.codehaus.groovy.grails.orm.hibernate.ConfigurableLocalSessionFactoryBean subclass) that’s used to configure org.hibernate.SessionFactory instances to the org.springframework.orm.hibernate3.HibernateTransactionManager implementation of the org.springframework.transaction.PlatformTransactionManager interface that abstracts away the implementation details of transaction management (this is also a Grails-specific subclass, org.codehaus.groovy.grails.orm.hibernate.GrailsHibernateTransactionManager).

Thread-Local Holders

One significant feature of the Spring/Hibernate integration is the seamless access of active persistence objects. It would be cumbersome to explicitly open a Hibernate Session or start a transaction and have to pass one or more related objects from method to method, so Spring stores various objects (the active transaction, the current Hibernate session, and so on) in ThreadLocal scope, because web requests are handled per thread. So it’s easy for code that’s aware of this pattern to access the current transaction or Hibernate session (or just know if one is active) by using the org.springframework.transaction.support.TransactionSynchronizationManager and org.springframework.orm.hibernate3.SessionFactoryUtils helper classes.

This is further helped by the org.codehaus.groovy.grails.orm.hibernate.support.GrailsOpenSessionInViewInterceptor instance, which implements the org.springframework.web.context.request.WebRequestInterceptor interface that Grails registers to intercept all controller requests. This interface has callbacks for doing work before a controller action starts, after it does its work, and after the view is rendered. This should sound familiar if you’ve used filters before, because they are also managed by a WebRequestInterceptor. The GrailsOpenSessionInViewInterceptor opens a Session at the start of all controller requests and registers it in thread-local scope (in an org.springframework.orm.hibernate3.SessionHolder keyed by the owning SessionFactory). Then, after the request, it flushes and closes the Session.

So, for the entire duration of the request, there is always an active Session available. This is important for a few reasons. The Hibernate implementation of GORM uses an org.springframework.orm.hibernate3.HibernateTemplate under the hood to execute most queries. Criteria queries are relatively thin wrappers around the Hibernate Criteria feature, and where queries, dynamic finders, and other GORM methods are converted to Criteria queries or call an applicable Hibernate Session method. HibernateTemplate uses SessionFactoryUtils.getSession() to find or create a Session. If one is active, it uses it and doesn’t close it, because that’s the responsibility of whatever code opened it (most likely, GrailsOpenSessionInViewInterceptor). If one isn’t, it creates one and closes it when finished. This is why lazy-loaded collections and entities fail to load when a query executes in a new thread; the instances retrieved become disconnected when the session closes. But, when the query runs in the request’s thread, the session is still active after the query, so lazy loading works. The plugins that enable asynchronous processing (Quartz, GPars, and Executor) all implement patterns similar to OpenSessionInView, because they support running in new threads.

JdbcTemplate

It is usually most convenient to use groovy.sql.Sql when executing SQL queries in Groovy, but Spring has a utility class with many of the same features, JdbcTemplate. You give it a reference to a DataSource (typically, in the constructor) and it handles most of the gory details of getting a Connection, Statement, and ResultSet for you (and closing them when it is finished), and has smart error handling which converts checked SQLExceptions into a rich hierarchy of unchecked exceptions. The code ends up being a bit more verbose than using groovy.sql.Sql but far more compact than the equivalent direct JDBC code:

import misc.Person
import org.springframework.jdbc.core.RowMapper
import org.springframework.jdbc.core.JdbcTemplate
import java.sql.ResultSet
import java.sql.SQLException

def dataSource = ctx.dataSource

def template = new JdbcTemplate(dataSource)

long id = ...

Person person = template.queryForObject(
    "select first_name, initial, last_name from person where id = ?",
    [id] as Object[],
    new RowMapper<Person>() {
        Person mapRow(ResultSet rs, int rowNum) throws SQLException {
            def p = new Person(firstName: rs.getString('first_name'),
                               initial: rs.getString('initial'),
                               lastName: rs.getString('last_name'))
            p.id = id
            p
        }
    }
)

Other Database Support

Although they’re less often used (especially in Grails), Spring does have support for JDO with the org.springframework.orm.jdo.JdoTemplate and org.springframework.orm.jdo.support.JdoDaoSupport classes, JPA with the org.springframework.orm.jpa.JpaTemplate and org.springframework.orm.jpa.support.JpaDaoSupport classes, and iBATIS (2.x) SQL Maps.

Spring MVC

Nearly all Grails applications have a web frontend, and most of the time, this is implemented with controllers. These are core artifacts in the grails-app/controllers folder. There are several convenient conventions associated with controllers; classes in the controllers folder are automatically registered as controllers, public closures and methods are automatically registered as actions, simply returning a Map from an action renders the GSP corresponding to that controller and that action, using the Map as the data model in the view, and the "/$controller/$action?/$id?" { ... } URL mapping entry (added by default in the generated UrlMappings.groovy file) ensures that actions are automatically available externally using a REST-like URL scheme.

Your classes in grails-app/controllers don’t implement the Spring Controller interface (directly or via something funky like an AST transformation) and don’t extend a Controller base class; instead, Grails uses one facade Controller to handle all requests: org.codehaus.groovy.grails.web.servlet.mvc.SimpleGrailsController. This is registered as the mainSimpleController bean. This delegates most of the work to the grailsControllerHelper bean, an instance of MixedGrailsControllerHelper which finds the action method or closure and invokes it, returning an org.springframework.web.servlet.ModelAndView that you may be familiar with if you’ve worked with Spring MVC in a traditional Spring application.

In addition, Grails invokes interceptors before and after controller actions. These come from various sources, including explicitly created HandlerInterceptor classes such as GrailsOpenSessionInViewInterceptor (via an org.springframework.web.servlet.handler.WebRequestHandlerInterceptorAdapter adapter) and org.codehaus.groovy.grails.web.i18n.ParamsAwareLocaleChangeInterceptor (which extends Spring’s org.springframework.web.servlet.i18n.LocaleChangeInterceptor), but also Grails filters and controller interceptors (beforeInterceptor and afterInterceptor closures defined in controller classes).

Filters

Filters in Grails are somewhat misleadingly named, because it seems like they’re Servlet filters, but they’re implemented with a HandlerInterceptor (indirectly), so they only work with controller requests. For each filter class, Grails creates an adapter instance of org.codehaus.groovy.grails.plugins.web.filters.FilterToHandlerAdapter to integrate it into the filters list. FilterToHandlerAdapter implements the HandlerInterceptor interface and extracts information from the DSL that developers use to define the filtering rules in an XXXFilters.groovy file (the patterns for which URIs, controllers, and actions apply; the before, after, and afterView closures; and so on) to use when the various interface methods are called. This way, we can take advantage of the filter conventions so there’s less plumbing work involved while still taking advantage of the Spring integration.

Controller interceptors look a lot like filters (although there are only the before and after phases, no “after view”) but they’re not implemented with a HandlerInterceptor. Because they only apply to the controller where they’re defined, the logic is applied per request, in AbstractGrailsControllerHelper.

Note

If you need to intercept more than just controller requests, you can create a class that implements javax.servlet.Filter (or extend an existing base class like org.springframework.web.filter.OncePerRequestFilter) and add it to web.xml like in any application. This can be done in plugins in the doWithWebDescriptor block, or in an application by running the install-templates script and editing src/templates/war/web.xml.

Using Spring MVC Controllers

It’s been possible to use Spring MVC controllers in Grails since version 1.2; before that, it was possible with the springmvc plugin. The process is fairly straightforward; create your controller classes in the src/java or src/groovy folder and add an org.springframework.stereotype.Controller annotation. Grails doesn’t autodiscover the annotated classes though; you need to add the relevant packages to the grails.spring.bean.packages list property in Config.groovy; for example:

grails.spring.bean.packages = ['com.mycompany.myapp.billing',
                               'com.mycompany.myapp.card.api']

When you create the classes, use the same techniques that you would in a traditional Spring application; for example, annotating an action method with org.springframework.web.bind.annotation.RequestMapping:

@RequestMapping("/mvc/hello.dispatch")
public ModelMap handleRequest() {
   return new ModelMap()
      .addAttribute("text", "some text")
      .addAttribute("cost", 42)
      .addAttribute("config",
          grailsApplication.getConfig().flatten()));
}

One unfortunate aspect of the integration is that all RequestMapping URI values must end in .dispatch. You can make this more natural by adding entries in UrlMappings.groovy; for example:

class UrlMappings {

   static mappings = {
      ...

      "/mvc/hello"(uri:"/mvc/hello.dispatch")

      "/mvc/other"(uri:"/mvc/other.dispatch")
   }
}

These controller classes will become standard Spring beans, so they’re candidates for dependency injection. Use the org.springframework.beans.factory.annotation.Autowired annotation on fields in Groovy classes:

@Autowired
def grailsApplication

and on setters in Java:

private GrailsApplication grailsApplication;

@Autowired
public void setGrailsApplication(GrailsApplication app) {
   grailsApplication = app;
}

You can also use the javax.inject.Inject annotation; for example, using constructor injection:

private GrailsApplication grailsApplication;

@Inject
public FooController(GrailsApplication app) {
   grailsApplication = app;
}

Remoting

Spring has support for remoting using several protocols. The Grails remoting plugin implements this support for remote method invocation (RMI), Hessian (Caucho’s lightweight binary HTTP-based protocol), Burlap (another protocol from Caucho, which uses XML), and Spring’s HTTP invoker (implemented by Java serialization via HTTP).

The plugin makes it simple to provide remote access to a Grails service. The service must implement an interface, because it will be used to create a proxy that clients use to make the remote calls. For example, consider this simple interface (in this case, a Groovy version in src/groovy, but it can also be written in Java or from a JAR file):

package test.remoting

interface Math {
   int add(int i1, int i2)
   int multiply(int i1, int i2)
}

Creating the remoted service only requires two things: you have to implement the interface, and you have to add a static expose property containing a list of one or more protocol names to expose (any of burlap, hessian, httpinvoker, and rmi). This service (in grails-app/services like any Grails service) exposes all four protocols:

package test

import test.remoting.Math

class MathService implements Math {

   static expose = ['hessian', 'rmi', 'httpinvoker', 'burlap']

   int add(int i1, int i2) {
      i1 + i2
   }

   int multiply(int i1, int i2) {
      i1 * i2
   }
}

The plugin adds a servlet (an org.springframework.web.servlet.DispatcherServlet) for each protocol and an org.springframework.web.servlet.HandlerMapping to route to them, and registers a proxy (using an org.springframework.aop.framework.ProxyFactoryBean and an org.springframework.aop.target.HotSwappableTargetSource) in the ApplicationContext for each remoted service (in this example, MathServiceProxy and MathServiceTargetSource beans). In addition, for each exposed protocol, it registers an org.springframework.remoting.support.RemoteExporter subclass (e.g., an org.springframework.remoting.caucho.HessianServiceExporter for the Hessian protocol) bean (in this example, burlap.MathService, hessian.MathService, httpinvoker.MathService, and rmi.MathService).

Client Access

The most convenient way for clients to connect to your exposed services is to use Spring’s client support for the various protocols, and Grails applications using the remoting plugin can create services that connect to remoted services just as easily as exporting the remoted services in the server application. All that’s involved is creating a service with the same name as the remoted service (the package can be different) and adding a remote property defining connection information.

The service shouldn’t implement the interface that the remote service exposes, but it must be available in the classpath; it would be a good idea to create a third Java/Groovy project containing all of your remoted interfaces and any custom classes used in method calls and adding the generated JAR file to the dependencies of the server and client applications. This is because the plugin just uses the service as a container for the remote property and replaces it in the ApplicationContext with a proxy (an org.springframework.remoting.support.RemoteAccessor subclass such as an org.springframework.remoting.caucho.BurlapProxyFactoryBean for the Burlap protocol) bean that does implement the interface and makes the remote calls for you.

The remote property is a Map and specifies the interface to implement (under the iface key) and the remote protocol to use (under the protocol key); the protocol value can be one of the four supported values that are valid in the expose list in the remoted service class. In addition, you must specify the connection information. If you specify the full URL string under the url key it will be used; otherwise, the host, port, and webcontext values are used to build a URL. host defaults to localhost if not specified, “port” defaults to 1199 when using RMI or 8080 otherwise, and webcontext defaults to the root context.

For example, this service will create a proxy client using Hessian:

package client

class MathService {
   static remote = [
      protocol: 'hessian',
      iface: test.remoting.Math,
      host: 'my.server.com',
      port: 8888,
      webcontext: 'remote'
   ]
}

This service will create a proxy client using Burlap:

package client

class MathService {
   static remote = [
      protocol: 'burlap',
      iface: test.remoting.Math,
      host: 'my.server.com',
      port: 8888,
      webcontext: 'remote'
   ]
}

This service will create a proxy client using HttpInvoker:

package client

class MathService {
   static remote = [
      protocol: 'httpinvoker',
      iface: test.remoting.Math,
      host: 'my.server.com',
      port: 8888,
      webcontext: 'remote'
   ]
}

Finally, this service will create a proxy client using RMI:

package client

class MathService {
   static remote = [
      protocol: 'rmi',
      iface: test.remoting.Math,
      host: 'my.server.com',
      port: 10199,
      webcontext: 'remote'
   ]
}

JMS

Using the Java Message Service (JMS) is a common way to add synchronous and asynchronous messaging to an application, to make the application components more loosely coupled and reliable. Spring adds support for sending and receiving messages by using JMS topics and queues. It is common to use the org.springframework.jms.core.JmsTemplate helper class, which has features similar to the JdbcTemplate JDBC helper. It manages connecting to the JMS ConnectionFactory, provides helper methods to abstract away the rather cumbersome JMS API, and also converts checked JMSExceptions to a hierarchy of runtime exceptions.

EJBs

Enterprise JavaBeans (EJBs) are rarely used in Grails applications, because Spring and Grails provide lightweight replacements for most of the useful features of EJB; for example, Hibernate and GORM (and now NoSQL support) instead of Entity beans, Grails services instead of stateless and stateful session beans, and the jms plugin to use JMS instead of message-driven beans. But, if you have existing EJBs that provide useful services, there’s no need to rewrite them unless you also need the benefits of deploying on a lightweight container instead of a full application server, and Spring has several integration hooks to make EJB access transparent to your code.

JMX

There are plenty of highend monitoring solutions for web applications, but JMX remains as a simple and straightforward solution for monitoring and configuring aspects of an application using tools like JConsole (which is included with all JDK installs). Spring offers integration with JMX through various helper classes such as org.springframework.jmx.export.MBeanExporter and others.

It shouldn’t be much of a surprise that there’s a Grails plugin to make using JMX even easier: the jmx plugin significantly reduces the amount of configuration you need to do.

It creates a javax.management.MBeanServer by using the Spring org.springframework.jmx.support.MBeanServerFactoryBean factory bean, and automatically registers a Log4j and an org.hibernate.jmx.StatisticsService MBean (the latter only if the Hibernate plugin is installed). In addition, it exposes any Grails service that declares static expose = ['jmx'] and any Spring beans listed in the grails.jmx.exportBeans attribute in Config.groovy as MBeans. All public setters and getters are exposed except for any that you exclude using the plugin’s configuration.

See the jmx plugin documentation for more details.

Email

Many applications need to send email, and the JavaMail API provides a robust implementation of this. It’s not the easiest API to use, but luckily, the Spring support for sending email using JavaMail makes it a lot more straightforward, and the Grails mail plugin makes it painless to send plain-text and HTML emails, add attachments, and even use GSP templates.

See the mail plugin documentation for more details.

Cache Abstraction

The cache abstraction feature was added to Spring in version 3.1, so applications using Grails 2.0 or higher can use it. This is an API for caching method calls, typically those that are slow or resource-intensive but that return the same result given the same parameter values.

This has been implemented in Grails in plugins; there is a “core” cache plugin that provides an in-memory implementation, and extension plugins including cache-ehcache and cache-redis that use Ehcache and Redis, respectively, to implement the caching logic.

Method call caching is supported in Spring beans (typically Grails services) by using the Spring org.springframework.cache.annotation.Cacheable, org.springframework.cache.annotation.CachePut, and org.springframework.cache.annotation.CacheEvict annotations.

The core plugin also has annotations with the same names in the expectation that we can add additional parameters above what Spring supports in the future. The plugins also add web-tier caching for controller actions (for annotated controller methods, but not closures) and GSPs, using the <cache:block> and <cache:render> tags.

See the documentation for the caching plugins for more details about how to use them in your applications.

Get Programming Grails now with the O’Reilly learning platform.

O’Reilly members experience books, live events, courses curated by job role, and more from O’Reilly and nearly 200 top publishers.