260 likes | 425 Views
Struts. Java avançado – PCC Jobson Ronan {jrjs@cin.ufpe.br} Guilherme Kely {gkmo@cin.ufpe.br}. O que é?. Um framework para facilitar a implementação de uma arquitetura MVC em aplicações web Oferece
E N D
Struts Java avançado – PCC Jobson Ronan {jrjs@cin.ufpe.br} Guilherme Kely {gkmo@cin.ufpe.br}
O que é? • Um framework para facilitar a implementação de uma arquitetura MVC em aplicações web • Oferece • Um servlet controlador configurável (Front Controller) através de arquivos XML externos, que despacham requisições a classe Action (Command) implementados pelo desenvolvedor • Uma vasta coleção de taglibs JSP • Classes ajudantes que oferecem suporte a tratamento de XML, preenchimento de JavaBeans, validação de formulários e gerenciamento externo de conteúdo
Componentes • Model (M) • Geralmente um objeto java (JavaBean) • View (V) • Geralmente uma página HTML ou JSP. Embora o Struts seja independente da camada de apresentação (ex. velstruts) • Controller (C) • org.apache.struts.action.ActionServlet ou subclasse
Componentes • Classes ajudantes • FromBean: Encapsula dados de um formulário HTML (M) • ActionError(s): Encapsula dados de Erros (M) (deprecated 1.2) • ActionMessage(s): Encapsula dados de Mensagens (M) • Custon tags: Encapsulam lógica de apresentação (V) • Actions: implementam lógica comandos (C) • ActionForward: Encapsulam lógica de redirecionamento (C)
Como funciona? • Componentes-chave: • ActionServlet: despachante de ações • Action: classe estendida por cada ação (comando) a ser implementada (Command pattern) • struts-config.xml: arquivo onde se definem mapeamentos entre ações, páginas, beans e dados Form Bean JSP Action Servlet Action delega http Dados, Dao ou Session Facade lê despacha Bean prenche
Como usar? • struts-blank.war • Um template básico para um aplicação web já configurada para usar o struts • web.xml <servlet> <servlet-name>action</servlet-name> <servlet-class>org.apache.struts.action.ActionServlet</servlet-class> <init-param> <param-name>config</param-name> <param-value>/WEB-INF/struts-config.xml</param-value> </init-param> ... </servlet>
Como usar? • web.xml (cont.) ... <!-- Standard Action Servlet Mapping --> <servlet-mapping> <servlet-name>action</servlet-name> <url-pattern>*.do</url-pattern> </servlet-mapping> ... <!-- Struts Tag Library Descriptors --> <taglib> <taglib-uri>/tags/struts-bean</taglib-uri> <taglib-location>/WEB-INF/struts-bean.tld</taglib-location> </taglib> <taglib> <taglib-uri>/tags/struts-html</taglib-uri> <taglib-location>/WEB-INF/struts-html.tld</taglib-location> </taglib> ...
Como usar? • struts-config.xml <?xml version="1.0" encoding="ISO-8859-1" ?> <!DOCTYPE struts-config PUBLIC "-//Apache Software Foundation//DTD Struts Configuration 1.2//EN" "http://jakarta.apache.org/struts/dtds/struts-config_1_2.dtd"> <struts-config> <!-- ============================================== Form Bean Definitions --> <form-beans> </form-beans> <!-- ======================================= Global Exception Definitions --> <global-exceptions> </global-exceptions> <!-- ========================================= Global Forward Definitions --> <global-forwards> <forward name="welcome" path="/Welcome.do"/> </global-forwards>
Como usar? • struts-config.xml (cont.) ... <!-- ========================================= Action Mapping Definitions --> <action-mappings> <action path="/Welcome“ forward="/pages/Welcome.jsp"/> </action-mappings> <!-- =========================================== Controller Configuration --> <controller processorClass="org.apache.struts.tiles.TilesRequestProcessor"/> <!-- ====================================== Message Resources Definitions --> <message-resources parameter="MessageResources" /> ...
Entendendo... • Index.jsp <%@ taglib uri="/tags/struts-logic" prefix="logic" %> <logic:redirect forward="welcome"/>
Actions • Implementando a ação cadastrar novo filme package pec; //imports public class CadastrarFilmeAction extends Action { public ActionForward execute(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws Exception { //código de efetuar cadastro... return mapping.findForward("sucesso"); } }
Actions • Declarando <!-- ========================================= Action Mapping Definitions --> <action-mappings> <action path="/Welcome“ forward="/pages/Welcome.jsp"/> <action path="/cadastrarFilme" type="pec.CadastrarFilmeAction"/> <forward name="sucesso" path="pages/cadastroSucesso.jsp"/> </action-mappings> ...
ActionForm • Nossa ação precisa de um formulário • Java bean comum • As propriedades do bean são populadas de forma transparente public class CadastroFilmeForm extends ActionForm { private String idRef; private String nomeOriginal; private String nomeNacional; private String numeroCopias; //get´s e set´s }
ActionForm • ActionFroms podem ser validados package pec; public class CadastroFilmeForm extends ActionForm { //... public ActionErrors validate(ActionMapping mapping, HttpServletRequest response) { ActionErrors validatorErros = new ActionErrors(); if (idRef == null || idRef.trim().equals("")) validatorErros.add("idRef", new ActionMessage( "filme.cadastro.idRef.required")); if (nomeOriginal == null || nomeOriginal.trim().equals("")) validatorErros.add("nomeOriginal", new ActionMessage( "filme.cadastro.nomeOriginal.required")); if (numCopias == null || numCopias.trim().equals("")) validatorErros.add("numCopias", new ActionMessage( "filme.cadastro.numCopias.required")); elseif (!GenericValidator.isInt(numCopias)) validatorErros.add("numCopias", new ActionMessage( "filme.cadastro.numCopias.notInt")); return validatorErros; } } Commons validator
ActionForm Formulário (HTML/JSP) Request recebido pelo controler Cria ou recicla um ActionForm Chama reset() Formulário (HTML/JSP) Guarda o ActionForm no escopo desejado Com menssagens de erro! Popula ActionForm a partir do request Dá um forward para o input Chama validate() do ActionForm Validação falha Página Sucesso (HTML/JSP) Validação ok Chama execute() do Action Dá um forward para “sucesso”
ActionForm • ActionForm são firewalls dos Actions • O ActionForms só chegam aos actions caso tenham sido validados • Cuidado com a definição dos tipos • Se o usuário digita um valor, torne esta propriedade uma String
ActionForm • Declarando (struts-config.xml) ... <form-beans> <form-beanname="cadastroFilmeForm" type="pec.CadastrarFilmeForm"/> </form-beans> ... <action-mappings> ... <action path="/cadastrarFilme" type="pec.CadastrarFilmeAction" name="cadastroFilmeForm" input="/cadastrarNovoFilme.jsp"> <forward name="sucesso" path="/pages/cadastroFilmeSuc.jsp" /> </action> ...
ActionForm • De volta ao action... package pec; //imports public class CadastrarFilmeAction extends Action { public ActionForward execute(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws Exception { CadastroFilmeForm cadastroForm = (CadastroFilmeForm) form; //código de efetuar cadastro... return mapping.findForward("sucesso"); } } • Garantia de validação!
ActionForm • cadastrarNovoFilme.jsp <%@ taglib uri="/tags/struts-html" prefix="html"%> <%@ taglib uri="/tags/struts-bean" prefix="bean"%> <html:html locale="true"> <head> <title>Cadastrar Filme</title> </head> <body> <h1>Cadastrar Filme</h1> <html:errors /> <table> <html:form action="cadastrarFilme"> <tr> <td><bean:message key="filme.cadastro.idRef" />*</td> <td><html:text property="idRef" /></td> </tr> <td><bean:message key="filme.cadastro.nomeOriginal" />*</td> <td><html:text property="nomeOriginal" /></td> <tr> <td><bean:message key="filme.cadastro.nomeNacional" /></td> <td><html:text property="nomeNacional" /></td> </tr> ...
ActionForm • cadastrarNovoFilme.jsp (cont) ... <tr> <td><bean:message key="filme.cadastro.numCopias" />*</td> <td><html:text property="numCopias" /></td> </tr> <tr> <td colspan="2"> <html:submit value="Cadastrar"/> <html:cancel value="Cancelar"/> </td> </tr> </html:form> </table> </body> </html:html>
ActionForm • MessageResources.properties # -- cadastro filme success -- filme.cadastro.title=Filme Cadastrado filme.cadastro.heading=Sucesso! filme.cadastro.message=Filme Cadastrado com sucesso! # -- cadastro filme form -- filme.cadastro.idRef=IdRef filme.cadastro.nomeOriginal=NomeOriginal filme.cadastro.nomeNacional=NomeNacional filme.cadastro.numCopias=NúmerodeCópias filme.cadastro.idRef.required=IdRefRequerido filme.cadastro.nomeOriginal.required=NomeOriginalRequerido filme.cadastro.numCopias.required=NúmerodeCópiasRequerido filme.cadastro.numCopias.notInt=NúmerodeCópiasinválido
ActionForm • ActionForm também podem ser usados para fornecer dados ... <form-beans> <form-beanname="filmeForm" type="pec.FilmeForm"/> </form-beans> ... <action-mappings> ... <action path="/verDadosFilme" type="pec.VerDadosFilmeAction" name="filmeForm" scope="request" validate="false"> <forward name="sucesso" path="/pages/filmeForm.jsp" /> </action> ...
ActionForm • Problemas • Muitos objetos de domínio duplicados • Muito código de cópia de propriedades • Usar BeanUtils.copyProperties(Object dest, Object src); • Grande quantidade de Froms com grandes quantidades de propriedades pode ser difícil de manter • Usar DynaActionForm?
Exceções • Struts dá suporte a um tratamento de exceções declarativo • Suponha que o código de negócio de VerDadosFilmeAction lance a exceção pec.FilmeNaoEncontradoException <action path="/verDadosFilme" type="pec.VerDadosFilmeAction" name="filmeForm" scope="request" validate="false"> <forward name="sucesso" path="/pages/filmeForm.jsp" /> <exception key="filmeNaoEncontrado.exception" type="pec.FilmeNaoEncontradoException" path="/pages/exception.jsp" /> </action> ...
O que mais? • Outros tipos de actions • DispatchAction: quando tempos um formulário que terá mais de uma ação associada • Plugins • Struts-Validator • Struts-Tiles
Exercícios • Implemente um aplicação web usando o struts para cadastrar, visualizar, atualizar, remover e listar usuários (CRUD) • Usuários possuem: • Nome, login (único), senha, data de cadastro • Implemente a persistência usando JDBC *