By- Saurabh Dixit Grails Plugins Resources Restful API Integration Tests What’s new in grails 2.0 What’s new in grails 2.1 What’s new in grails 2.2 How to upgrade plugins Grails Plugins: Install Grails plugins Create a new plugin Use custom plugin in multiple applications Installing Plugin Install-plugin spring-security-core Using s2-quick start Configuration in config file: import grails.plugins.springsecurity.SecurityConfigType; grails.plugins.springsecurity.securityConfigType = SecurityConfigType.InterceptUrlMap grails.plugins.springsecurity.interceptUrlMap = [ '/':[ 'ROLE_SUPER_ADMIN', 'ROLE_ADMIN', 'ROLE_USER' ], '/login/**':[ 'IS_AUTHENTICATED_ANONYMOUSLY' ], '/logout/**':[ 'IS_AUTHENTICATED_ANONYMOUSLY' ], '/register/**':[ 'IS_AUTHENTICATED_ANONYMOUSLY' ], '/userInfo/**':[ 'ROLE_SUPER_ADMIN', 'ROLE_ADMIN', 'ROLE_USER' ] Including resources - using tags: Declaring modules: You can declare resource modules in both applications and plugins. There are a couple of ways of doing this, but the most common approach is to add one or more dedicated artifacts to the project. For an application this might be grailsapp/conf/ApplicationResources.groovy. modules = { core { resource url: 'js/core.js', disposition: 'head' resource url: 'js/ui.js' resource url: 'css/main.css' resource url: 'css/branding.css' resource url: 'css/print.css', attrs: [media: 'print'] } utils { dependsOn 'jquery' resource url: 'js/utils.js' } forms { dependsOn 'core', 'utils' } } resource url: 'css/forms.css' resource url: 'js/forms.js' "core", "utils" and "forms" are the names of our application modules. You can also see that the "utils" module depends on "jquery“ If we look a bit deeper into the above module definitions, we can see that individual resources are declared within a module using "resource" plus a URL. This URL is the location of the resource relative to the web-app directory in your project. If you wish, you can also add extra attributes for fine-grained control of resources, in particular via the "disposition" setting. There are two standard dispositions: "head", meaning that a resource goes inside the <head> element, and "defer“. By default, CSS files have a disposition of "head" while Javascript files use "defer" Including resources in a page As you know, you previously had to declare all your CSS and Javascript links explicitly in your layouts and views. So how does this change with the Resources plugin? Instead of putting in links to individual resources, you declare which modules your page requires, which makes for much conciser <head> blocks. In addition, you specify where in the page the resource links should go. Here's an example of a very simple layout using Resources: <html> <head> ... <r:require modules="common, jquery"/> <r:layoutResources/> </head> <body> ... <r:layoutResources/> </body> </html> <r:require> tag tells Grails which static resources to include in the page <r:layoutResources> tags specify where the links should go. You should have two <r:layoutResources> tags: one in <head> and the other in <body>. Any resource with a disposition of "head" will go where the first one is, while those with a disposition of "defer" will be inserted at the second's location. Ad-hoc resources The Resources plugin calls inline images and scripts "ad-hoc resources". These typically aren't declared in modules and are simply processed as and when they are encountered in the page. A standard inline image link looks something like: <img src="${resource(dir:'images',file:'grails_logo.p ng')}" ... /> Adding resources on the layout->main <r:require modules=" bootstrap, bootstrapNavigation, validationEngine,maskedInput, smartPagination, jqueryTmpl, jqueryUi, jquery, toolTip " /> <g:layoutHead /> <r:layoutResources /> Adding Layout file to view: <g:applyLayout name="main" /> In this way you need not to include resources on every view Web services are all about providing a web API onto your web application and are typically implemented in either REST or SOAP. REST: Using a RESTful solution ▪ The first step in creating an API for an application is deciding what it should allow clients to do. ▪ After all, if a feature isn’t available in the API, a client can’t use it. ▪ Working out what should go into the API isn’t always an easy task, but during development you have scope to experiment. Once the API is published, that’s it. You have to avoid changes that will disrupt those software clients that rely on it. Adding elements to an API often causes fewer problems than changing or removing existing elements. A good strategy is to start minimally and grow the API as required. REST is not really a technology in itself, but more an architectural pattern. REST is very simple and just involves using plain XML or JSON as a communication medium, combined with URL patterns that are "representational" of the underlying system, and HTTP methods such as GET, PUT, POST and DELETE. Def handlePosts = { if (request.method == "GET") { ... } else if (request.method == "POST") { ... } } Each HTTP method maps to an action type. For example GET for retrieving data, PUT for creating data, POST for updating and so on. In this sense REST fits quite well with CRUD. URL patterns: The first step to implementing REST with Grails is to provide RESTful URL mappings: static mappings = { "/product/$id?"(resource:"product") } This maps the URI /product onto a ProductController. Each HTTP method such as GET, PUT, POST and DELETE map to unique actions within the controller as outlined by the table below: Method Action GET show PUT update POST save DELETE delete You can alter how HTTP methods are handled by using URL Mappings to map to HTTP methods: "/product/$id"(controller: "product") { action = [GET: "show", PUT: "update", DELETE: "delete", POST: "save"] } However, unlike the resource argument used previously, in this case Grails will not provide automatic XML or JSON marshalling unless you specify the parseRequest argument: "/product/$id"(controller: "product", parseRequest: true) { action = [GET: "show", PUT: "update", DELETE: "delete", POST: "save"] } Issuing a request with a method other than GET or POST from a regular browser is not possible without some help from Grails. When defining a form you can specify an alternative method such as DELETE: <g:form controller="book" method="DELETE"> .. </g:form> Grails will send a hidden parameter called _method, which will be used as the request's HTTP method. Another alternative for changing the method for nonbrowser clients is to use the XHTTP-Method-Override to specify the alternative method name. XML Marshalling – Reading: The controller can use Grails' XML marshalling support to implement the GET method: import grails.converters.XML class ProductController { def show() { if (params.id && Product.exists(params.id)) { def p = Product.findByName(params.id) render p as XML } else { def all = Product.list() render all as XML } } .. } If there is an id we search for the Product by name and return it, otherwise we return all Products. This way if we go to /products we get all products, otherwise if we go to /product/MacBook we only get a MacBook. Using firefox Poster addon: Install poster plugin on the firefox, and then find it on the tools tab, and then you will be able to send http requests to your application and test your rest API requests and responses. 1. Unit testing: 2. Functional Testing 3. Integration Testing Unit Testing: Why are we starting with unit tests? But as you’ll see later, you can also use Grails integration tests for “unit testing” if you want. There are two primary advantages of unit tests over integration tests: ▪ They’re quicker to run. ▪ You can run them from within your IDE. Useful assertions available to your test cases: assertEquals(expected, actual) Compares two values or objects for equality using the equals() method assertTrue(value) Checks that the given value is true after being coerced to a Boolean assertFalse(value) Checks that the given value is false after being coerced to a Boolean assertNull(value) Checks that the given value is null assertNotNull(value) Checks that the given value is not null assertSame(expected, actual) Checks that two objects are the same instance assertArrayEquals(expected, actual) Compares two arrays for equality, checking that they have exactly the same elements shouldFail(type, closure) Checks that the given closure throws an exception of the given type, or any exception if type is omitted Who are you mocking? The process of mocking involves providing fake versions of classes or methods that can be used in place of the real implementations. The cool thing is that you can control the behavior of the mock object or method, so you can pass known data to the object under test. Mocking can be used at any level of testing, but it’s most commonly associated with unit tests. Many of the methods provided by GrailsUnitTestCase are used to mock the dynamic properties and methods that would normally be injected into classes by Grails. All of the mock*() methods provided by GrailsUnitTestCase use metaclass programming to add mock properties, methods, and objects. That means you can add your own or override the existing ones to fine-tune the behavior. In addition, the mock validation performs real Spring databinding, so the errors property is a real instance of Spring’s Errors interface. This allows you to check for multiple constraint violations on a single field. Integration Testing: Where unit tests are about testing individual, atomic units of functionality (like classes and their methods), integration tests are designed to test larger parts of an application, such as a controller and its dependencies together. The main focus is on ensuring that the units work together correctly—that they integrate properly. In Grails, integration tests appear on the surface to be unit tests. In fact, if you create a new integration test with this command, grails create-integration-test Book The fundamental difference is that integration tests run inside a full Grails environment, with a running database and all those dynamic methods and properties that you’re used to. You don’t have to mock any of them. For all intents and purposes, the tests run against a real instance of your application. The main thing missing is the servlet container, the lack of which has certain repercussions. Here is a summary of what works and what doesn’t: All plugins that don’t exclude the test environment are loaded. BootStrap is executed. Spring application context is fully populated. Domain classes work against a live database (an in-memory HSQLDB, by default). All dynamic methods and properties are available. Mock versions of the servlet request, response, and session are used. No Grails or servlet filters are executed. URL mappings have no effect. Views can’t be tested. Under the hood: Each integration test is run inside a transaction that’s rolled back at the end of the test. This means that no changes are committed to the database. Also, the default Grails environment for tests is “test”. class MyController { def myService def show = { def items = myService.fetchItemsFor(params.userId) [ itemNames: items.collect { it.name } ] } } what if the service method returns null instead? There’s no reason it can’t do so, but now you can see that the controller will throw a NullPointerException because of the code items.collect {...}. class MyControllerTests extends GroovyTestCase{ def myService void testShowNoItems() { def myController = new MyController() myController.myService = myService myController.params.userId = "glen" def model = myController.show() assertEquals 0, model["itemNames"].size() } } approach for integration tests is different: tests are run against a live database, so you create data via the domain classes as you do in the live application. But because you are working against a database, there are no guarantees that data will be returned in the order you expect When only an integration test will do: Grails’ unit test support will get you a long way in your testing endeavors, but there are gaps in its coverage you need to be aware of. In particular, it doesn’t give you any help with either criteria or Hibernate Query Language (HQL) queries, nor does it have any support for testing URL mappings. Testing URL mappings is a simple matter of leveraging the GrailsUrlMappings- TestCase support class: Let’s say, for the sake of argument, that we have these mappings: class UrlMappings { static mappings = { "/basket/$username"(controller: "basket", action: "show") "/$controller/$action?/$id?"() "500"(view: "error") } } class UrlMappingsTestCase extends grails.test.GrailsUrlMappingsTestCase { void testMappings() { assertUrlMapping("/item/edit/123", controller: "item", action: "edit") { id = 123 } assertUrlMapping("/basket/fred", controller: "basket", action: "show") { username = "fred" } assertForwardUrlMapping(500, view: "error") } } loads all the application’s URL mappings and does all the necessary preparation in setUp().themselves. The foot soldier of URL mapping tests is the assertUrlMapping() method B, which accepts a URL as the first argument, and a controller and action as named ones. In the first test, we make sure that the URL "/item/edit/123" maps to the item controller and edit action, with the value 123 mapped to the id parameter. This method also checks that the reverse mapping works. There is also a corresponding assertReverseUrlMapping() method that accepts the same arguments as the other assertion methods. Reloading Agent Grails 2.0 reloading mechanism no longer uses class loaders, but instead uses a JVM agent to reload changes to class files. This results in greatly improved reliability when reloading changes and also ensures that the class files stored in disk remain consistent with the class files loaded in memory. which reduces the need to run the clean command. Clean Command Purpose: The clean command deletes all compiled resources from the application. Since Groovy is a compiled language, as with Java, this is sometimes useful to clear old instances of classes and ensure correct compilation. It's also a good idea to run this script before running tests or creating a WAR file to ensure a full compilation occurs. Enhanced Error Reporting and Diagnosis Error reporting and problem diagnosis has been greatly improved with a new errors view that analyses stack traces and recursively displays problem areas in your code: Grails 2.0 now uses the H2 database instead of HSQLDB, and enables the H2 database console in development mode (at the URI /dbconsole) to check the database Groovy 1.8 Grails 2.0 comes with Groovy 1.8 Binary Plugins Grails plugins can now be packaged as JAR files and published to standard maven repositories. This even works for GSP and static resources (with resources plugin 1.0.1). Controller Actions as Methods It is now possible to define controller actions as methods instead of using closures as in previous versions of Grails. In fact this is now the preferred way of expressing an action. For example: // action as a method def index() { } // action as a closure def index = { } Binding Primitive Method Action Arguments It is now possible to bind form parameters to action arguments where the name of the form element matches the argument name. For example given the following form: <g:form name="myForm" action="save"> <input name="name" /> <input name="age" /> </g:form> You can define an action that declares arguments for each input and automatically converts the parameters to the appropriate type: def save(String name, int age) { // remaining } Servlet 3.0 Async Features Grails now supports Servlet 3.0 including the Asynchronous programming model defined by the specification: def index() { def ctx = startAsync() ctx.start { new Book(title:"The Stand").save() render template:"books", model:[books:Book.list()] ctx.complete() } } Link Generation API A general purpose LinkGenerator class is now available. that is usable anywhere within a Grails application and not just within the context of a controller. For example if you need to generate links in a service or an asynchronous background job outside the scope of a request: LinkGenerator grailsLinkGenerator def generateLink() { grailsLinkGenerator.link(controller:"book", action:"list") } Page Rendering API: Like the LinkGenerator the new PageRenderer can be used to render GSP pages outside the scope of a web request, such as in a scheduled job or web service. The PageRenderer class features a very similar API to the render method found within controllers: grails.gsp.PageRenderer groovyPageRenderer void welcomeUser(User user) { def contents = groovyPageRenderer.render(view:"/emails/welcomeLetter", model:[user: user]) sendEmail { to user.email body contents } } The PageRenderer service also allows you to pre-process GSPs into HTML templates: new File("/path/to/welcome.html").withWriter { w -> groovyPageRenderer.renderTo(view:"/page/c ontent", w) } Filter Exclusions Filters may now express controller, action and uri exclusions to offer more options for expressing to which requests a particular filter should be applied. filter1(actionExclude: 'log*') { before = { // … } } filter2(controllerExclude: 'auth') { before = { // … } } filter3(uriExclude: '/secure*') { before = { // … } } HTML5 Scaffolding There is a new HTML5-based scaffolding UI jQuery by Default Customizable URL Formats The default URL Mapping mechanism supports camel case names in the URLs. The default URL for accessing an action named addNumbers in a controller named MathHelperController would be something like /mathHelper/addNumbers. Grails allows for the customization of this pattern and provides an implementation which replaces the camel case convention with a hyphenated convention that would support URLs like /math-helper/addnumbers. To enable hyphenated URLs assign a value of "hyphenated" to the grails.web.url.converter property in grails-app/conf/Config.groovy. // grails-app/conf/Config.groovy grails.web.url.converter = 'hyphenated' Detached Criteria and Where Queries Grails 2.0 features support for DetachedCriteria which are criteria queries that are not associated with any session or connection and thus can be more easily reused and composed. New findOrCreate and findOrSave Methods Domain classes have support for the findOrCreateWhere, findOrSaveWhere, findOrCreateBy and findOrSaveBy query methods which behave just like findWhere and findBy methods except that they should never return null. If a matching instance cannot be found in the database then a new instance is created, populated with values represented in the query parameters and returned. In the case of findOrSaveWhere and findOrSaveBy, the instance is saved before being returned. def book = Book.findOrCreateWhere(author: 'Douglas Adams', title: "TheHitchiker's Guide To The Galaxy") def book = Book.findOrSaveWhere(author: 'Daniel Suarez', title: 'Daemon') def book = Book.findOrCreateByAuthorAndTitle('Daniel Suarez', 'Daemon') def book = Book.findOrSaveByAuthorAndTitle('Daniel Suarez', 'Daemon') Multiple Data Sources Support It is now possible to define multiple datasources in DataSource.groovy and declare one or more datasources a particular domain uses by default: class ZipCode { String code static mapping = { datasource 'ZIP_CODES' } } development { dataSource { dbCreate = "create-drop" url = "jdbc:h2:mem:devDb" } dataSource_lookup { dialect = org.hibernate.dialect.MySQLInnoDBDialect driverClassName = 'com.mysql.jdbc.Driver' username = 'lookup' password = 'secret' url = 'jdbc:mysql://localhost/lookup' dbCreate = 'update' } } Database Reverse Engineering A new database reverse engineering plugin has been designed and built for Grails 2.0 that allows you to generate a domain model from an existing database schema. Hibernate 3.6 Grails 2.0 is now built on Hibernate 3.6 Grails Command Aliases The alias command may be used to define aliases for grails commands. The following command creates an alias named rit (short for "run integration tests"): grails alias rit test-app integration: Cache Plugin Grails 2.1 installs the cache plugin by default. This plugin provides powerful and easy to use cache functionality to applications and plugins. New GORM Methods In Grails 2.1.1 domain classes now have static methods named first and last to retrieve the first and last instances from the datastore. See the first and last documentation for details. Namespace Support for plugins: Domain classes provided by a plugin will have their default database table name prefixed with the plugin name if the grails.gorm.table.prefix.enabled config property is set to true. For example, if the PublishingUtilities plugin provides a domain class named Book, the default table name for that domain class will be PUBLISHING_UTILITIES_BOOK if the grails.gorm.table.prefix.enabled config property is set to true. URL Mappings may now include a plugin attribute to indicate that the controller referenced in the mapping is provided by a particular plugin. static mappings = { // requests to /bookAuthors will be handled by the // AuthorController provided by the BookUtilities plugin "/bookAuthors" { controller = 'author' plugin = 'bookUtilities' } // requests to /publishingAuthors will be handled by the // AuthorController provided by the Publishing plugin "/publishingAuthors" { controller = 'author' plugin = 'publishing' } } Controller methods and GSP Tags which accept a controller name as a paramater now support an optional parameter indicating that the controller is provided by a specific plugin. <g:link controller="user" plugin="springSecurity">Manage Users</g:link> class DemoController { def index() { redirect controller: 'user', action: 'list', plugin: 'springSecurity' } } Forked Tomcat Execution Grails 2.2 supports forked JVM execution of the Tomcat container in development mode. This has several benefits including: • Reduced memory consumption, since the Grails build system can exit • Isolation of the build classpath from the runtime classpath • The ability to deploy other Grails/Spring applications in parallel without conflicting dependencies SQL Projections In Criteria Queries Grails 2.2 adds new functionality to criteria queries to provide access to Hibernate's SQL projection following scripts to see what plugins needed updating grails list-plugin-updates To update a plugin you just run install-plugin again and it'll detect that the plugin's already installed and will remove the old one and install the new one. For a small version delta this should be fine, but I'd do them one at a time and test in-between (but do the 2 JQuery plugins together). If you're lucky the plugin either has no compatibility issues, or they're documented in the plugin docs, so be sure to check there before upgrading. From Grails 2.2 on, you should change the plugins section of BuildConfig.groovy. After that you can run grails list-plugin-updates again and it will ask to update your dependencies.