First they ignore you
then they ridicule you
then they fight you
then you win
    -- Mahatma Gandhi
Chinese => English     英文 => 中文             
随笔-221  评论-1047  文章-0  trackbacks-0
Grails中的GORM是一个基于Hibernate开发出来的崭新ORM框架,其优点就是无需任何配置。但早期的GORM有个不太方便的地方,就是如果想Grails自动创建的表名和字段名是由自己制定的,那么我们就不得不使用hibernate的映射文件,这样就又用回hibernate了。幸好Grails1.0提供了让我们DIY表和字段的DSL,使我们可以彻底摆脱XML配置文件的阴影。

遵循“Groovy轻松入门系列”的一贯做法,下面还是以一个实例来说明GORM DSL到底是怎么回事,它会带给我们多大的便利。

1,执行‘grails create-app GormDslDemo’,创建一个名为GormDslDemo的Grails项目
D:\_DEV\grails_apps>grails create-app GormDslDemo

Welcome to Grails 1.0.2 - http://grails.org/
Licensed under Apache Standard License 2.0
Grails home is set to: D:\D\MY_DEV\grails-1.0.2

Base Directory: D:\_DEV\grails_apps
Note: No plugin scripts found
Running script D:\D\MY_DEV\grails-1.0.2\scripts\CreateApp.groovy
Environment set to development
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\src
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\src\java
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\src\groovy
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\grails-app
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\grails-app\controllers
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\grails-app\services
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\grails-app\domain
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\grails-app\taglib
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\grails-app\utils
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\grails-app\views
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\grails-app\views\layouts
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\grails-app\i18n
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\grails-app\conf
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\test
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\test\unit
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\test\integration
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\scripts
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\web-app
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\web-app\js
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\web-app\css
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\web-app\images
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\web-app\META-INF
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\lib
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\grails-app\conf\spring
    [mkdir] Created dir: D:\_DEV\grails_apps\GormDslDemo\grails-app\conf\hibernate
[propertyfile] Creating new property file: D:\_DEV\grails_apps\GormDslDemo\application.properties
     [copy] Copying 2 files to D:\_DEV\grails_apps\GormDslDemo
     [copy] Copying 2 files to D:\_DEV\grails_apps\GormDslDemo\web-app\WEB-INF
     [copy] Copying 5 files to D:\_DEV\grails_apps\GormDslDemo\web-app\WEB-INF\tld
     [copy] Copying 87 files to D:\_DEV\grails_apps\GormDslDemo\web-app
     [copy] Copying 17 files to D:\_DEV\grails_apps\GormDslDemo\grails-app
     [copy] Copying 1 file to D:\_DEV\grails_apps\GormDslDemo
     [copy] Copying 1 file to D:\_DEV\grails_apps\GormDslDemo
     [copy] Copying 1 file to D:\_DEV\grails_apps\GormDslDemo
[propertyfile] Updating property file: D:\_DEV\grails_apps\GormDslDemo\application.properties
Created Grails Application at D:\_DEV\grails_apps/GormDslDemo
D:\_DEV\grails_apps>

2,将数据库JDBC驱动jar文件放到lib目录下,比如我使用的数据库是MySQL,那么JDBC驱动jar文件就是mysql-connector-java-5.1.5-bin.jar

3,配置数据源,将grails-app\conf\DataSource.groovy修改为(注意:假设您也是用MySQL,记得将用户名和密码改为自己的)
dataSource {
    pooled 
= false
    
//driverClassName = "org.hsqldb.jdbcDriver"
    driverClassName = "com.mysql.jdbc.Driver"
    
//username = "sa"
    username = "root"
    
//password = ""
    password = "123"
}
hibernate {
    cache.use_second_level_cache
=true
    cache.use_query_cache
=true
    cache.provider_class
='org.hibernate.cache.EhCacheProvider'
}
// environment specific settings
environments {
    development {
        dataSource {
            dbCreate 
= "create-drop" // one of 'create', 'create-drop','update'
            
//url = "jdbc:hsqldb:mem:devDB"
            url = "jdbc:mysql://localhost:3306/gorm_dsl_demo?createDatabaseIfNotExist=true"
        }
    }
    test {
        dataSource {
            dbCreate 
= "update"
            url 
= "jdbc:hsqldb:mem:testDb"
        }
    }
    production {
        dataSource {
            dbCreate 
= "update"
            url 
= "jdbc:hsqldb:file:prodDb;shutdown=true"
        }
    }
}

4,创建domain class,在本例中,我们创建两个domain class,沿用经典的Author和Book
创建Author
D:\_DEV\grails_apps\GormDslDemo>grails create-domain-class Author

Welcome to Grails 1.0.2 - http://grails.org/
Licensed under Apache Standard License 2.0
Grails home is set to: D:\D\MY_DEV\grails-1.0.2

Base Directory: D:\_DEV\grails_apps\GormDslDemo
Note: No plugin scripts found
Running script D:\D\MY_DEV\grails-1.0.2\scripts\CreateDomainClass.groovy
Environment set to development
     [copy] Copying 1 file to D:\_DEV\grails_apps\GormDslDemo\grails-app\domain
Created  for Author
     [copy] Copying 1 file to D:\_DEV\grails_apps\GormDslDemo\test\integration
Created Tests for Author
D:\_DEV\grails_apps\GormDslDemo>
创建Book
D:\_DEV\grails_apps\GormDslDemo>grails create-domain-class Book

Welcome to Grails 1.0.2 - http://grails.org/
Licensed under Apache Standard License 2.0
Grails home is set to: D:\D\MY_DEV\grails-1.0.2

Base Directory: D:\_DEV\grails_apps\GormDslDemo
Note: No plugin scripts found
Running script D:\D\MY_DEV\grails-1.0.2\scripts\CreateDomainClass.groovy
Environment set to development
     [copy] Copying 1 file to D:\_DEV\grails_apps\GormDslDemo\grails-app\domain
Created  for Book
     [copy] Copying 1 file to D:\_DEV\grails_apps\GormDslDemo\test\integration
Created Tests for Book
D:\_DEV\grails_apps\GormDslDemo>

5,修改grails-app\domain目录下的Author.groovy和Book.groovy:
Author.groovy
class Author {
    String name
    
static hasMany = [books: Book]
    
static mapping = {
        table 
'AUTHOR'

        columns {
            name column:
'AUTHOR_NAME'
        }

        id generator:
'increment', column:'AUTHOR_ID_PK'
        version
false
    }
}

Book.groovy
class Book {
    String name
    Float price
    Author author
    
static mapping = {
        table 
'BOOK'
        
        columns {
            name column:
'BOOK_NAME'
            price column:
'BOOK_PRICE'
            author column:
'AUTHOR_ID_FK'
        }

        id generator:
'increment', column:'BOOK_ID_PK'
       
version false
    }
}

对上面的mapping这个closure稍微解释一下,以Book中的mapping为例,
    static mapping = {
        table 'BOOK'    // 为Book类生成的表名为BOOK,您可以将它改为其他名字,比如BOOK_TABLE等
       
        columns {
            name column:'BOOK_NAME'       // 表中与name属性相对应的字段名为BOOK_NAME
            price column:'BOOK_PRICE'     // 类似地,表中与price属性相对应的字段名为BOOK_PRICE
            author column:'AUTHOR_ID_FK'  // 表中与author属性相对应的字段名为AUTHOR_ID_FK,该字段是一个外键
        }

        id generator:'increment', column:'BOOK_ID_PK' // 指定id生成的策略为increment以及其对应的字段名为BOOK_ID_PK
        version false  // 不让Grails自动生成version字段,该字段用来支持乐观锁,一般不建议将其去除,这里仅仅是为了演示
    }


6, 执行'grails generate-all Author'和'grails generate-all Book'命令生成与Author和Book相关的CRUD的所有代码和页面。
D:\_DEV\grails_apps\GormDslDemo>grails generate-all Author

Welcome to Grails 1.0.2 - http://grails.org/
Licensed under Apache Standard License 2.0
Grails home is set to: D:\D\MY_DEV\grails-1.0.2

Base Directory: D:\_DEV\grails_apps\GormDslDemo
Note: No plugin scripts found
Running script D:\D\MY_DEV\grails-1.0.2\scripts\GenerateAll.groovy
Environment set to development
    [mkdir] Created dir: C:\Documents and Settings\Daniel\.grails\1.0.2\projects\GormDslDemo\classes

  [groovyc] Compiling 8 source files to C:\Documents and Settings\Daniel\.grails\1.0.2\projects\Gorm
DslDemo\classes
    [mkdir] Created dir: C:\Documents and Settings\Daniel\.grails\1.0.2\projects\GormDslDemo\resourc
es\grails-app\i18n
[native2ascii] Converting 10 files from D:\_DEV\grails_apps\GormDslDemo\grails-app\i18n to C:\Docume
nts and Settings\Daniel\.grails\1.0.2\projects\GormDslDemo\resources\grails-app\i18n
     [copy] Copying 1 file to C:\Documents and Settings\Daniel\.grails\1.0.2\projects\GormDslDemo\cl
asses
     [copy] Copying 1 file to C:\Documents and Settings\Daniel\.grails\1.0.2\projects\GormDslDemo\re
sources
     [copy] Copying 1 file to C:\Documents and Settings\Daniel\.grails\1.0.2\projects\GormDslDemo
[0] spring.GrailsWebApplicationContext Refreshing org.codehaus.groovy.grails.commons.spring.GrailsWe
bApplicationContext@f4a376: display name [org.codehaus.groovy.grails.commons.spring.GrailsWebApplica
tionContext@f4a376]; startup date [Fri Apr 04 00:00:55 CST 2008]; root of context hierarchy
[0] spring.GrailsWebApplicationContext Bean factory for application context [org.codehaus.groovy.gra
ils.commons.spring.GrailsWebApplicationContext@f4a376]: org.springframework.beans.factory.support.De
faultListableBeanFactory@101ac1c
Generating views for domain class Author 
Generating controller for domain class Author 
Finished generation for domain class Author

D:\_DEV\grails_apps\GormDslDemo>grails generate-all Book

Welcome to Grails 1.0.2 - http://grails.org/
Licensed under Apache Standard License 2.0
Grails home is set to: D:\D\MY_DEV\grails-1.0.2

Base Directory: D:\_DEV\grails_apps\GormDslDemo
Note: No plugin scripts found
Running script D:\D\MY_DEV\grails-1.0.2\scripts\GenerateAll.groovy
Environment set to development
  [groovyc] Compiling 2 source files to C:\Documents and Settings\Daniel\.grails\1.0.2\projects\Gorm
DslDemo\classes
[0] spring.GrailsWebApplicationContext Refreshing org.codehaus.groovy.grails.commons.spring.GrailsWe
bApplicationContext@15863e4: display name [org.codehaus.groovy.grails.commons.spring.GrailsWebApplic
ationContext@15863e4]; startup date [Fri Apr 04 00:03:29 CST 2008]; root of context hierarchy
[15] spring.GrailsWebApplicationContext Bean factory for application context [org.codehaus.groovy.gr
ails.commons.spring.GrailsWebApplicationContext@15863e4]: org.springframework.beans.factory.support.
DefaultListableBeanFactory@f4ca49
Generating views for domain class Book 
Generating controller for domain class Book 
Finished generation for domain class Book
D:\_DEV\grails_apps\GormDslDemo>

7,启动完MySQL数据库之后,执行'grails run-app'命令,启动web服务器。
D:\_DEV\grails_apps\GormDslDemo>grails run-app

Welcome to Grails 1.0.2 - http://grails.org/
Licensed under Apache Standard License 2.0
Grails home is set to: D:\D\MY_DEV\grails-1.0.2

Base Directory: D:\_DEV\grails_apps\GormDslDemo
Note: No plugin scripts found
Running script D:\D\MY_DEV\grails-1.0.2\scripts\RunApp.groovy
Environment set to development
  [groovyc] Compiling 2 source files to C:\Documents and Settings\Daniel\.grails\1.0.2\projects\Gorm
DslDemo\classes
Running Grails application..
2008-04-04 00:06:07.861::INFO:  Logging to STDERR via org.mortbay.log.StdErrLog
2008-04-04 00:06:07.095::INFO:  jetty-6.1.4
2008-04-04 00:06:08.454::INFO:  No Transaction manager found - if your webapp requires one, please c
onfigure one.
2008-04-04 00:06:08.329:/GormDslDemo:INFO:  Set web app root system property: 'GormDslDemo' = [D:\_D
EV\grails_apps\GormDslDemo\web-app\]
2008-04-04 00:06:08.345:/GormDslDemo:INFO:  Initializing Log4J from [file:C:\Documents and Settings\
Daniel/.grails/1.0.2/projects/GormDslDemo/resources/log4j.properties]
2008-04-04 00:06:08.376:/GormDslDemo:INFO:  Initializing Spring root WebApplicationContext
[0] spring.GrailsWebApplicationContext Refreshing org.codehaus.groovy.grails.commons.spring.GrailsWe
bApplicationContext@c393a1: display name [org.codehaus.groovy.grails.commons.spring.GrailsWebApplica
tionContext@c393a1]; startup date [Fri Apr 04 00:06:12 CST 2008]; parent: org.springframework.web.co
ntext.support.XmlWebApplicationContext@bd3b2d
[0] spring.GrailsWebApplicationContext Bean factory for application context [org.codehaus.groovy.gra
ils.commons.spring.GrailsWebApplicationContext@c393a1]: org.springframework.beans.factory.support.De
faultListableBeanFactory@144569b
2008-04-04 00:06:19.620:/GormDslDemo:INFO:  Initializing Spring FrameworkServlet 'grails'
2008-04-04 00:06:20.151::INFO:  Started SelectChannelConnector@0.0.0.0:8080
Server running. Browse to http://localhost:8080/GormDslDemo

8,打开浏览器,访问:http://localhost:8080/GormDslDemo ,看一下自己的劳动成果。

9,查看MySQL中,Grails自动帮您生成的表:
AUTHOR表
CREATE TABLE `author` (
  `AUTHOR_ID_PK` 
bigint(20NOT NULL,
  `AUTHOR_NAME` 
varchar(255NOT NULL,
  
PRIMARY KEY  (`AUTHOR_ID_PK`)
)

BOOK表
CREATE TABLE `book` (
  `BOOK_ID_PK` 
bigint(20NOT NULL,
  `AUTHOR_ID_FK` 
bigint(20NOT NULL,
  `BOOK_NAME` 
varchar(255NOT NULL,
  `BOOK_PRICE` 
float NOT NULL,
  
PRIMARY KEY  (`BOOK_ID_PK`),
  
KEY `FK1F32E99AB78860` (`AUTHOR_ID_FK`),
  
CONSTRAINT `FK1F32E99AB78860` FOREIGN KEY (`AUTHOR_ID_FK`) REFERENCES `author` (`AUTHOR_ID_PK`)
)


看过这篇文章后,或多或少给了您一些如何方便地处理遗留数据库的启发了吧 :)

附:朝花夕拾——Groovy & Grails
posted on 2008-04-04 00:53 山风小子 阅读(4489) 评论(6)  编辑  收藏 所属分类: Groovy & Grails