Tendo desenvolvido aplicações em Java por algum tempo, sei o poder da plataforma java e também da dificuldade de seu uso.
O mundo java é tão grande que a gente se perde. Desenvolver web em java é ótimo, é orientado a objetos, se você seguir uma boa arquitetura você cria uma aplicação fácil de manter e evoluir, você pode usar diversos projetos open source de qualidade para ajudar no seu trabalho, é estável, performático, etc, etc. Mas tem um lado que a gente fica se questionando às vezes: mas precisa disso tudo mesmo? Cria o POJO, adiciona atributos, getters e setters (td bem o Eclipse gera), cria JSP, cria controlador, cria classe de serviços, cria DAO, cria as interfaces de serviços e DAOs, faz a query, configura tudo nos XMLs, testa tudo, faz o WAR, faz o deploy, starta o tomcat, ufa....eu só queria mostrar um relatóriozinho na tela do browser.... é, não é mole.
Aí, a gente olha para os lados e vê, por exemplo, PHP (eu mesmo já usei e continuo usando em alguns projetos). É mais simples não é? MEsmo se você usar um framework MVC de PHP, as coisas são mais simples na minha opinião, sem falar que é só dar um refresh no browser e vc vê a mudança imediatamente. Porém, e tudo aquilo que a gente gosta de Java: Apache Commons, Log4j, Quartz, Spring, Hibernate, Lucene, entre tantos outros projetos open source que nos ajudam, sem falar em orientação a objetos sem opção, etc, etc.
Dentro deste cenário todo, eu passei a ver todo o movimento sobre o Ruby on Rails (RoR): que é isso , que é aquilo, que é ótimo, rápido de desenvolver, não precisa configurar em XML, e isso, e aquilo. Realmente o grupo do RoR criou um framework MVC para aplicações web com bancos de dados que funciona e ajuda MUITO os desenvolvedores. Foi quando eu descobri o Grails (inicialmente chamado de Groovy on Rails).
O Grails foi inspirado no RoR, seguindo o padrão de convenção ao invés de configuração (o que já nos tira um trabalho de configurar tudo). Não sou profundo conhecedor do RoR, mas sabendo que o Grails se inspirou nele, podemos ver que realmente o grupo do RoR fez um excelente trabalho. Mas excelente também é o Grails: um framework MVC para desenvolvimento ágil de aplicações web com bancos de dados, sobre a plataforma Java.
O Grails foi desenvolvido em Groovy, uma linguagem de script dinamicamente tipada, orientada a objetos, que roda sobre a JVM e se intgra nativamente com Java. Você pode dar um import de uma classe java no seu script Groovy, instanciar e usar a classe Java normalmente (perdoem se eu estiver falando besteira, não sou expert em Groovy ainda).
Por baixo dos panos...
O Grails não quis reinventar a roda, e portanto utiliza tudo que a gente gosta do mundo java: Log4j, Hibernate, Spring, SpringMVC, Sitemesh, Quartz... tudo por baixo dos panos, abstraindo todo este mundo de mais "baixo nível". A configuração do spring ele mesmo faz usando groovy ao invés de xml. A persistência ele usa Hibernate. Para templates ele usa Sitemesh. E assim vai. Mas o fato é que você não precisa conhecer cada um desses frameworks, pois o Grails abstrai isso tudo. É claro que às vezes, se você conhecer um pouco de cada, você pode ter vantagens.
Auto reloading...
Você gosta de dar um refresh e e ver as mudanças imediatamente? O Grails é assim em 99% dos casos! :-)
Convenções do Grails...
O Grails usa a codificação por convenção: estrutura de diretórios, nomenclatura de classes, URL, ...
Por exemplo:
http://locahost:8080/minhaApp/user/add = UserController + add closure
A Closure add do controlador UserController será executada.
Você pode "configurar" o framework com atributos reservados, como por exemplo, se você quiser fazer com que um closure de um controlador seja a Action default a ser executada para aquele controlador, você faz:
class BookController {
def defaultAction = "list"
def list = {
// do controller logic and create model
return model
}
}
Grails MVC...
- M =>
Classes do modelo seguem o padrão "Active Record"
User u = User.get(1)
u.delete() - C =>
Grails Controllers: Classes Groovy, Não herdam ninguém, Tem classes de serviços injetados pelo Spring. - V =>
GSP ou JSP (GSP = Groovy Server Pages)
Sitemesh
Grails Taglib: classes groovy, Não precisa de TLD.
Grails Controllers..
- closures = actions (ações a serem executadas pelo controlador são as closures do seu controlador)
- fazer redirect nunca foi tão fácil:
redirect(action:list) - É possível fazer restrição do método Http requisitado (POST, GET)
def allowedMethods = [action1:'POST', action3:['POST', 'DELETE']] - Os contextos estão disponíveis para o seu controlador: Request, Session, appContext
class BookController {
def find = {
def findBy = params["findBy"] // ou params.findBy
def appContext = servletContext["appContext"] // ou sContext.appContext
def loggedUser = session["logged_user"] // session.logged_user
}
} Existe o escopo Flash (variável colocada na sessão até ser usada no request seguinte):
flash.message = ‘Operação realizada com sucesso’
redirect(action:list)- Binding:
O binding do form para os atributos do seu objeto POGO é muito simples, bastanto objeto.properties = params (onde params é um mapa disponível no seu controlador contendo os parâmetros recebidos pelo POST ou GET:
def save = {
def b = new Book()
b.properties = params
b.save()
// Ou usando um objeto command
def sc = new SaveCommand()
bindData(sc, params)
return [book:b]
} - Por trás dos panos retorna ModelAndView do Spring
Caso não declare “return”, retorna propriedades do controlador - Rendering: encaminha para view apropriada:
http://localhost:8080/meuprojeto/user/add = views/user/add.gsp (ou .jsp)
render "Hello World!
render {
for(b in books) {
div(id:b.id, b.title)
}
}
Action redirection and chaining- Action Interceptors: é possível interceptar a chamada das actions (closures):
. def beforeInterceptor
. def afterInterceptor - File uploads: o Grails possui facilidades que ajudam no upload de arquivos.
Grails Object Relational Mapping: GORM...
O Grails criou uma nova forma de mapeamento objeto relacional. Na verdade, o Grails usa o Hibernate mas facilita o mapeamento, que ao invés de ser com XML (até pode ser se vc quiser), faz com atributos reservados na sua classe de modelo (POGO , Plain Old Groovy Object). As classes de modelo tem seus atributos mapeados como campos, e você pode especificar algum atributo como opcional ou transiente.
class Book {
static optionals = [ "releaseDate" ]
static transients = [ "digitalCopy" ]
Author author
String title
String author
Date releaseDate
File digitalCopy
}
Os relacionamentos entre as entidades são especificados com atributos reservados do Grails. São suportados relacionamentos one-to-many, many-to-one, e many-to-many.
One-to-many
class Author {
static hasMany = [ books : Book ]
String name
}
Many-to-one
class Book {
static belongsTo = Author
Author author
String title
}
Many-to-many
class Book {
static belongsTo = Author
static hasMany = [authors:Author]
}
class Author {
static hasMany = [books:Book]
}
new Author(..).addBook(new Book(..)).save()
Grails Querying
- findBy*:
def results = Book.findByTitle("The Stand")
results = Book .findByTitleLike("Harry Pot%")
results = Book .findByReleaseDateBetween( firstDate, secondDate )
results = Book .findByTitleLikeOrReleaseDateLessThan( "%Something%", someDate ) - Creteria Builder
def c = Book.createCriteria()
def results = c {
like("author.name", "Stephen%")
between("releaseDate", firstDate, secondDate )
} - Query by Example:
def b = Book.find( new Book(title:'The Shining') ) - HQL:
def results = Book.find("from Book as b where b.title like 'Lord of the%'")
E o Grails ainda possui facilidades para:
- Jobs: uso do Quartz
- Transactions: métodos dos “services” são transacionais
- Validation
- Scaffolding
- Ajax
- Unit testing
- Spring Integration
- Hibernate Integration
Para finalizar....
- a lista de usuários é bastante ativa tendo todo o apoio dos líderes do projeto;
- a documentação já é bem razoável e melhora a cada dia;
- o primeiro livro já foi escript e publicado;
- não se assuste com a versão ainda em 0.3.1 nesta data. O projeto já possui muitas funcionalidades estáveis que ajudam muitos projetos web.
Boa sorte!
7 comentários:
Estou definindo uma arquitetura para um prototipo de aplicação web em java. Estou (estava) praticamente resolvido com JSF/Facelets/Hibernate, depois de ler seus posts talvez tome outra direção...
Olá Douglas. É bom saber que meus comentários estão chegando até o público certo. Obrigado pelo comentário. Vale a pena sim olhar o Grails e ver como ele pode nos ajudar. Boa sorte!
Felipe,
Tem algum material do tipo passo a passo que possa ser encontrado na web???
Dei uma olhada no site e achei a documentação meio fraquinha....
O livro oferece esse passo a passo??
Olá,
eu acho que a documentação realmente não é a melhor (ultimamente houve bastante discussão na lista sobre documentação, e o pessoal da G2one vai investir em documentação em breve). Mas para o básico ela cobre os principais pontos.
Dê uma olhada:
http://www.grails.org/Quick+Start
Depois, leia o User Guide:
http://www.grails.org/User+Guide
Vá lendo item por item. No final você terá uma excelente noção do grails.
Além disso, há sim pequenos tutoriais na web, tem é que garimpar.
Tem uma que eu fiz há um tempo já....
se quiser olhar:
http://wiki.les.inf.puc-rio.br/uploads/4/44/GrailsFelipe.ppt
O livro é muito bom. Mas foi feito na versão 0.3.1. Muita coisa mudou desde então. Mas mesmo assim, tem bastante coisa lá.
Outra opção é um pdf gratuito, um minibook:
http://www.infoq.com/minibooks/grails
Esse é legal tbem.
Por ultimo, vale olhar o www.groovyblogs.org , que é um site que agrupa blogs sobre groovy e grails. O próprio site é feito em grails e tem seu código fonte livre para download. (http://www.bytecode.com.au/downloads/grails/groovyblogs-0.5.6.tar.gz)
Você diz que os campos podem ser "opcionais ou transientes" o que isso significa exatamente?
obrigado.
Olá Cleber,
Atributos opcionais são aqueles que não precisam ser preenchidos, ou seja, que podem ter valor NULL no BD. Transientes são aqueles que não são persistidos, ou sejam, não existem campos na tabela para esses atributos. Normalmente são atributos de ajuda, usados em memória, mas que não são persistidos.
Grande abraço
Felipe Nascimento
Aprendi muito
Postar um comentário