• Share
  • Email
  • Embed
  • Like
  • Save
  • Private Content
A Case for Grails
 

A Case for Grails

on

  • 3,208 views

 

Statistics

Views

Total Views
3,208
Views on SlideShare
3,151
Embed Views
57

Actions

Likes
1
Downloads
13
Comments
0

3 Embeds 57

http://www.citytechinc.com 55
http://www.techgig.com 1
http://citytechinc.com 1

Accessibility

Categories

Upload Details

Uploaded via as Microsoft PowerPoint

Usage Rights

© All Rights Reserved

Report content

Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

Cancel
  • Full Name Full Name Comment goes here.
    Are you sure you want to
    Your message goes here
    Processing…
Post Comment
Edit your comment

    A Case for Grails A Case for Grails Presentation Transcript

    • (A case for) GRAILS
      Mark Daugherty
      CITYTECH, Inc.
      July 7th, 2010
    • Outline
      Inspiration
      Grails overview
      Comparison of Java/Spring/JPA application to Groovy/Grails
    • Context
      February 2010 : wrote a small Groovy/Grails app to learn the technologies
      March 1st, 2010 : started on CDGA project (Struts, Spring, JPA)
      March 1st, 2010 (later that day) : realized that CDGA had an enormous amount of boilerplate code that Grails could eliminate
    • (Additional) Context
      May 7th, 2010 : wrote CITYTECH blog post about code savings from replacing Spring DAO code with Grails
      May 8th, 2010 – present : blog is read by a total of 4 CITYTECH employees
      July 7th, 2010 : Grails begins to learn at a geometric rate. It becomes self-aware at 2:14 AM, Eastern time.
    • Grails Primer
      Web application framework built with Groovy (Java-based dynamic language) on top of proven Java technologies
      Spring MVC, Hibernate
      Full stack for rapid development
      Embedded Tomcat container, HSQLDB, (G)Ant, scaffolding features
      Get a basic app running within minutes
    • You may notice…
      Convention over configuration
      Little-to-no initial configuration
      Project structure is predefined according to best practices
      Command line scripts for common tasks
      Create new application, compile, test, run
      Generate domain classes, controllers, services, test cases
      Install plugins
      Contrast with your last Maven-built project
    • In practice…
    • Simple Domain
      Delegate 1  ∞ User
      Delegate 1  ∞ Application
      A “delegate agency” has one-to-many users and one-to-many applications. An application contains various forms, input by users, to collect data about the delegate agency.
    • JPA (Java Persistence API)
      @Entity
      @Table(name = "USER")
      public class User implements Serializable {
      @Id
      private Integer id;
      @OneToOne(fetch = FetchType.LAZY)
      @JoinColumn(name = "DELEGATE", referencedColumnName = "ID")
      private Delegate delegate;
      // getters and setters, equals(), hashCode(), toString()…
      }
    • (More) JPA
      @Entity
      @Table(name = "DELEGATE")
      public class Delegate implements Serializable {
      @Id
      private Integer id;
      @OneToMany(cascade = { CascadeType.ALL }, fetch = FetchType.EAGER)
      private Set<User> users;
      @OneToMany(cascade = { CascadeType.REMOVE }, fetch = FetchType.LAZY)
      private Set<Application> applications;
      // getters and setters, equals(), hashCode(), toString()...
      }
    • (Still more) JPA
      @Entity
      @Table(name = "APPLICATION")
      public class Application implements Serializable {
      @Id
      private Integer id;
      @ManyToOne(cascade = { CascadeType.REFRESH }, optional = false)
      @JoinColumn(name = "DELEGATE”)
      private Delegate delegate;
      // getters and setters, equals(), hashCode(), toString()...
      }
    • Grails
      class User {
      static belongsTo = [delegate:Delegate]
      }
      class Delegate {
      static hasMany = [users:User, applications:Application]
      static mapping = {
      users lazy:false
      applications cascade:'delete'
      }
      }
      class Application {
      static belongsTo = [delegate:Delegate]
      static mapping = {
      delegate cascade:'refresh'
      }
      }
    • DAO
      JPA/Hibernate = verbose, repetitive
      Even a small domain model can have 1000’s of lines of code for basic CRUD operations
      Tedious to maintain
    • GORM!
      Hibernate under the hood
      Groovy + runtime code synthesis to eliminate boilerplate code
    • Basic CRUD
    • Dynamic Finders
    • Additional GORM Features
      ORM DSL for mapping to legacy DB schemas
      Custom mappings for non-standard table and column names
      Event handlers (beforeInsert, afterUpdate)
      Customizable caching and fetching strategies, transactions
    • Web
      Render XML or JSON responses using markup builders
      Automatic marshalling of domain classes to XML/JSON
    • (More) Web
      GSP
      Similar to JSP, but with better tag libraries
      findAll, grep (filter) for collections
      Method calls
      Templates
      Sitemesh (decorator) layouts
      Customizable URL mappings
    • Validation
      Often painful, less so with Grails
    • More Features
      Spring Web Flow
      Supports subflows, conversation scope (similar to Seam)
      Interceptors / Filters
      AJAX
      DOJO, GWT plugins
    • Even more to like
      Groovy tests
      Ideal for TDD
      Unit tests created automatically from command line script
      Dynamic language features for easy mocking
      Easy RESTful web services
      URL mappings
      Controllers can render XML or JSON
      Consider attending a CGUG meeting
      Extremely active community
      400+ plugins (Spring Security, JQuery, GWT, Google App Engine, Flex)
      Wide range of tutorials
      Frequent releases
    • Summary
      Grails compared to Spring, EJB, JPA
      Substantially less code without compromises
      Easier to maintain and test
      Shorter iterations and release cycles
      Same proven underlying technologies
      Gain competitive edge
      Why not?