Tapestry Apache - Guia rápido
Apache Tapestry é uma estrutura da web de código aberto escrita em Java. É umcomponent based web framework. Os componentes da tapeçaria são classes Java. Eles não são herdados de uma classe base específica do framework nem da implementação de uma interface e são simplesmente POJOs (Plain old Java Objects).
O recurso importante do Java usado pela tapeçaria é Annotation. As páginas da Web de tapeçaria são construídas usando um ou mais componentes, cada um tendo um modelo baseado em XML e uma classe de componente decorada com várias Anotações de Tapestry. Tapestry pode criar qualquer coisa, desde um pequeno aplicativo da web de uma única página até um enorme que consiste em centenas de páginas.
Benefícios da Tapeçaria
Alguns dos benefícios fornecidos pela tapeçaria são -
- Aplicativos da web altamente escalonáveis.
- API adaptável.
- Estrutura rápida e madura.
- Gerenciamento de armazenamento de estado persistente.
- Inversão de controle embutida.
Características da Tapeçaria
A tapeçaria tem os seguintes recursos -
- Recarregando aula ao vivo
- Relatórios de exceção claros e detalhados
- Estrutura estática, comportamentos dinâmicos.
- Uso extensivo de Plain Old Java Objects (POJOs)
- Codifique menos, forneça mais.
Por que tapeçaria?
Java já tem muitos frameworks web como JSP, Struts, etc., então, por que precisamos de outro framework? A maioria dos Java Web Frameworks de hoje são complexos e têm uma curva de aprendizado íngreme. Eles são antiquados e requerem um ciclo de compilação, teste e implantação para cada atualização.
Por outro lado, Tapestry fornece uma abordagem moderna para a programação de aplicativos da web, fornecendo live class reloading. Enquanto outras estruturas estão introduzindo muitas interfaces, classes abstratas e básicas, Tapestry apenas apresenta um pequeno conjunto de anotações e ainda fornece a capacidade de escrever aplicativos grandes com suporte avançado de AJAX.
Tapestry tenta usar os recursos disponíveis do Java tanto quanto possível. Por exemplo, todas as páginas Tapestry são simplesmente POJOs. Ele não impõe nenhuma interface customizada ou classe base para escrever o aplicativo. Em vez disso, ele usa Annotation (uma opção leve para estender a funcionalidade de uma classe Java) para fornecer recursos. É baseado em testes de batalhaJava Servlet APIe é implementado como um filtro de servlet. Ele fornece uma nova dimensão para a aplicação web e a programação é bastante Simples, Flexível, Compreensível e Robusta.
Fluxo de Trabalho
Vamos discutir a seqüência de ação que ocorre quando uma página de tapeçaria é solicitada.
Step 1 - o Java Servletrecebe a solicitação de página. Este Java Servlet é configurado de forma que a solicitação recebida seja encaminhada para a tapeçaria. A configuração é feita noweb.xmlconforme especificado no programa a seguir. A tag Filter and Filter Mapping redireciona todas as solicitações para o Tapestry Filter .
<!DOCTYPE web-app PUBLIC "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"
"http://java.sun.com/dtd/web-app_2_3.dtd">
<web-app>
<display-name>My Tapestry Application</display-name>
<context-param>
<param-name>tapestry.app-package</param-name>
<param-value>org.example.myapp</param-value>
</context-param>
<filter>
<filter-name>app</filter-name>
<filter-class>org.apache.tapestry5.TapestryFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>app</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
</web-app>
Step 2 - o Tapestry Filter chama o HttpServletRequestHandler Serviço por seu Service() método.
Step 3 - HttpServletRequestHandler armazena a solicitação e resposta em RequestGlobals. Ele também envolve a solicitação e a resposta como um objeto de Solicitação e Resposta e a envia para o RequestHandler.
Step 4 - o RequestHandler é uma abstração em cima de HttpServletRequestda API Servlet. Algumas das características salientes da tapeçaria são feitas emRequestHandlerseção. O recurso de tapeçaria pode ser estendido escrevendo um filtro no RequestHandler. RequestHandler fornece vários filtros integrados, que incluem -
CheckForUpdates Filter- Responsável pelo recarregamento da aula ao vivo. Este filtro verifica as classes java para alterações e atualiza o aplicativo conforme necessário.
Localization Filter - Identificar a localização do usuário e fornecer suporte de localização para o aplicativo.
StaticFiles Filter- Identifica a solicitação estática e aborta o processo. Depois que o processo é abortado, o Java Servlet assume o controle e processa a solicitação.
Error Filter - Captura a exceção não capturada e apresenta a página de relatório de exceção.
O RequestHandler também modifica e armazena a solicitação e a resposta no RequestQlobals e chama o serviço MasterDispatcher.
Step 5 - o MasterDispatcheré responsável por renderizar a página chamando vários despachantes em um pedido específico. Os quatro despachantes principais chamados pelo MasterDispatcher são os seguintes -
RootPath Dispatcher - Reconhece o caminho raiz “/” da solicitação e processa o mesmo da página inicial.
Asset Dispatcher - Ele reconheceu a solicitação de ativo (ativos Java) verificando o padrão de url / ativos / e envia os ativos solicitados como fluxos de bytes.
PageRender Dispatcher- A maioria das operações de tapeçaria são feitas no PageRender Dispatcher e no próximo dispatcher Component Dispatcher. Este dispatcher reconhece a página específica dessa solicitação e seu contexto de ativação (informações extras). Em seguida, ele renderiza essa página específica e a envia ao cliente. Por exemplo, se o URL da solicitação for / product / 12123434, o despachante verificará se alguma classe com o nome product / 12123434 está disponível. Se encontrado, ele chama product / 12123434 class, gera a resposta e envia para o cliente. Caso contrário, verifica a classe do produto. Se encontrado, ele chama a classe de produto com a informação extra 121234434, gera a resposta e a envia ao cliente. Essas informações extras são chamadas de Contexto de Ativação. Se nenhuma classe for encontrada, ele simplesmente encaminha a solicitação para o Component Dispatcher.
Component Dispatcher- O expedidor do componente corresponde ao URL da página com o padrão - / <class_name> / <component_id>: <event_type> / <activation_context>. Por exemplo, / product / grid: sort / asc representa a classe do produto, o componente da grade, o tipo de evento sort e o contexto de ativação asc. Aqui, event_type é opcional e se nenhum for fornecido, a ação do tipo de evento padrão será disparada. Normalmente, a resposta do distribuidor de componentes é enviar um redirecionamento ao cliente. Geralmente, o redirecionamento corresponderá ao PageRender Dispatcher na próxima solicitação e a resposta adequada será enviada ao cliente.
Neste capítulo, discutiremos como instalar o Tapestry em nossa máquina.
Pré-requisito
A única dependência da tapeçaria é Core Java. Tapestry é desenvolvido independentemente, sem usar qualquer biblioteca / estrutura de terceiros. Até mesmo a biblioteca IoC usada pela tapeçaria é desenvolvida do zero. O aplicativo da Web escrito em tapeçaria pode ser construído e implantado no próprio console.
Podemos usar Maven, Eclipse e Jettypara melhorar a experiência de desenvolvimento. O Maven fornece modelos de aplicativos de início rápido e opções para hospedar aplicativos no Jetty, o servidor de desenvolvimento de fato do Java. O Eclipse fornece recursos abrangentes de gerenciamento de projeto e se integra bem ao maven.
Um desenvolvimento de aplicativo de tapeçaria ideal precisa do seguinte -
- Java 1.6 ou posterior
- Apache Maven
- IDE Eclipse
- Jetty Server
Verifique a instalação do Maven
Felizmente, você instalou o Maven em sua máquina. Para verificar a instalação do Maven, digite o comando fornecido abaixo -
mvn --version
Você pode ver a resposta conforme mostrado abaixo -
Apache Maven 3.3.9 (bb52d8502b132ec0a5a3f4c09453c07478323dc5; 2015-1110T22:11:47+05:30)
Maven home: /Users/workspace/maven/apache-maven-3.3.9
Java version: 1.8.0_92, vendor: Oracle Corporation
Java home: /Library/Java/JavaVirtualMachines/jdk1.8.0_92.jdk/Contents/Home/jre
Default locale: en_US, platform encoding: UTF-8
OS name: "mac os x", version: "10.11.4", arch: "x86_64", family: "mac"
Se o Maven não estiver instalado, baixe e instale a versão mais recente do maven visitando o site do Maven .
Baixar Tapeçaria
A última versão da tapeçaria é 5.4 e pode ser baixada do site da Tapestry . Basta baixar o pacote binário . Se usarmos o modelo de início rápido do Maven, não será necessário baixar o Tapestry separadamente. O Maven baixa automaticamente os Tapestry Jars necessários e configura o aplicativo. Discutiremos como criar um aplicativo Tapestry básico usando Maven no próximo capítulo.
Após a instalação do Tapestry, vamos criar um novo projeto inicial usando Maven como mostrado abaixo -
$ mvn archetype:generate -DarchetypeCatalog=http://tapestry.apache.org
Você pode ver a resposta conforme mostrado abaixo -
[INFO] Scanning for projects...
[INFO]
[INFO] ---------------------------------------------------------------------------------
[INFO] Building Maven Stub Project (No POM) 1
[INFO] ---------------------------------------------------------------------------------
[INFO]
[INFO] >>> maven-archetype-plugin:2.4:generate (default-cli) >
generatesources @ standalone-pom >>>
[INFO]
[INFO] <<< maven-archetype-plugin:2.4:generate (default-cli)
< generatesources @ standalone-pom <<<
[INFO]
[INFO] --- maven-archetype-plugin:2.4:generate (default-cli) @ standalone-pom ---
[INFO] Generating project in Interactive mode
[INFO] No archetype defined. Using maven-archetype-quickstart
(org.apache.maven.archetypes:maven-archetype-quickstart:1.0)
Após o Maven construir todas as operações, escolha o arquétipo para criar Tapestry 5 QuickStart projeto da seguinte forma -
Choose archetype -
https://tapestry.apache.org → org.apache.tapestry: quickstart (Tapestry 5 Quickstart Project)
https://tapestry.apache.org → org.apache.tapestry: tapestry-archetype (Tapestry 4.1.6 Archetype)
Escolha um número ou aplique o filtro (formato: [groupId:] artifactId, diferencia maiúsculas de minúsculas e contém):: 1
Agora você receberá uma resposta como a mostrada abaixo -
Choose org.apache.tapestry:quickstart version:
1: 5.0.19
2: 5.1.0.5
3: 5.2.6
4: 5.3.7
5: 5.4.1
Extraia o número da versão QuickStart da seguinte forma -
Choose a number: 5: 5
Aqui, o projeto QuickStart assume a versão para a opção 5, “5.4.1”. Agora, o arquétipo da Tapeçaria pede as seguintes informações, uma por uma, da seguinte forma -
5.1 groupId - Defina o valor da propriedade 'groupId':: com.example
5.2 artifactId - Defina o valor da propriedade 'artifactId':: Myapp
5.3 version - Defina o valor da propriedade 'versão': 1.0-SNAPSHOT::
5.4 package name - Defina o valor da propriedade 'package': com.example:: com.example.Myapp
Agora sua tela pede sua confirmação -
Confirme a configuração das propriedades -
groupId - com.example
artifactId - Myapp
version - 1.0-SNAPSHOT
package - com.example.Myapp
Verifique todas as propriedades e confirme as alterações usando a opção mostrada abaixo -
Y: : Y
Você veria a tela como a mostrada abaixo.
[INFO] ---------------------------------------------------------------------------------
[INFO] Using following parameters for creating project from Archetype: quickstart:5.4.1
[INFO] ---------------------------------------------------------------------------------
[INFO] Parameter: groupId, Value: com.example
[INFO] Parameter: artifactId, Value: Myapp
[INFO] Parameter: version, Value: 1.0-SNAPSHOT
[INFO] Parameter: package, Value: com.example.Myapp
[INFO] Parameter: packageInPathFormat, Value: com/example/Myapp
[INFO] Parameter: package, Value: com.example.Myapp
[INFO] Parameter: version, Value: 1.0-SNAPSHOT
[INFO] Parameter: groupId, Value: com.example
[INFO] Parameter: artifactId, Value: Myapp
[WARNING] Don't override file /Users/workspace/tapestry/Myapp/src/test/java
[WARNING] Don't override file /Users/workspace/tapestry/Myapp/src/main/webapp
[WARNING] Don't override file /Users/workspace/tapestry/Myapp/src/main/resources/com/
example/Myapp
[WARNING] Don't override file /Users/workspace/tapestry/Myapp/src/test/resource
[WARNING] Don't override file /Users/workspace/tapestry/Myapp/src/test/conf
[WARNING] Don't override file /Users/workspace/tapestry/Myapp/src/site
[INFO] project created from Archetype in dir: /Users/workspace/tapestry/Myapp
[INFO] ---------------------------------------------------------------------------------
[INFO] BUILD SUCCESS
[INFO] ---------------------------------------------------------------------------------
[INFO] Total time: 11:28 min
[INFO] Finished at: 2016-09-14T00:47:23+05:30
[INFO] Final Memory: 14M/142M
[INFO] ---------------------------------------------------------------------------------
Aqui, você construiu com sucesso o projeto Tapestry Quick Start. Mova para o local do recém-criadoMyapp com o seguinte comando e comece a codificar.
cd Myapp
Executar aplicativo
Para executar o projeto de esqueleto, use o seguinte comando.
mvn jetty:run -Dtapestry.execution-mode=development
Você tem uma tela como esta,
[INFO] Scanning for projects...
[INFO]
[INFO] ---------------------------------------------------------------------------------
[INFO] Building Myapp Tapestry 5 Application 1.0-SNAPSHOT
[INFO] ---------------------------------------------------------------------------------
........
........
........
Application 'app' (version 1.0-SNAPSHOT-DEV) startup time: 346 ms to build IoC
Registry, 1,246 ms overall.
______ __ ____
/_ __/__ ____ ___ ___ / /_______ __ / __/
/ / / _ `/ _ \/ -_|_-</ __/ __/ // / /__ \
/_/ \_,_/ .__/\__/___/\__/_/ \_, / /____/
/_/ /___/ 5.4.1 (development mode)
[INFO] Started [email protected]:8080
[INFO] Started Jetty Server
A partir de agora, criamos um projeto básico de início rápido no Tapestry. Para visualizar o aplicativo em execução no navegador da web, basta digitar a seguinte URL na barra de endereço e pressionar Enter -
https://localhost:8080/myapp
Aqui, myapp é o nome do aplicativo e a porta padrão do aplicativo no modo de desenvolvimento é 8080.
Usando Eclipse
No capítulo anterior, discutimos sobre como criar um aplicativo Tapestry Quick Start na CLI. Este capítulo explica sobre a criação de um aplicativo esqueleto emEclipse IDE.
Vamos usar um arquétipo Maven para criar o esqueleto do aplicativo. Para configurar um novo aplicativo, você pode seguir as etapas abaixo.
Etapa 1: Abra o Eclipse IDE
Abra seu Eclipse e escolha Arquivo → Novo → Projeto… → opção como mostrado na imagem a seguir.
Agora, escolha a opção de projeto Maven → Maven.
Note - Se o Maven não estiver configurado, configure e crie um projeto.
Após selecionar o projeto Maven, clique em Avançar e novamente no botão Avançar.
Após isso, você obterá uma tela onde deve escolher a opção de configuração. Uma vez configurado, você obterá a seguinte tela.
Etapa 2: configuração do catálogo
Depois que a primeira etapa for concluída, você deve clicar em Add Remote Catalog. Em seguida, adicione as seguintes alterações, conforme mostrado na imagem a seguir.
Agora, o Apache Tapestry Catalog foi adicionado. Em seguida, escolha a opção de filtro org.apache.tapestry quickstart 5.4.1 conforme mostrado abaixo.
Em seguida, clique em Avançar e a tela a seguir aparecerá.
Etapa 3: configurar GroupId, ArtifactId, versão e pacote
Adicione as seguintes alterações à configuração do Catálogo de Tapeçaria.
Em seguida, clique no botão Concluir, agora criamos o primeiro aplicativo de esqueleto. Na primeira vez que você usa o Maven, a criação do projeto pode demorar um pouco, pois o Maven baixa muitas dependências JAR para Maven, Jetty e Tapestry. Depois que o Maven terminar, você verá um novo diretório, MyFirstApplication, na visualização do Package Explorer.
Etapa 4: execute o aplicativo usando o servidor Jetty
Você pode usar o Maven para executar o Jetty diretamente. Clique com o botão direito do mouse no projeto MyFirstApplication em sua visualização Package Explorer e selecione Run As → Maven Build ... você verá a tela mostrada abaixo.
Na caixa de diálogo de configuração, insira a opção de metas como “jetty: run” e clique no botão Run.
Assim que o Jetty for inicializado, você verá a seguinte tela em seu console.
Etapa 5: execute no navegador da web
Digite o seguinte URL para executar o aplicativo em um navegador da web -
https://loclhost:8080/MyFirstApplication
Etapa 6: Pare o servidor Jetty
Para parar o servidor Jetty, clique no ícone do quadrado vermelho em seu console, conforme mostrado abaixo.
Aqui está o layout do código-fonte criado por Maven Quickstart CLI. Além disso, este é o layout sugerido de um aplicativo de tapeçaria padrão.
├── build.gradle
├── gradle
│ └── wrapper
│ ├── gradle-wrapper.jar
│ └── gradle-wrapper.properties
├── gradlew
├── gradlew.bat
├── pom.xml
├── src
│ ├── main
│ │ ├── java
│ │ │ └── com
│ │ │ └── example
│ │ │ └── MyFirstApplication
│ │ │ ├── components
│ │ │ ├── data
│ │ │ ├── entities
│ │ │ ├── pages
│ │ │ └── services
│ │ ├── resources
│ │ │ ├── com
│ │ │ │ └── example
│ │ │ │ └── MyFirstApplication
│ │ │ │ ├── components
│ │ │ │ ├── logback.xml
│ │ │ │ └── pages
│ │ │ │ └── Index.properties
│ │ │ ├── hibernate.cfg.xml
│ │ │ └── log4j.properties
│ │ └── webapp
│ │ ├── favicon.ico
│ │ ├── images
│ │ │ └── tapestry.png
│ │ ├── mybootstrap
│ │ │ ├── css
│ │ │ │ ├── bootstrap.css
│ │ │ │ └── bootstrap-theme.css
│ │ │ ├── fonts
│ ├── glyphicons-halflings-regular.eot
│ │ │ │ ├── glyphicons-halflings-regular.svg
│ │ │ │ ├── glyphicons-halflings-regular.ttf
│ │ │ │ ├── glyphicons-halflings-regular.woff
│ │ │ │ └── glyphicons-halflings-regular.woff2
│ │ │ └── js
│ │ └── WEB-INF
│ │ ├── app.properties
│ │ └── web.xml
│ ├── site
│ │ ├── apt
│ │ │ └── index.apt
│ │ └── site.xml
│ └── test
│ ├── conf
│ │ ├── testng.xml
│ │ └── webdefault.xml
│ ├── java
│ │ └── PLACEHOLDER
│ └── resources
│ └── PLACEHOLDER
└── target
├── classes
│ ├── com
│ │ └── example
│ │ └── MyFirstApplication
│ │ ├── components
│ │ ├── data
│ │ ├── entities
│ │ ├── logback.xml
│ │ ├── pages
│ │ │ └── Index.properties
│ │ └── services
│ ├── hibernate.cfg.xml
│ └── log4j.properties
├── m2e-wtp
│ └── web-resources
│ └── META-INF
│ ├── MANIFEST.MF
│ └── maven
│ └── com.example
│ └──MyFirstApplication
│ ├── pom.properties
│ └── pom.xml
├── test-classes
│ └── PLACEHOLDER
└── work
├── jsp
├── sampleapp.properties
└── sampleapp.script
O layout padrão é organizado como o WAR Internal File Format. Usar o formato WAR ajuda a executar o aplicativo sem empacotar e implantar. Este layout é apenas uma sugestão, mas o aplicativo pode ser organizado em qualquer formato, se for empacotado em um formato WAR adequado durante a implementação.
O código-fonte pode ser dividido nas quatro seções principais a seguir.
Java Code - Todos os códigos-fonte java são colocados em /src/main/javapasta. As classes de página de tapeçaria são colocadas na pasta “Pages” e as classes de componentes de Tapeçaria são colocadas na pasta de componentes. As classes de serviço de tapeçaria são colocadas na pasta de serviços.
ClassPath Resources- No Tapestry, a maioria das classes possui recursos associados (Template XML, arquivos JavaScript, etc.). Esses recursos são colocados sob o/src/main/resourcespasta. As classes de página Tapestry têm seus recursos associados na pasta “Pages” e as classes de componentes Tapestry têm seus recursos associados na pasta Componentes. Esses recursos são empacotados noWEB-INF/classes pasta do WAR.
Context Resources - Eles são recursos estáticos de um aplicativo da web, como imagens, folha de estilo e biblioteca JavaScript / Modules. They are usually placed under the /src/main/webapp pasta e eles são chamados Context Resources. Além disso, o arquivo de descrição do aplicativo da web (de Java Servlet), web.xml, é colocado sob oWEB-INF pasta de recursos de contexto.
Testing Code - Esses são arquivos opcionais usados para testar o aplicativo e colocados sob o src/test/java e src/test/Pastas de recursos. Eles não são incluídos no WAR.
Apache Tapestry segue Convention over Configurationem todos os aspectos da programação. Cada recurso da estrutura tem uma convenção padrão sensata.
Por exemplo, como aprendemos no capítulo Layout do projeto, todas as páginas precisam ser colocadas no /src/main/java/«package_path»/pages/ pasta a ser considerada como páginas de tapeçaria.
Em outro sentido, não há necessidade de configurar uma determinada classe Java como páginas de tapeçaria. Basta colocar a aula em um local pré-definido. Em alguns casos, é estranho seguir a convenção padrão da Tapeçaria.
Por exemplo, o componente Tapestry pode ter um método setupRenderque será disparado no início da fase de renderização. Um desenvolvedor pode querer usar seu próprio nome opinativo, digamosinitializeValue. Nesta situação, Tapestry forneceAnnotation para substituir as convenções conforme mostrado no bloco de código a seguir.
void setupRender() {
// initialize component
}
@SetupRender
void initializeValue() {
// initialize component
}
Ambas as formas de programação são válidas na Tapeçaria. Resumindo, a configuração padrão do Tapestry é mínima. Apenas oApache Tapestry Filter (Java Servlet Filter) precisa ser configurado no “Web.xml” para o bom funcionamento do aplicativo.
Tapestry fornece uma outra maneira de configurar o aplicativo e é chamado de AppModule.java.
A anotação é um recurso muito importante explorado pela Tapestry para simplificar o desenvolvimento de aplicativos da web. Tapestry oferece muitas anotações personalizadas. Possui Anotação para Classes, Métodos e Campos Membros. Conforme discutido na seção anterior, a Anotação também pode ser usada para substituir a convenção padrão de um recurso. As anotações de tapeçaria são agrupadas em quatro categorias principais e são as seguintes.
Anotação de componente
Usado em classes de páginas, componentes e mixins. Algumas das anotações úteis são -
@Property- É aplicável a campos. Usado para converter um campo em uma propriedade de tapeçaria.
@Parameter- É aplicável a campos. Usado para especificar um campo como parâmetro de um componente.
@Environmental- É aplicável a campos. Usado para compartilhar um campo privado entre diferentes componentes.
@import- É aplicável a classes e campos. Usado para incluir Ativos, CSS e JavaScript.
@Path - Usado em conjunto com a anotação @Inject para injetar um Ativo com base em um caminho.
@Log- É aplicável a classes e campos. Usado para fins de depuração. Pode ser usado para emitir informações de evento do componente, como início do evento, fim do evento, etc.
Anotação IoC
Usado para injetar objetos no Container IoC. Algumas das anotações úteis são -
@Inject- É aplicável a campos. Usado para marcar parâmetros que devem ser injetados no contêiner IoC. Ele marca os campos que devem ser injetados nos componentes.
@Value- É aplicável a campos. Usado junto com a anotação @inject para injetar um valor literal em vez de um serviço (que é o comportamento padrão da anotação @Inject).
Anotação para classes de armazenamento de dados
É usado para especificar informações específicas do componente em uma classe (geralmente modelos ou classes de armazenamento de dados) para componentes de alto nível, como
Grid (usado para criar dados tabulares avançados, como relatório, galeria, etc.)
BeanEditForm (Usado para criar formulários avançados)
Hibernate (Usado no acesso avançado ao banco de dados), etc.
Essas anotações são agregadas e empacotadas em um frasco separado, sem qualquer dependência de tapeçaria. Algumas das anotações são -
@DataType- É usado para especificar o tipo de dados do campo. O componente Tapestry pode usar essas informações para criar um design ou marcação na camada de apresentação.
@Validate - É usado para especificar a regra de validação para um campo.
Essas separações permitem que o aplicativo Tapestry use um Multi-Tier Design.
O aplicativo Tapestry é simplesmente uma coleção de páginas de tapeçaria. Eles trabalham juntos para formar um aplicativo da Web bem definido. Cada Página terá um Modelo XML correspondente e Zero, um ou mais Componentes. A Página e o Componente são iguais, exceto que a Página é um componente raiz e geralmente criado por um desenvolvedor de aplicativos.
Components are children of the root Pagecomponent. A tapeçaria tem muitos componentes integrados e tem a opção de criar um componente personalizado.
Páginas
Conforme discutido anteriormente, Pages são blocos de construção de um aplicativo Tapestry. As páginas são POJOs simples, colocadas sob -/src/main/java/«package_path»/pages/pasta. Cada página terá um correspondenteXML Template e seu local padrão é - /src/main/resources/«package_name»/pages/.
Você pode ver aqui que a estrutura do caminho é semelhante para a página e o modelo, exceto que o modelo está no Resource Folder.
Por exemplo, uma página de registro de usuário em um aplicativo Tapestry com o nome do pacote - com.example.MyFirstApplication terá os seguintes arquivos de página e modelo -
Java Class -
/src/main/java/com/example/MyFirstApplication/pages/index.java
XML Template -
/src/main/resources/com/example/MyFirstApplication/pages/index.tml
Vamos criar um simples Hello Worldpágina. Primeiro, precisamos criar umJava Class em - /src/main/java/com/example/MyFirstApplication/pages/HelloWorld.java ”.
package com.example.MyFirstApplication.pages;
public class HelloWorld {
}
Em seguida, crie um modelo XML em -
“/Src/main/resources/com/example/MyFirstApplication/pages/helloworld.html”.
<html xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd">
<head>
<title>Hello World Page</title>
</head>
<body>
<h1>Hello World</h1>
</body>
</html>
Agora, esta página pode ser acessada em https://localhost:8080/myapp/helloworld. Esta é uma página simples de tapeçaria. Tapestry oferece muito mais recursos para desenvolver páginas da Web dinâmicas, que discutiremos nos próximos capítulos.
Vamos considerar o modelo XML Tapestry nesta seção. O modelo XML é um documento XML bem formado. A camada de apresentação (interface do usuário) de uma página é o modelo XML. Um modelo XML tem marcação HTML normal, além dos itens fornecidos abaixo -
- Espaço para nome de tapeçaria
- Expansions
- Elements
- Components
Vamos agora discuti-los em detalhes.
Espaço para nome de tapeçaria
Os namespaces de tapeçaria nada mais são do que namespaces XML. Os namespaces devem ser definidos no elemento raiz do modelo. É usado para incluir componentes de tapeçaria e informações relacionadas a componentes no modelo. Os namespaces mais comumente usados são os seguintes -
xmlns: t = “https://tapestry.apache.org/schema/tapestry_5_4.xsd” - É usado para identificar os Elementos, Componentes e Atributos da Tapeçaria.
xmlns: p = “tapeçaria: parâmetro” - É usado para passar pedaços arbitrários de código para componentes.
Um exemplo de espaço para nome Tapestry é o seguinte -
<html xmlns:t = "https://tapestry.apache.org/schema/tapestry_5_3.xsd"
xmlns:p = "tapestry:parameter">
<head>
<title>Hello World Page</title>
</head>
<body>
<h1>Hello World</h1>
<t:eventlink page = "Index">refresh page</t:eventlink>
</body>
</html>
Expansões
Expansão é um método simples e eficiente para alterar dinamicamente o Modelo XML durante a fase de renderização da Página. A expansão usa a sintaxe $ {<name>}. Existem muitas opções para expressar a expansão no modelo XML. Vejamos algumas das opções mais comumente usadas -
Expansões de propriedade
Ele mapeia a propriedade definida na classe de página correspondente. Ele segue a Especificação Java Bean para definição de propriedade em uma classe Java. Ele vai um passo adiante, ignorando os casos de nome de propriedade. Vamos mudar o exemplo “Hello World” usando expansão de propriedade. O bloco de código a seguir é a classe Page modificada.
package com.example.MyFirstApplication.pages;
public class HelloWorld {
// Java Bean Property
public String getName {
return "World!";
}
}
Em seguida, altere o modelo XML correspondente conforme mostrado abaixo.
<html xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd">
<head>
<title>Hello World Page</title>
</head>
<body>
<!-- expansion -->
<h1>Hello ${name}</h1>
</body>
</html>
Aqui, nós definimos name Como Java Bean Property na classe Page e processou-o dinamicamente no modelo XML usando expansão ${name}.
Expansão da Mensagem
Cada classe de página pode ou não ter um arquivo de propriedade associado - «page_name».propertiesna pasta de recursos. Os arquivos de propriedades são arquivos de texto simples com um único par de chave / valor (mensagem) por linha. Vamos criar um arquivo de propriedades para a página HelloWorld em -
“/Src/main/resources/com/example/MyFirstApplication/pages/helloworld.properties” e adicione uma mensagem de “Saudação”.
Greeting = Hello
o Greeting mensagem pode ser usada no modelo XML como ${message:greeting}
<html xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd">
<head>
<title>Hello World Page</title>
</head>
<body>
<!-- expansion -->
<h1>${message:greeting} ${name}</h1>
</body>
</html>
Elementos
Tapestry possui um pequeno conjunto de elementos para serem usados em Templates XML. Elementos são tags predefinidas definidas no namespace Tapestry -
https://tapestry.apache.org/schema/tapestry_5_4.xsd
Cada elemento é criado para um propósito específico. Os elementos de tapeçaria disponíveis são os seguintes -
<t: body>
Quando dois componentes são aninhados, o modelo do componente pai pode ter que envolver o modelo do componente filho. O elemento <t: body> é útil nessa situação. Um dos usos de <t: body> é no Layout de modelo.
Em geral, a interface do usuário de um aplicativo da web terá um cabeçalho, rodapé, menu comum, etc. Esses itens comuns são definidos em um modelo XML e é chamado de layout de modelo ou componente de layout. No Tapestry, ele precisa ser criado por um desenvolvedor de aplicativos. Um Layout Component é apenas outro componente e é colocado na pasta de componentes, que tem o seguinte caminho -src/main/«java|resources»/«package_name»/components.
Vamos criar um componente de layout simples chamado MyCustomLayout. O código para MyCustomLayout é o seguinte -
<!DOCTYPE html>
<html xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd">
<head>
<meta charset = "UTF-8" />
<title>${title}</title>
</head>
<body>
<div>Sample Web Application</div>
<h1>${title}</h1>
<t:body/>
<div>(C) 2016 TutorialsPoint.</div>
</body>
</html>
package com.example.MyFirstApplication.components;
import org.apache.tapestry5.*;
import org.apache.tapestry5.annotations.*;
import org.apache.tapestry5.BindingConstants;
public class MyCustomLayout {
@Property
@Parameter(required = true, defaultPrefix = BindingConstants.LITERAL)
private String title;
}
Na classe do componente MyCustomLayout, declaramos um campo de título e, usando a anotação, o tornamos obrigatório. Agora, altere o modelo HelloWorld.html para usar nosso layout personalizado, conforme mostrado no bloco de código abaixo.
<html>
t:type = "mycustomlayout" title = "Hello World Test page"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd">
<h1>${message:greeting} ${name}</h1>
</html>
Podemos ver aqui que o Template XML não possui tags head e body. Tapestry coletará esses detalhes do componente de layout e o <t: body> do componente de layout será substituído pelo modelo HelloWorld. Assim que tudo estiver feito, Tapestry emitirá marcação semelhante conforme especificado abaixo -
<!DOCTYPE html>
<html>
<head>
<meta charset = "UTF-8" />
<title>Hello World Test Page</title>
</head>
<body>
<div>Sample Web Application</div>
<h1>Hello World Test Page</h1>
<h1>Hello World!</h1>
<div>(C) 2016 TutorialsPoint.</div>
</body>
</html>
Os layouts podem ser aninhados. Por exemplo, podemos estender nosso layout personalizado incluindo a funcionalidade de administração e usá-la para a seção administrativa conforme especificado abaixo.
<html t:type = "MyCommonLayout"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd">
<div><!-- Admin related items --><div>
<t:body/>
</html>
<t: container>
O <t: container> é um elemento de nível superior e inclui um namespace de tapeçaria. Isso é usado para especificar a seção dinâmica de um componente.
Por exemplo, um componente de grade pode precisar de um modelo para identificar como renderizar suas linhas - tr (e coluna td) em uma tabela HTML.
<t:container xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd">
<td>${name}</td>
<td>${age}</td>
</t:container>
<t: block>
O <t: block> é um espaço reservado para uma seção dinâmica no modelo. Geralmente, o elemento de bloco não é renderizado. Apenas os componentes definidos no modelo usam elemento de bloco. Os componentes injetarão dados dinamicamente no elemento de bloco e os renderizarão. Um dos casos de uso populares éAJAX.
O elemento de bloco fornece a posição exata e marcação para os dados dinâmicos a serem renderizados. Cada elemento de bloco deve ter uma propriedade Java correspondente. Só então ele pode ser renderizado dinamicamente. O id do elemento de bloco deve seguir as regras de identificador de variável Java. A amostra parcial é fornecida abaixo.
@Inject
private Block block;
<html t:type = "mycustomlayout" title = "block example"
xmlns:t = "https://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<h1>${title}</h1>
<!--
...
...
-->
<t:block t:id = "block">
<h2>Highly dynamic section</h2>
I'v been updated through AJAX call
The current time is: <strong>${currentTime}</strong>
</t:block>
<!--
...
...
-->
</html>
<t: conteúdo>
O elemento <t: content> é usado para especificar o conteúdo real do modelo. Em geral, toda a marcação é considerada parte do modelo. Se <t: content> for especificado, apenas a marcação dentro dele será considerada. Este recurso é usado por designers para criar uma página sem um componente de layout.
<t: remove>
O <t: remove> é exatamente o oposto do elemento de conteúdo. A marcação dentro do elemento remove não é considerada parte do template. Ele pode ser usado apenas para comentários do servidor e para fins de design.
Ativos
Ativos são arquivos de recursos estáticos, como folhas de estilo, imagens e arquivos JavaScript. Geralmente, os ativos são colocados no diretório raiz do aplicativo da web/src/main/webapp.
<head>
<link href = "/css/site.css" rel = "stylesheet" type = "text/css"/>
Tapestry também trata os arquivos armazenados no Java Classpathcomo ativos. Tapestry fornece opções avançadas para incluir ativos no modelo por meio da opção de expansão.
Context - Opção para obter ativos disponíveis no contexto web.
<img src = "${context:image/tapestry_banner.gif}" alt = "Banner"/>
asset- Os componentes geralmente armazenam seus próprios ativos dentro do arquivo jar junto com as classes Java. A partir do Tapestry 5.4, o caminho padrão para armazenar ativos no caminho de classe éMETA-INF/assets. Para bibliotecas, o caminho padrão para armazenar ativos éMETA-INF/assets/«library_name»/. asset: também pode ligar context: expansão para obter ativos do contexto da web.
<img src = "${asset:context:image/tapestry_banner.gif}" alt = "Banner"/>
Os ativos podem ser injetados na página ou componente da tapeçaria usando a anotação Injetar e Caminho. O parâmetro para a anotação de caminho é o caminho relativo dos ativos.
@Inject
@Path("images/edit.png")
private Asset icon;
o Path parameter também pode conter símbolos de tapeçaria definidos no AppModule.java seção.
Por exemplo, podemos definir um símbolo, skin.root com o contexto de valor: skins / basic e usá-lo como mostrado abaixo -
@Inject
@Path("${skin.root}/style.css")
private Asset style;
Localização
Incluir recursos por meio de tapeçaria fornece funcionalidade extra. Uma dessas funcionalidades é “Localização”. A tapeçaria verificará o local atual e incluirá os recursos adequados.
Por exemplo, se o local atual é definido como de, então edit_de.png será incluído em vez de edit.png.
CSS
A tapeçaria possui suporte integrado para folhas de estilo. A tapeçaria vai injetartapestry.csscomo parte da pilha Javascript principal. Do Tapestry 5.4, tapeçaria incluibootstrap css frameworktambém. Podemos incluir nossa própria folha de estilo usando a tag de link normal. Neste caso, as folhas de estilo devem estar no diretório raiz da web -/src/main/webapp/.
<head>
<link href = "/css/site.css" rel = "stylesheet" type = "text/css"/>
A tapeçaria oferece opções avançadas para incluir folhas de estilo no modelo por meio da opção de expansão, conforme discutido anteriormente.
<head>
<link href = "${context:css/site.css}" rel = "stylesheet" type = "text/css"/>
Tapestry também fornece anotação de importação para incluir folha de estilo diretamente nas classes Java.
@Import(stylesheet="context:css/site.css")
public class MyCommonLayout {
}
Tapestry oferece muitas opções para gerenciar a folha de estilo por meio de AppModule.java. Algumas das opções importantes são -
A folha de estilo padrão da tapeçaria pode ser removida.
@Contribute(MarkupRenderer.class)
public static void
deactiveDefaultCSS(OrderedConfiguration<MarkupRendererFilter> configuration) {
configuration.override("InjectDefaultStyleheet", null);
}
O bootstrap também pode ser desabilitado substituindo seu caminho.
configuration.add(SymbolConstants.BOOTSTRAP_ROOT, "classpath:/METAINF/assets");
Habilite a minimização dinâmica dos ativos (CSS e JavaScript). Precisamos incluirtapestry-webresources dependência (em pom.xml) também.
@Contribute(SymbolProvider.class)
@ApplicationDefaults
public static void contributeApplicationDefaults(
MappedConfiguration<String, String> configuration) {
configuration.add(SymbolConstants.MINIFICATION_ENABLED, "true");
}
<dependency>
<groupId>org.apache.tapestry</groupId>
<artifactId>tapestry-webresources</artifactId>
<version>5.4</version>
</dependency>
JavaScript do lado do cliente
A geração atual de aplicativos da web depende muito do JavaScript para fornecer uma rica experiência do lado do cliente. Tapestry reconhece e fornece suporte de primeira classe para JavaScript. O suporte a JavaScript está profundamente enraizado na tapeçaria e disponível em todas as fases da programação.
Anteriormente, Tapestry suportava apenas Prototype e Scriptaculous. Mas, a partir da versão 5.4, a tapeçaria reescreveu completamente a camada JavaScript para torná-la o mais genérica possível e fornecer suporte de primeira classe para JQuery, a biblioteca de fato para JavaScript. Além disso, a tapeçaria incentiva a programação JavaScript baseada em Módulos e suporta RequireJS, uma implementação popular do lado do cliente de AMD (Asynchronous Module Definition - especificação JavaScript para suportar módulos e sua dependência de maneira assíncrona).
Localização
Os arquivos JavaScript são ativos do aplicativo Tapestry. De acordo com as regras de ativos, os arquivos JavaScript são colocados no contexto da web,/sr/main/webapp/ ou colocado dentro da jarra sob META-INF/assets/ location.
Vinculando arquivos JavaScript
A maneira mais simples de vincular arquivos JavaScript no modelo XML é usando diretamente a tag de script, que é - <script language = "javascript" src = "relative/path/to/js"></script>. Mas a tapeçaria não recomenda essas abordagens. Tapestry oferece várias opções para vincular arquivos JavaScript diretamente na própria página / componente. Alguns deles são fornecidos abaixo.
@import annotation- A anotação @import fornece a opção de vincular várias bibliotecas JavaScript usando a expressão de contexto. Pode ser aplicado tanto à classe Page quanto ao seu método. Se aplicado a uma classe Page, ele se aplica a todos os seus métodos. Se aplicado a um Método de Página, só se aplica a esse método e, em seguida, Tapestry vincula a biblioteca JavaScript apenas quando o método é invocado.
@Import(library = {"context:js/jquery.js","context:js/myeffects.js"})
public class MyComponent {
// ...
}
JavaScriptSupport interface - O JavaScriptSupport é uma interface definida por tapestry e possui um método, importJavaScriptLibrarypara importar arquivos JavaScript. O objeto JavScriptSupport pode ser facilmente criado simplesmente declarando e anotando com a anotação @Environmental.
@Inject @Path("context:/js/myeffects.js")
private Asset myEffects;
@Environmental
private JavaScriptSupport javaScriptSupport;
void setupRender() {
javaScriptSupport.importJavaScriptLibrary(myEffects);
}
JavaScripSupport só pode ser injetado em um componente usando o @Environmentalanotação. Para serviços, precisamos usar um@Inject anotação ou adicione-a como um argumento no método do construtor de serviço.
@Inject
private JavaScriptSupport javaScriptSupport;
public MyServiceImpl(JavaScriptSupport support) {
// ...
}
addScript method - É semelhante à interface JavaScriptSupport, exceto que usa o addScript método e o código é adicionado diretamente à saída na parte inferior da página.
void afterRender() {
javaScriptSupport.addScript(
"$('%s').observe('click', hideMe());", container.getClientId());
}
Pilha de JavaScript
Tapestry permite que um grupo de arquivos JavaScript e folhas de estilo relacionadas sejam combinados e usados como uma única entidade. Atualmente, Tapestry inclui pilhas baseadas em protótipo e baseadas em JQuery.
Um desenvolvedor pode desenvolver suas próprias pilhas implementando o JavaScriptStack interface e registrá-lo no AppModule.java. Uma vez registrada, a pilha pode ser importada usando o@import anotação.
@Contribute(JavaScriptStackSource.class)
public static void addMyStack(
MappedConfiguration<String, JavaScriptStack> configuration) {
configuration.addInstance("MyStack", myStack.class);
}
@Import(stack = "MyStack")
public class myPage {
}
Conforme discutido anteriormente, Componentes e Páginas são iguais, exceto que a Página é o componente raiz e inclui um ou mais componentes filhos. Os componentes sempre residem dentro de uma página e fazem quase todas as funcionalidades dinâmicas da página.
Os componentes Tapestry renderizam links HTML simples para funcionalidades de grade complexas com interactive AJAX. Um componente pode incluir outro componente também. Os componentes da tapeçaria consistem nos seguintes itens -
Component Class - A principal classe Java do componente.
XML Template- O modelo XML é semelhante ao modelo da página. A classe do componente renderiza o modelo como a saída final. Alguns componentes podem não ter modelos. Neste caso, a saída será gerada pela própria classe do componente usando oMarkupWriter classe.
Body- O componente especificado dentro do modelo de página pode ter marcação personalizada e é chamado de “Corpo do componente”. Se o modelo de componente tiver<body />elemento, então o elemento <body /> será substituído pelo corpo do componente. Isso é semelhante ao layout discutido anteriormente na seção de modelo XML.
Rendering - Renderização é um processo que transforma o modelo XML e o corpo do componente na saída real do componente.
Parameters - Usado para criar comunicação entre componentes e páginas e, assim, passar dados entre eles.
Events- Delega funcionalidade de componentes para seu contêiner / pai (páginas ou outro componente). É amplamente utilizado no propósito de navegação de página.
Renderização
A renderização de um componente é feita em uma série de fases pré-definidas. Cada fase no sistema de componente deve ter um método correspondente definido por convenção ou anotação na classe de componente.
// Using annotaion
@SetupRender
void initializeValues() {
// initialize values
}
// using convention
boolean afterRender() {
// do logic
return true;
}
As fases, seu nome de método e suas anotações estão listados abaixo.
Anotação | Nomes de métodos padrão |
---|---|
@SetupRender | setupRender () |
@BeginRender | beginRender () |
@BeforeRenderTemplate | beforeRenderTemplate () |
@BeforeRenderBody | beforeRenderBody () |
@AfterRenderBody | afterRenderBody () |
@AfterRenderTemplate | afterRenderTemplate () |
@AfterRender | afterRender () |
@CleanupRender | cleanupRender () |
Cada fase tem uma finalidade específica e são as seguintes -
SetupRender
SetupRender inicia o processo de renderização. Geralmente, define os parâmetros do componente.
BeginRender
BeginRender começa a renderizar o componente. Geralmente renderiza a tag de início / início do componente.
BeforeRenderTemplate
BeforeRenderTemplate é usado para decorar o modelo XML, adicionando marcação especial ao redor do modelo. Ele também oferece uma opção para pular a renderização do modelo.
BeforeRenderBody
BeforeRenderTemplate fornece uma opção para pular a renderização do elemento do corpo do componente.
AfterRenderBody
AfterRenderBody será chamado depois que o corpo do componente for renderizado.
AfterRenderTemplate
AfterRenderTemplate será chamado depois que o modelo do componente for renderizado.
AfterRender
AfterRender é a contraparte de BeginRender e geralmente renderiza a tag de fechamento.
CleanupRender
CleanupRender é a contraparte do SetupRender. Ele libera / descarta todos os objetos criados durante o processo de renderização.
O fluxo das fases de renderização não é apenas para frente. Ele vai e volta entre as fases dependendo do valor de retorno de uma fase.
Por exemplo, se o método SetupRender retornar falso, a renderização vai para a fase CleanupRender e vice-versa. Para encontrar uma compreensão clara do fluxo entre as diferentes fases, verifique o fluxo no diagrama abaixo.
Componente Simples
Vamos criar um componente simples, Hello, que terá a mensagem de saída “Hello, Tapestry”. A seguir está o código do componente Hello e seu modelo.
package com.example.MyFirstApplication.components;
public class Hello {
}
<html
xmlns:t = "https://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<div>
<p>Hello, Tapestry (from component).</p>
</div>
</html>
O componente Hello pode ser chamado em um modelo de página como -
<html title = "Hello component test page"
xmlns:t = "https://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<t:hello />
</html>
Da mesma forma, o componente pode renderizar a mesma saída usando MarkupWriter em vez do modelo conforme mostrado abaixo.
package com.example.MyFirstApplication.components;
import org.apache.tapestry5.MarkupWriter;
import org.apache.tapestry5.annotations.BeginRender;
public class Hello {
@BeginRender
void renderMessage(MarkupWriter writer) {
writer.write("<p>Hello, Tapestry (from component)</p>");
}
}
Vamos mudar o template do componente e incluir o elemento <body /> como mostrado no bloco de código abaixo.
<html>
xmlns:t = "https://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<div>
<t:body />
</div>
</html>
Agora, o modelo de página pode incluir corpo na marcação do componente, conforme mostrado abaixo.
<html title = "Hello component test page"
xmlns:t = "https://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<t:hello>
<p>Hello, Tapestry (from page).</p>
</t:hello>
</html>
O resultado será o seguinte -
<html>
<div>
<p>Hello, Tapestry (from page).</p>
</div>
</html>
Parâmetros
O objetivo principal desses parâmetros é criar uma conexão entre um campo do componente e uma propriedade / recurso da página. Usando parâmetros, o componente e sua página correspondente comunicam e transferem dados entre si. Isso é chamadoTwo Way Data Binding.
Por exemplo, um componente de caixa de texto usado para representar a idade em uma página de gerenciamento de usuário obtém seu valor inicial (disponível no banco de dados) por meio do parâmetro. Novamente, depois que a idade do usuário for atualizada e enviada de volta, o componente enviará de volta a idade atualizada por meio do mesmo parâmetro.
Para criar um novo parâmetro na classe do componente, declare um campo e especifique um @Parameteranotação. Este @Parameter tem dois argumentos opcionais, que são -
required- torna o parâmetro obrigatório. A tapeçaria gera exceção se não for fornecida.
value - especifica o valor padrão do parâmetro.
O parâmetro deve ser especificado no modelo de página como atributos da tag do componente. O valor dos atributos deve ser especificado usando Binding Expression / Expansion, que discutimos nos capítulos anteriores. Algumas das expansões que aprendemos anteriormente são -
Property expansion (prop:«val») - Obtenha os dados da propriedade da classe da página.
Message expansion (message:«val») - Obtenha os dados da chave definida no arquivo index.properties.
Context expansion (context:«val») - Obtenha os dados da pasta de contexto da web / src / main / webapp.
Asset expansion (asset:«val») - Obtenha os dados dos recursos incorporados no arquivo jar, / META-INF / assets.
Symbol expansion (symbol:«val») - Obtenha os dados dos símbolos definidos no AppModule.javafile.
A tapeçaria tem muitas expansões mais úteis, algumas das quais são fornecidas abaixo -
Literal expansion (literal:«val») - Uma string literal.
Var expansion (var:«val») - Permite que uma variável renderizada do componente seja lida ou atualizada.
Validate expansion (validate:«val»)- Uma string especializada usada para especificar a regra de validação de um objeto. Por exemplo, valide: obrigatório, minLength = 5.
Translate (translate:«val») - Usado para especificar a classe Conversor (conversão da representação do lado do cliente em representação do lado do servidor) na validação de entrada.
Block (block:«val») - O id do elemento de bloco dentro do modelo.
Component (component:«val») - O id de outro componente no modelo.
Todas as expansões acima são somente leitura, exceto expansão de propriedade e expansão de Var. Eles são usados pelo componente para trocar dados com a página. Ao usar a expansão como valores de atributo,${...}não deve ser usado. Em vez disso, apenas use a expansão sem os símbolos de dólar e colchetes.
Componente Usando Parâmetro
Vamos criar um novo componente, HelloWithParameter, modificando o componente Hello para renderizar dinamicamente a mensagem adicionando um name parâmetro na classe de componente e alterando o modelo de componente e modelo de página de acordo.
Crie uma nova classe de componente HelloWithParameter.java.
Adicione um campo privado e nomeie-o com o @Parameteranotação. Use o argumento necessário para torná-lo obrigatório.
@Parameter(required = true)
private String name;
Adicione um campo privado, o resultado com @Properyanotação. A propriedade do resultado será usada no modelo do componente. O modelo de componente não tem acesso aos campos anotados com@Parameter e só consegue acessar os campos anotados com @Property. As variáveis disponíveis nos modelos de componentes são chamadas de Variáveis de renderização.
@Property
private String result;
Adicione um método RenderBody e copie o valor do parâmetro name para a propriedade result.
@BeginRender
void initializeValues() {
result = name;
}
Adicionar um novo modelo de componente HelloWithParamter.tml e use a propriedade result para renderizar a mensagem.
<div> Hello, ${result} </div>
Adicione uma nova propriedade, Nome de usuário na página de teste (testhello.java).
public String getUsername() {
return "User1";
}
Use o componente recém-criado no modelo de página e defina a propriedade Username no parâmetro name de HelloWithParameter componente.
<t:helloWithParameter name = "username" />
A lista completa é a seguinte -
package com.example.MyFirstApplication.components;
import org.apache.tapestry5.annotations.*;
public class HelloWithParameter {
@Parameter(required = true)
private String name;
@Property
private String result;
@BeginRender
void initializeValues() {
result = name;
}
}
<html
xmlns:t = "https://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<div> Hello, ${result} </div>
</html>
package com.example.MyFirstApplication.pages;
import org.apache.tapestry5.annotations.*;
public class TestHello {
public String getUsername() {
return "User1";
}
}
<html title = "Hello component test page"
xmlns:t = "https://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<t:helloWithParameter name = "username" />
</html>
O resultado será o seguinte -
<div> Hello, User1 </div>
Parâmetro Avançado
Nos capítulos anteriores, analisamos como criar e usar um parâmetro simples em um componente personalizado. Um parâmetro avançado também pode conter marcação completa. Nesse caso, a marcação deve ser especificada dentro da tag do componente, como a subseção no modelo de página. O componente if embutido tem marcação para condição de sucesso e falha. A marcação de sucesso é especificada como o corpo da tag do componente e a marcação de falha é especificada usando umelseparameter.
Vamos ver como usar o ifcomponente. O componente if tem dois parâmetros -
test - Parâmetro baseado em propriedade simples.
Else - Parâmetro avançado usado para especificar marcação alternativa, se a condição falhar
Tapestry verificará o valor da propriedade de teste usando a seguinte lógica e retornará verdadeiro ou falso. Isso é chamadoType Coercion, uma maneira de converter um objeto de um tipo em outro com o mesmo conteúdo.
Se o tipo de dados for String, “Verdadeiro” se não estiver em branco e não for a string literal “Falso” (não diferencia maiúsculas de minúsculas).
Se o tipo de dados for Number, Verdadeiro se diferente de zero.
Se o tipo de dados for Collection, Verdadeiro se não estiver vazio.
Se o tipo de dados for Object, True (desde que não seja nulo).
Se a condição for aprovada, o componente renderizará seu corpo; caso contrário, ele renderiza o corpo do parâmetro else.
A lista completa é a seguinte -
package com.example.MyFirstApplication.pages;
public class TestIf {
public String getUser() {
return "User1";
}
}
<html title = "If Test Page"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<body>
<h1>Welcome!</h1>
<t:if test = "user">
Welcome back, ${user}
<p:else>
Please <t:pagelink page = "login">Login</t:pagelink>
</p:else>
</t:if>
</body>
</html>
Eventos de componente / navegação de página
O aplicativo Tapestry é um collection of Pagesinteragindo uns com os outros. Até agora, aprendemos como criar páginas individuais sem qualquer comunicação entre elas. O objetivo principal de um evento de componente é fornecer interação entre as páginas (dentro das páginas também) usando eventos do lado do servidor. A maioria dos eventos de componentes se origina de eventos do lado do cliente.
Por exemplo, quando um usuário clica em um link em uma página, Tapestry chama a própria página com informações de destino em vez de chamar a página de destino e gera um evento do lado do servidor. A página de tapeçaria irá capturar o evento, processar as informações de destino e fazer um redirecionamento do lado do servidor para a página de destino.
A tapeçaria segue um Post/Redirect/Get (RPG) design patternpara navegação na página. No RPG, quando um usuário faz uma solicitação de postagem enviando um formulário, o servidor processa os dados postados, mas não retorna a resposta diretamente. Em vez disso, ele fará um redirecionamento do lado do cliente para outra página, que produzirá o resultado. Um padrão de RPG é usado para evitar envios de formulários duplicados por meio do botão Voltar do navegador, botão de atualização do navegador, etc., Tapestry fornece um padrão de RPG fornecendo os dois tipos de solicitação a seguir.
Component Event Request- Esse tipo de solicitação tem como alvo um componente específico em uma página e gera eventos dentro do componente. Esta solicitação faz apenas um redirecionamento e não produz a resposta.
Render Request - Esses tipos de solicitações direcionam uma página e transmitem a resposta de volta para o cliente.
Para entender os eventos do componente e a navegação da página, precisamos saber o padrão de URL da solicitação de tapeçaria. O padrão de URL para ambos os tipos de solicitação é o seguinte -
Component Event Requests -
/<<page_name_with_path>>.<<component_id|event_id>>/<<context_information>>
Render Request -
/<<page_name_with_path>>/<<context_information>>
Alguns dos exemplos de padrões de URL são -
A página de índice pode ser solicitada por https://«domain»/«app»/index.
Se a página de índice estiver disponível em uma subpasta admin, ela pode ser solicitada por https://«domain»/«app»/admin/index.
Se o usuário clicar no ActionLink component com id test na página de índice, o URL será https://«domain»/«app»/index.test.
Eventos
Por padrão, Tapestry aumenta OnPassivate e OnActivateeventos para todos os pedidos. Para o tipo de solicitação de evento de componente, a tapeçaria gera um ou mais eventos adicionais, dependendo do componente. O componente ActionLink gera um evento Action, enquanto um componente Form gera vários eventos, comoValidate, Success, etc.,
Os eventos podem ser tratados na classe de página usando o manipulador de método correspondente. O manipulador de método é criado por meio de uma convenção de nomenclatura de método ou por meio do@OnEventanotação. O formato da convenção de nomenclatura do método éOn«EventName»From«ComponentId».
Um evento de ação do componente ActionLink com id test pode ser tratado por um dos seguintes métodos -
void OnActionFromTest() {
}
@OnEvent(component = "test", name = "action")
void CustomFunctionName() {
}
Se o nome do método não tiver nenhum componente específico, o método será chamado para todos os componentes com eventos correspondentes.
void OnAction() {
}
OnPassivate e OnActivate Event
OnPassivate é usado para fornecer informações de contexto para um manipulador de eventos OnActivate. Em geral, Tapestry fornece as informações de contexto e pode ser usado como um argumento no manipulador OnActivateevent.
Por exemplo, se as informações de contexto forem 3 do tipo int, o evento OnActivate pode ser chamado de -
void OnActivate(int id) {
}
Em alguns cenários, as informações de contexto podem não estar disponíveis. Nessa situação, podemos fornecer as informações de contexto ao manipulador de eventos OnActivate por meio do manipulador de eventos OnPassivate. O tipo de retorno do manipulador de eventos OnPassivate deve ser usado como argumento do manipulador de eventos OnActivate.
int OnPassivate() {
int id = 3;
return id;
}
void OnActivate(int id) {
}
Valores de retorno do manipulador de eventos
A tapeçaria emite o redirecionamento da página com base nos valores de retorno do manipulador de eventos. O manipulador de eventos deve retornar qualquer um dos seguintes valores.
Null Response- Retorna valor nulo. Tapestry construirá o URL da página atual e enviará ao cliente como redirecionamento.
public Object onAction() {
return null;
}
String Response- Retorna o valor da string. Tapestry construirá a URL da página que corresponde ao valor e enviará ao cliente como redirecionamento.
public String onAction() {
return "Index";
}
Class Response- Retorna uma classe de página. Tapestry construirá o URL da classe de página retornada e enviará ao cliente como redirecionamento.
public Object onAction() {
return Index.class
}
Page Response- Retorna um campo anotado com @InjectPage. Tapestry irá construir a URL da página injetada e enviar ao cliente como redirecionamento.
@InjectPage
private Index index;
public Object onAction(){
return index;
}
HttpError- Retorna o objeto HTTPError. Tapestry emitirá um erro HTTP do lado do cliente.
public Object onAction(){
return new HttpError(302, "The Error message);
}
Link Response- Retorna uma instância de link diretamente. Tapestry construirá a URL do objeto Link e enviará ao cliente como redirecionamento.
Stream Response - Retorna o StreamResponseobjeto. Tapestry enviará o stream como resposta diretamente ao navegador do cliente. É utilizado para gerar relatórios e imagens diretamente e enviá-los ao cliente.
Url Response - Retorna o java.net.URLobjeto. Tapestry obterá o URL correspondente do objeto e enviará ao cliente como redirecionamento.
Object Response- Retorna qualquer valor diferente dos valores especificados acima. A tapeçaria gerará um erro.
Contexto do Evento
Em geral, o manipulador de eventos pode obter as informações de contexto usando argumentos. Por exemplo, se as informações de contexto forem 3 do tipo int, o manipulador de eventos será -
Object onActionFromTest(int id) {
}
Tapestry trata adequadamente as informações de contexto e as fornece aos métodos por meio de argumentos. Às vezes, Tapestry pode não ser capaz de lidar com isso de forma adequada devido à complexidade da programação. Nesse momento, podemos obter as informações de contexto completas e processar nós mesmos.
Object onActionFromEdit(EventContext context) {
if (context.getCount() > 0) {
this.selectedId = context.get(0);
} else {
alertManager.warn("Please select a document.");
return null;
}
}
Este capítulo explica sobre os componentes embutidos que Tapestry possui com exemplos adequados. Tapestry oferece suporte a mais de 65 componentes integrados. Você também pode criar componentes personalizados. Vamos cobrir alguns dos componentes notáveis em detalhes.
If Component
O componente if é usado para renderizar um bloco condicionalmente. A condição é verificada por um parâmetro de teste.
Crie uma página IfSample.java como mostrado abaixo -
package com.example.MyFirstApplication.pages;
public class Ifsample {
public String getUser() {
return "user1";
}
}
Agora, crie um arquivo de modelo correspondente da seguinte maneira -
<html t:type = "newlayout" title = "About MyFirstApplication"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<h3>If-else component example </h3>
<t:if test = "user">
Hello ${user}
<p:else>
<h4> You are not a Tapestry user </h4>
</p:else>
</t:if>
</html>
Solicitar a página renderizará o resultado conforme mostrado abaixo.
Result - http: // localhost: 8080 / MyFirstApplication / ifsample
A menos e delegar componente
o unless componenté exatamente o oposto do componente if que foi discutido acima. Enquanto odelegate componentnão faz nenhuma renderização por conta própria. Em vez disso, ele normalmente delega a marcação ao elemento de bloco. A menos que e se os componentes podem usar delegate e block para trocar condicionalmente o conteúdo dinâmico.
Crie uma página Unless.java do seguinte modo.
package com.example.MyFirstApplication.pages;
import org.apache.tapestry5.Block;
import org.apache.tapestry5.annotations.Property;
import org.apache.tapestry5.ioc.annotations.Inject;
import org.apache.tapestry5.PersistenceConstants;
import org.apache.tapestry5.annotations.Persist;
public class Unless {
@Property
@Persist(PersistenceConstants.FLASH)
private String value;
@Property
private Boolean bool;
@Inject
Block t, f, n;
public Block getCase() {
if (bool == Boolean.TRUE ) {
return t;
} else {
return f;
}
}
}
Agora, crie um arquivo de modelo correspondente da seguinte maneira -
<html t:type = "newlayout" title = "About MyFirstApplication"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<h4> Delegate component </h4>
<div class = "div1">
<t:delegate to = "case"/>
</div>
<h4> If-Unless component </h4>
<div class = "div1">
<t:if test = "bool">
<t:delegate to = "block:t"/>
</t:if>
<t:unless test = "bool">
<t:delegate to = "block:notT"/>
</t:unless>
</div>
<t:block id = "t">
bool == Boolean.TRUE.
</t:block>
<t:block id = "notT">
bool = Boolean.FALSE.
</t:block>
<t:block id = "f">
bool == Boolean.FALSE.
</t:block>
</html>
Solicitar a página renderizará o resultado conforme mostrado abaixo.
Result - http: // localhost: 8080 / MyFirstApplication / a menos
Componente de Loop
O componente de loop é o componente básico para fazer um loop sobre os itens de uma coleção e renderizar o corpo para cada valor / iteração.
Crie uma página de loop conforme mostrado abaixo -
Loop.java
package com.example.MyFirstApplication.pages;
import org.apache.tapestry5.annotations.Property;
public class Loop {
@Property
private int i;
}
Em seguida, crie o modelo correspondente Loop.tml
Loop.tml
<html t:type = "newlayout" title = "About MyFirstApplication"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<p>This is sample parameter rendering example...</p>
<ol>
<li t:type = "loop" source = "1..5" value = "var:i">${var:i}</li>
</ol>
</html>
O componente de loop tem os seguintes dois parâmetros -
source- Fonte de coleta. 1 a 5 é uma expansão de propriedade usada para criar uma matriz com um intervalo especificado.
var- Variável de renderização. Usado para renderizar o valor atual no corpo do modelo.
Solicitar a página renderizará o resultado conforme mostrado abaixo -
Componente PageLink
Um componente PageLink é usado para vincular uma página de uma página a outra. Crie uma página de teste PageLink conforme abaixo -PageLink.java.
package com.example.MyFirstApplication.pages;
public class PageLink {
}
Em seguida, crie um arquivo de modelo correspondente conforme mostrado abaixo -
PageLink.tml
<html t:type = "newlayout" title = "About MyFirstApplication"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<body>
<h3><u>Page Link</u> </h3>
<div class = "page">
<t:pagelink page = "Index">Click here to navigate Index page</t:pagelink>
<br/>
</div>
</body>
</html>
O componente PageLink tem um parâmetro de página que deve se referir à página de tapeçaria de destino.
Result - http: // localhost: 8080 / myFirstApplication / pagelink
Componente EventLink
O componente EventLink envia o nome do evento e o parâmetro correspondente por meio do URL. Crie uma classe de página EventsLink conforme mostrado abaixo.
EventsLink.java
package com.example.MyFirstApplication.pages;
import org.apache.tapestry5.annotations.Property;
public class EventsLink {
@Property
private int x;
void onActivate(int count) {
this.x = x;
}
int onPassivate() {
return x;
}
void onAdd(int value) {
x += value;
}
}
Em seguida, crie um arquivo de modelo “EventsLink” correspondente da seguinte forma -
EventsLink.tml
<html t:type = "newlayout" title = "About MyFirstApplication"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<h3> Event link example </h3>
AddedCount = ${x}. <br/>
<t:eventlink t:event = "add" t:context = "literal:1">
Click here to add count
</t:eventlink><br/>
</html>
EventLink tem os seguintes dois parâmetros -
Event- O nome do evento a ser disparado no componente EventLink. Por padrão, ele aponta para o id do componente.
Context- É um parâmetro opcional. Ele define o contexto do link.
Result - http: // localhost: 8080 / myFirstApplication / EventsLink
Depois de clicar no valor de contagem, a página exibirá o nome do evento no URL, conforme mostrado na captura de tela de saída a seguir.
Componente ActionLink
O componente ActionLink é semelhante ao componente EventLink, mas envia apenas o ID do componente de destino. O nome do evento padrão é ação.
Crie uma página “ActivationLinks.java” conforme mostrado abaixo,
ActivationLinks.java
package com.example.MyFirstApplication.pages;
import org.apache.tapestry5.annotations.Property;
public class ActivationLinks {
@Property
private int x;
void onActivate(int count) {
this.x = x;
}
int onPassivate() {
return x;
}
void onActionFromsub(int value) {
x -= value;
}
}
Agora, crie um arquivo de modelo correspondente conforme mostrado abaixo -
ActivationLinks.tml
<html t:type = "Newlayout" title = "About MyFirstApplication"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<div class = "div1">
Count = ${count}. <br/>
<t:actionlink t:id = "sub" t:context = "literal:1">
Decrement
</t:actionlink><br/>
</div>
</html>
Aqui o OnActionFromSub método será chamado ao clicar no componente ActionLink.
Result - http: // localhost: 8080 / myFirstApplication / ActivationsLink
Componente de Alerta
Uma caixa de diálogo de alerta é usada principalmente para dar uma mensagem de aviso aos usuários. Por exemplo, se o campo de entrada requer algum texto obrigatório, mas o usuário não fornece nenhuma entrada, então, como parte da validação, você pode usar uma caixa de alerta para fornecer uma mensagem de aviso.
Crie uma página “Alertas” conforme mostrado no programa a seguir.
Alerts.java
package com.example.MyFirstApplication.pages;
public class Alerts {
public String getUser() {
return "user1";
}
}
Em seguida, crie um arquivo de modelo correspondente da seguinte maneira -
Alerts.tml
<html t:type = "Newlayout" title = "About MyFirstApplication"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<h3>Alerts</h3>
<div class = "alert alert-info">
<h5> Welcome ${user} </h5>
</div>
</html>
Um alerta tem três níveis de gravidade, que são -
- Info
- Warn
- Error
O modelo acima é criado usando um alerta de informação. É definido comoalert-info. Você pode criar outras gravidades dependendo da necessidade.
Solicitar a página produzirá o seguinte resultado -
http://localhost:8080/myFirstApplication/Alerts
o Form Componenté usado para criar um formulário na página de tapeçaria para entrada do usuário. Um formulário pode conter campos de texto, campos de data, campos de caixa de seleção, opções de seleção, botão de envio e muito mais.
Este capítulo explica em detalhes alguns dos componentes de formulário notáveis.
Componente de caixa de seleção
Um componente de caixa de seleção é usado para escolher entre duas opções mutuamente exclusivas. Crie uma página usando a caixa de seleção conforme mostrado abaixo -
Checkbox.java
package com.example.MyFirstApplication.pages;
import org.apache.tapestry5.annotations.Property;
public class Checkbox {
@Property
private boolean check1;
@Property
private boolean check2;
}
Agora, crie um modelo correspondente Checkbox.tml como mostrado abaixo -
<html t:type = "newlayout" title = "About MyFirstApplication"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<h3> checkbox component</h3>
<t:form>
<t:checkbox t:id = "check1"/> I have a bike <br/>
<t:checkbox t:id = "check2"/> I have a car
</t:form>
</html>
Aqui, o id do parâmetro da caixa de seleção corresponde ao valor booleano correspondente.
Result - Após solicitar a página, http: // localhost: 8080 / myFirstApplication / checkbox ele produz o seguinte resultado.
Componente TextField
O componente TextField permite ao usuário editar uma única linha de texto. Crie uma páginaText como mostrado abaixo.
Text.java
package com.example.MyFirstApplication.pages;
import org.apache.tapestry5.annotations.Property;
import org.apache.tapestry5.corelib.components.TextField;public class Text {
@Property
private String fname;
@Property
private String lname;
}
Em seguida, crie um modelo correspondente conforme mostrado abaixo - Text.tml
<html t:type = "newlayout" title = "About MyFirstApplication"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<p> Form application </p>
<body>
<h3> Text field created from Tapestry component </h3>
<t:form>
<table>
<tr>
<td>
Firstname: </td> <td><t:textfield t:id = "fname" />
</td>
<td>Lastname: </td> <td> <t:textfield t:id = "lname" /> </td>
</tr>
</table>
</t:form>
</body>
</html>
Aqui, a página de texto inclui uma propriedade chamada fname e lname. Os ids do componente são acessados pelas propriedades.
Solicitar a página produzirá o seguinte resultado -
http://localhost:8080/myFirstApplication/Text
Componente PasswordField
O PasswordField é uma entrada de campo de texto especializada para senha. Crie uma senha de página conforme mostrado abaixo -
Password.java
package com.example.MyFirstApplication.pages;
import org.apache.tapestry5.annotations.Property;
import org.apache.tapestry5.corelib.components.PasswordField;
public class Password {
@Property
private String pwd;
}
Agora, crie um arquivo de modelo correspondente conforme mostrado abaixo -
Password.tml
<html t:type = "newlayout" title = "About MyFirstApplication"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<p> Form application </p>
<h3> Password field created from Tapestry component </h3>
<t:form>
<table>
<tr>
<td> Password: </td>
<td><t:passwordfield t:id = "pwd"/> </td>
</tr>
</table>
</t:form>
</html>
Aqui, o componente PasswordField possui o parâmetro id, que aponta para a propriedade pwd. Solicitar a página produzirá o seguinte resultado -
http://localhost:8080/myFirstApplication/Password
Componente TextArea
O componente TextArea é um controle de texto de entrada de várias linhas. Crie uma página TxtArea conforme mostrado abaixo.
TxtArea.java
package com.example.MyFirstApplication.pages;
import org.apache.tapestry5.annotations.Property;
import org.apache.tapestry5.corelib.components.TextArea;
public class TxtArea {
@Property
private String str;
}
Em seguida, crie um arquivo de modelo correspondente conforme mostrado abaixo.
TxtArea.tml
<html t:type = "newlayout" title = "About MyFirstApplication"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<h3>TextArea component </h3>
<t:form>
<table>
<tr>
<td><t:textarea t:id = "str"/>
</td>
</tr>
</table>
</t:form>
</html>
Aqui, o id do parâmetro do componente TextArea aponta para a propriedade “str”. Solicitar a página produzirá o seguinte resultado -
http://localhost:8080/myFirstApplication/TxtArea**
Selecione o Componente
O componente Selecionar contém uma lista suspensa de opções. Crie uma página SelectOption conforme mostrado abaixo.
SelectOption.java
package com.example.MyFirstApplication.pages;
import org.apache.tapestry5.annotations.Property;
import org.apache.tapestry5.corelib.components.Select;
public class SelectOption {
@Property
private String color0;
@Property
private Color1 color1;
public enum Color1 {
YELLOW, RED, GREEN, BLUE, ORANGE
}
}
Em seguida, crie um modelo correspondente da seguinte maneira -
SelectOption.tml
<html t:type = "newlayout" title = "About MyFirstApplication"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<p> Form application </p>
<h3> select component </h3>
<t:form>
<table>
<tr>
<td> Select your color here: </td>
<td> <select t:type = "select" t:id = "color1"></select></td>
</tr>
</table>
</t:form>
</html>
Aqui, o componente Select tem dois parâmetros -
Type - O tipo da propriedade é um enum.
Id - Id aponta para a propriedade Tapestry “color1”.
Solicitar a página produzirá o seguinte resultado -
http://localhost:8080/myFirstApplication/SelectOption
Componente RadioGroup
O componente RadioGroup fornece um grupo de contêineres para componentes Radio. Os componentes Radio e RadioGroup trabalham juntos para atualizar uma propriedade de um objeto. Este componente deve envolver outros componentes de rádio. Crie uma nova página “Radiobutton.java” como mostrado abaixo -
Radiobutton.java
package com.example.MyFirstApplication.pages;
import org.apache.tapestry5.PersistenceConstants;
import org.apache.tapestry5.annotations.Persist;
import org.apache.tapestry5.annotations.Property;
public class Radiobutton {
@Property
@Persist(PersistenceConstants.FLASH)
private String value;
}
Em seguida, crie um arquivo de modelo correspondente conforme mostrado abaixo -
Radiobutton.tml
<html t:type = "Newlayout" title = "About MyFirstApplication"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<h3>RadioGroup component </h3>
<t:form>
<t:radiogroup t:id = "value">
<t:radio t:id = "radioT" value = "literal:T" label = "Male" />
<t:label for = "radioT"/>
<t:radio t:id = "radioF" value = "literal:F" label = "Female"/>
<t:label for = "radioF"/>
</t:radiogroup>
</t:form>
</html>
Aqui, o ID do componente RadioGroup está vinculado à propriedade “valor”. Solicitar a página produzirá o seguinte resultado.
http://localhost:8080/myFirstApplication/Radiobutton
Enviar componente
Quando um usuário clica em um botão de envio, o formulário é enviado ao endereço especificado na configuração de ação da tag. Crie uma páginaSubmitComponent como mostrado abaixo.
package com.example.MyFirstApplication.pages;
import org.apache.tapestry5.annotations.InjectPage;
public class SubmitComponent {
@InjectPage
private Index page1;
Object onSuccess() {
return page1;
}
}
Agora, crie um arquivo de modelo correspondente conforme mostrado abaixo.
SubmitComponent.tml
<html t:type = "newlayout" title = "About MyFirstApplication"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<h3>Tapestry Submit component </h3>
<body>
<t:form>
<t:submit t:id = "submit1" value = "Click to go Index"/>
</t:form>
</body>
</html>
Aqui, o componente Enviar envia o valor para a página Índice. Solicitar a página produzirá o seguinte resultado -
http://localhost:8080/myFirstApplication/SubmitComponent
Validação de Formulário
A validação do formulário normalmente ocorre no servidor após o cliente inserir todos os dados necessários e, em seguida, enviar o formulário. Se os dados inseridos por um cliente estivessem incorretos ou simplesmente faltando, o servidor teria que enviar todos os dados de volta ao cliente e solicitar que o formulário fosse reenviado com as informações corretas.
Vamos considerar o seguinte exemplo simples para entender o processo de validação.
Crie uma página Validate como mostrado abaixo.
Validate.java
package com.example.MyFirstApplication.pages;
import org.apache.tapestry5.annotations.Property;
import org.apache.tapestry5.PersistenceConstants;
import org.apache.tapestry5.annotations.Persist;
public class Validate {
@Property
@Persist(PersistenceConstants.FLASH)
private String firstName;
@Property
@Persist(PersistenceConstants.FLASH)
private String lastName;
}
Agora, crie um arquivo de modelo correspondente conforme mostrado abaixo.
Validate.tml
<html t:type = "newlayout" title = "About MyFirstApplication"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<t:form>
<table>
<tr>
<td><t:label for = "firstName"/>:</td>
<td><input t:type = "TextField" t:id = "firstName"
t:validate = "required, maxlength = 7" size = "10"/></td>
</tr>
<tr>
<td><t:label for = "lastName"/>:</td>
<td><input t:type = "TextField" t:id = "lastName"
t:validate = "required, maxLength = 5" size = "10"/></td>
</tr>
</table>
<t:submit t:id = "sub" value =" Form validation"/>
</t:form>
</html>
A validação do formulário tem os seguintes parâmetros significativos -
Max - define o valor máximo, por exemplo = «valor máximo, 20».
MaxDate- define a maxDate, por exemplo = «data máxima, 06/09/2013». Da mesma forma, você também pode atribuir MinDate.
MaxLength - maxLength por exemplo = «comprimento máximo, 80».
Min - mínimo.
MinLength - Comprimento mínimo, por exemplo = «comprimento mínimo, 2».
Email - Validação de email que usa regexp padrão de email ^ \ w [._ \ w] * \ w @ \ w [-._ \ w] * \ w \. \ W2,6 $ ou nenhum.
Solicitar a página produzirá o seguinte resultado -
http://localhost:8080/myFirstApplication/Validate
AJAX significa Asynchronous JavaScript and XML. É uma técnica para criar aplicativos da web melhores, mais rápidos e mais interativos com a ajuda deXML, JSON, HTML, CSS, e JavaScript. O AJAX permite enviar e receber dados de forma assíncrona sem recarregar a página da web, por isso é rápido.
Componente de Zona
Um componente de zona é usado para fornecer o conteúdo (marcação), bem como a posição do próprio conteúdo. O corpo do Componente de Zona é usado internamente pela Tapestry para gerar o conteúdo. Uma vez que o conteúdo dinâmico é gerado, Tapestry irá enviá-lo ao cliente, renderizar novamente os dados no lugar correto, acionar e animar o HTML para chamar a atenção do usuário.
Este componente Zone é usado junto com um componente EventLink. Um EventLink tem a opção de vinculá-lo a uma zona específica usando ot:zoneatributos. Assim que a zona for configurada no EventLink, clicar no EventLink irá acionar a atualização da zona. Além disso, os eventos EventLink (refreshZone) podem ser usados para controlar a geração de dados dinâmicos.
Um exemplo simples de AJAX é o seguinte -
AjaxZone.tml
<html t:type = "Newlayout" title = "About MyFirstApplication"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd"
xmlns:p = "tapestry:parameter">
<body>
<h1>Ajax time zone example</h1>
<div class = "div1">
<a t:type = "eventlink" t:event = "refreshZone" href = "#"
t:zone = "timeZone">Ajax Link </a><br/><br/>
<t:zone t:id = "timeZone" id = "timeZone">Time zone: ${serverTime}</t:zone>
</div>
</body>
</html>
AjaxZone.java
package com.example.MyFirstApplication.pages;
import java.util.Date;
import org.apache.tapestry5.annotations.InjectComponent;
import org.apache.tapestry5.corelib.components.Zone;
import org.apache.tapestry5.ioc.annotations.Inject;
import org.apache.tapestry5.services.Request;
public class AjaxZone {
@Inject
private Request request;
@InjectComponent
private Zone timeZone;
void onRefreshPage() {
}
Object onRefreshZone() {
return request.isXHR() ? timeZone.getBody() : null;
}
public Date getServerTime() {
return new Date();
}
}
O resultado será mostrado em: http: // localhost: 8080 / MyFirstApplication / AjaxZone
Neste capítulo, discutiremos sobre a integração de BeanEditForm e Grid componentcom o Hibernate. O Hibernate é integrado à tapeçaria por meio do módulo de hibernação. Para habilitar o módulo de hibernação, adicione a dependência tapestry-hibernate e, opcionalmente,hsqldb no pom.xmlArquivo. Agora, configure a hibernação através dohibernate.cfg.xml arquivo colocado na raiz da pasta de recursos.
pom.xml (parcial)
<dependency>
<groupId>org.apache.tapestry</groupId>
<artifactId>tapestry-hibernate</artifactId>
<version>${tapestry-release-version}</version>
</dependency>
<dependency>
<groupId>org.hsqldb</groupId>
<artifactId>hsqldb</artifactId>
<version>2.3.2</version>
</dependency>
Hibernate.cfg.xml
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<property name = "hibernate.connection.driver_class">
org.hsqldb.jdbcDriver
</property>
<property name = "hibernate.connection.url">
jdbc:hsqldb:./target/work/sampleapp;shutdown = true
</property>
<property name = "hibernate.dialect">
org.hibernate.dialect.HSQLDialect
</property>
<property name = "hibernate.connection.username">sa</property>
<property name = "hibernate.connection.password"></property>
<property name = "hbm2ddl.auto">update</property>
<property name = "hibernate.show_sql">true</property>
<property name = "hibernate.format_sql">true</property>
</session-factory>
</hibernate-configuration>
Vamos ver como criar o employee add page usando o componente BeanEditForm e o employee list pageusando o componente Grid. A camada de persistência é gerenciada pelo módulo Hibernate.
Crie uma classe de funcionário e decore-a com a anotação @Entity. Em seguida, adicione a anotação de validação para os campos relevantes e a anotação relacionada ao hibernate @Id e @GeneratedValue para o campo id. Além disso, crie gênero como tipo de enum.
Employee.java
package com.example.MyFirstApplication.entities;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import org.apache.tapestry5.beaneditor.NonVisual;
import org.apache.tapestry5.beaneditor.Validate;
@Entity
public class Employee {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@NonVisual
public Long id;
@Validate("required")
public String firstName;
@Validate("required")
public String lastName;
@Validate("required")
public String userName;
@Validate("required")
public String password;
@Validate("required")
public String email;
public String phone;
@Validate("required")
public String Street;
@Validate("required")
public String city;
@Validate("required")
public String state;
@Validate("required,regexp=^\\d{5}(-\\d{4})?$")
public String zip;
}
Gender.java (enum)
package com.example.MyFirstApplication.data;
public enum Gender {
Male, Female
}
Crie a página da lista de funcionários, ListEmployee.java na nova pasta funcionário em páginas e arquivo de modelo correspondente ListEmployee.tml em /src/main/resources/pages/employeepasta. Tapestry fornece um URL curto para subpastas, removendo dados repetidos.
Por exemplo, a página ListEmployee pode ser acessada por um URL normal - (/ funcionário / listemployee) e pelo URL curto - (/ funcionário / lista).
Injete a sessão do Hibernate na página da lista usando a anotação @Inject. Defina uma propriedadegetEmployeesna página de lista e preenchê-la com funcionários usando o objeto de sessão injetado. Complete o código para a classe de funcionário conforme mostrado abaixo.
ListEmployee.java
package com.example.MyFirstApplication.pages.employee;
import java.util.List;
import org.apache.tapestry5.annotations.Import;
import org.apache.tapestry5.ioc.annotations.Inject;
import org.hibernate.Session;
import com.example.MyFirstApplication.entities.Employee;
import org.apache.tapestry5.annotations.Import;
@Import(stylesheet="context:mybootstrap/css/bootstrap.css")
public class ListEmployee {
@Inject
private Session session;
public List<Employee> getEmployees() {
return session.createCriteria(Employee.class).list();
}
}
Crie o arquivo de modelo para a classe ListEmployee. O modelo terá dois componentes principais, que são -
PageLink - Criar página de link de funcionário.
Grid- Usado para processar os detalhes do funcionário. O componente de grade tem atributos de origem para injetar lista de funcionários e incluir atributos para incluir os campos a serem renderizados.
ListEmployee.tml (lista todos os funcionários)
<html t:type = "simplelayout" title = "List Employee"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd">
<h1>Employees</h1>
<ul>
<li><t:pagelink page = "employee/create">Create new employee</t:pagelink></li>
</ul>
<t:grid source = "employees"
include = "userName,firstName,lastName,gender,dateOfBirth,phone,city,state"/>
</html>
Crie um arquivo de modelo de criação de funcionário e inclua o componente BeanEditForm. O componente possui os seguintes atributos -
object - Inclui fonte.
reorder - Define a ordem dos campos a serem renderizados.
submitlabel - A mensagem do botão de envio do formulário
A codificação completa é a seguinte -
<html t:type = "simplelayout" title = "Create New Address"
xmlns:t = "http://tapestry.apache.org/schema/tapestry_5_4.xsd">
<t:beaneditform
object = "employee"
submitlabel = "message:submit-label"
reorder = "userName,password,firstName,lastName,
dateOfBirth,gender,email,phone,s treet,city,state,zip" />
</html>
Crie a classe de criação de funcionários e inclua sessão, propriedade do funcionário, página de lista (link de navegação) e defina o evento OnSuccess (local para atualizar os dados) do componente. Os dados da sessão são mantidos no banco de dados usando a sessão de hibernação.
A codificação completa é a seguinte -
package com.example.MyFirstApplication.pages.employee;
import com.example.MyFirstApplication.entities.Employee;
import com.example.MyFirstApplication.pages.employee.ListEmployee;
import org.apache.tapestry5.annotations.InjectPage;
import org.apache.tapestry5.annotations.Property;
import org.apache.tapestry5.hibernate.annotations.CommitAfter;
import org.apache.tapestry5.ioc.annotations.Inject;
import org.hibernate.Session;
public class CreateEmployee {
@Property
private Employee employee;
@Inject
private Session session;
@InjectPage
private ListEmployee listPage;
@CommitAfter
Object onSuccess() {
session.persist(employee);
return listPage;
}
}
Adicione o CreateEmployee.propertiesarquivo e incluir a mensagem a ser usada nas validações de formulário. O código completo é o seguinte -
zip-regexp=^\\d{5}(-\\d{4})?$
zip-regexp-message = Zip Codes are five or nine digits. Example: 02134 or 901251655.
submit-label = Create Employee
A captura de tela da página de criação de funcionários e da página de listagem são mostradas abaixo -
Cada aplicativo da web deve ter alguma maneira de armazenar certos dados do usuário, como objeto do usuário, preferências do usuário, etc. Por exemplo, em um aplicativo de carrinho de compras, os itens / produtos selecionados do usuário devem ser salvos em um depósito temporário (carrinho) até que o usuário prefira para comprar os produtos. Podemos salvar os itens em um banco de dados, mas será muito caro, pois nem todos os usuários comprarão os itens selecionados. Portanto, precisamos de um arranjo temporário para armazenar / manter os itens. Apache Tapestry fornece duas maneiras de persistir os dados e são -
- Dados da página de persistência
- Armazenamento de Sessão
Ambos têm suas próprias vantagens e limitações. Verificaremos nas seções a seguir.
Dados da página de persistência
Os dados da página de persistência são um conceito simples para persistir dados em uma única página entre as solicitações e também é chamado de Page Level Persistence. Isso pode ser feito usando o@Persist anotação.
@Persist
public int age;
Depois que um campo é anotado com @Persist, o valor do campo será persistido na solicitação e se o valor for alterado durante a solicitação, será refletido quando for acessado na próxima vez. O Apache Tapestry fornece cinco tipos de estratégia para implementar o conceito @Persist. Eles são os seguintes -
Session Strategy - Os dados são persistidos usando a Sessão e é uma estratégia padrão.
Flash Strategy- Os dados são persistidos usando a Sessão também, mas é de curta duração. Os dados estarão disponíveis em apenas uma solicitação subsequente.
@Persist(PersistenceConstants.FLASH)
private int age;
Client Strategy - Os dados são mantidos no lado do cliente, como string de consulta de URL, campo oculto no formulário etc.
@Persist(PersistenceConstants.FLASH)
private int age;
Hibernate Entity Strategy- Os dados são persistidos usando o módulo Hibernate como Entidade. A entidade será armazenada no Hibernate e sua referência (nome da classe Java e sua chave primária) será salva como token noHttpSession. A entidade será restaurada usando o token disponível em HttpSession.
@Persist(HibernatePersistenceConstants.ENTITY)
private Category category;
JPA Entity Strategy- Os dados são persistidos usando um módulo JPA. Só será capaz de armazenar Entidade.
@Persist(JpaPersistenceConstants.ENTITY)
private User user;
Armazenamento de Sessão
Armazenamento de sessão é um conceito avançado usado para armazenar dados que precisam estar disponíveis nas páginas, como dados no assistente de várias páginas, detalhes do usuário conectado, etc. O Armazenamento de sessão oferece duas opções, uma para armazenar objetos complexos e outra para armazenar valores simples
Session Store Object - Usado para armazenar objetos complexos.
Session Attributes - Usado para armazenar valores simples.
Objeto de armazenamento de sessão (SSO)
Um SSO pode ser criado usando @SessionStoreanotação. O SSO armazenará o objeto usando o tipo do objeto. Por exemplo, oCart Objectserá armazenado usando um nome de classe Cart como token. Portanto, qualquer objeto complexo pode ser armazenado uma vez em um aplicativo (um por usuário).
public class MySSOPage {
@SessionState
private ShoppingCart cart;
}
Um SSO é um armazenamento especializado e deve ser usado para armazenar apenas objetos complexos / especiais. Tipos de dados simples também podem ser armazenados usando um SSO, mas armazenar tipos de dados simples como String faz com que ele armazene apenas um valor de “String” no aplicativo. Usar um único valor de “String” no aplicativo simplesmente não é possível. Você pode usar tipos de dados simples, pois o Apache Tapestry fornece atributos de sessão.
Atributos de sessão
Os atributos da sessão permitem que os dados sejam armazenados por nome em vez de por tipo.
public class MyPage {
@SessionAttribute
private String loggedInUsername;
}
Por padrão, os Atributos da sessão usam o nome do campo para referir-se aos dados na sessão. Podemos alterar o nome de referência por parâmetro de anotação, conforme mostrado abaixo -
public class MyPage {
@SessionAttribute("loggedInUserName")
private String userName;
}
Um dos principais problemas ao usar o nome como referência de sessão é que podemos acidentalmente usar o mesmo nome em mais de uma aula / página. Nesse caso, os dados armazenados podem ser alterados de forma inesperada. Para corrigir esse problema, será melhor usar o nome junto com o nome da classe / página e o nome do pacote comocom.myapp.pages.register.email, em que com.myapp.pages é o nome do pacote, register é o nome da página / classe e, finalmente, email é o nome da variável (a ser armazenada).
Neste capítulo, discutiremos alguns recursos avançados do Apache Tapestry em detalhes.
Inversão de controle
Tapestry fornece biblioteca de Inversão de Controle integrada. Tapestry está profundamente integrado ao IoC e usa IoC para todos os seus recursos. A configuração do Tapestry IoC é baseada no próprio Java em vez de XML, como muitos outros contêineres IoC. Módulos baseados em Tapestry IoC são empacotados em arquivo JAR e simplesmente colocados no classpath com configuração zero. O uso de IoC de tapeçaria é baseado na leveza, o que significa -
Pequenas interfaces de dois ou três métodos.
Métodos pequenos com dois ou três parâmetros.
Comunicação anônima por meio de eventos, em vez de invocações de método explícitas.
Módulos
Módulo é uma forma de estender a funcionalidade do aplicativo Tapestry. Tapestry tem módulos integrados e um grande número de módulos de terceiros. O Hibernate é um dos módulos quentes e muito úteis fornecidos pela Tapestry. Ele também tem módulos que integram JMX, JPA, Spring Framework, JSR 303 Bean Validation, JSON, etc. Alguns dos módulos de terceiros notáveis são -
- Tapestry-Cayenne
- Tapestry5-googleanalytics
- Gang of tapestry 5 - Tapestry5-HighCharts
- Gang of tapestry 5 - Tapestry5-jqPlot
- Gang of tapestry 5 - Tapestry5-Jquery
- Gang of tapestry 5 - Tapestry5-Jquery-mobile
- Gang of tapestry 5 - Tapestry5-Portlet
Exceções de tempo de execução
Uma das melhores características da tapeçaria é Detailed Error Reporting. Tapestry ajuda um desenvolvedor fornecendo relatórios de exceção de última geração. O relatório de exceção de tapeçaria é um HTML simples com informações detalhadas. Qualquer pessoa pode entender facilmente o relatório. Tapestry mostra o erro em HTML, bem como salva a exceção em um texto simples com data e hora em que ocorreu a exceção. Isso ajudará o desenvolvedor a verificar a exceção no ambiente de produção também. O desenvolvedor pode permanecer confiante em corrigir quaisquer problemas como modelos quebrados, valores nulos inesperados, solicitação sem correspondência, etc.,
Aula ao vivo e recarregamento de modelos
Tapestry irá recarregar os modelos e classes automaticamente quando modificados. Esse recurso permite a reflexão imediata das alterações do aplicativo sem passar pelo ciclo de construção e teste. Além disso, esse recurso melhora muito a produtividade do desenvolvimento de aplicativos.
Considere que o pacote raiz do aplicativo é org.example.myfirstapp. Em seguida, as classes nos caminhos a seguir são verificadas para recarregamento.
- org.example.myfirstapp.pages
- org.example.myfirstapp.components
- org.example.myfirstapp.mixins
- org.example.myfirstapp.base
- org.example.myfirstapp.services
O recarregamento da aula ao vivo pode ser desabilitado configurando o modo de produção para true dentro AppModule.java.
configuration.add(SymbolicConstants.PRODUCTION_MODE,”false”);
Teste de Unidade
O teste de unidade é uma técnica pela qual páginas e componentes individuais são testados. Tapestry oferece opções fáceis para páginas e componentes de teste de unidade.
Teste de unidade de uma página: Tapestry fornece uma aula PageTesterpara testar o aplicativo. Isso atua como o navegador e o contêiner do servlet. Ele renderiza a página sem o navegador no próprio lado do servidor e o documento resultante pode ser verificado quanto à renderização correta. Considere uma página simplesHello, que renderiza hello e o texto hello é colocado dentro de um elemento html com id hello_id. Para testar esse recurso, podemos usar o PageTester conforme mostrado abaixo -
public class PageTest extends Assert {
@Test
public void test1() {
Sring appPackage = "org.example.myfirstapp"; // package name
String appName = "App1"; // app name
PageTester tester = new PageTester(appPackage, appName, "src/main/webapp");
Document doc = tester.renderPage("Hello");
assertEquals(doc.getElementById("hello_id").getChildText(), "hello");
}
}
O PageTester também oferece a opção de incluir informações de contexto, envio de formulário, navegação de link, etc., além de renderizar a página.
Teste Integrado
O teste integrado ajuda a testar o aplicativo como um módulo em vez de verificar as páginas individuais como no teste de unidade. No teste integrado, vários módulos podem ser testados juntos como uma unidade. Tapestry oferece uma pequena biblioteca chamadaTapestry Test Utilitiespara fazer testes integrados. Esta biblioteca se integra com a ferramenta de teste Selenium para realizar o teste. A biblioteca fornece uma classe baseSeleniumTestCase, que inicia e gerencia o servidor Selenium, o cliente Selenium e a instância Jetty.
Um dos exemplos de teste integrado é o seguinte -
import org.apache.tapestry5.test.SeleniumTestCase;
import org.testng.annotations.Test;
public class IntegrationTest extends SeleniumTestCase {
@Test
public void persist_entities() {
open("/persistitem");
assertEquals(getText("//span[@id='name']").length(), 0);
clickAndWait("link = create item");
assertText("//span[@id = 'name']", "name");
}
}
Painel de Desenvolvimento
O painel de desenvolvimento é a página padrão que é usada para identificar / resolver os problemas em seu aplicativo. O painel é acessado pelo URLhttp://localhost:8080/myfirstapp/core/t5dashboard. O painel mostra todas as páginas, serviços e bibliotecas de componentes disponíveis no aplicativo.
Compressão de Resposta
Tapeçaria compacta automaticamente a resposta usando GZIP compressione transmitir para o cliente. Esse recurso reduzirá o tráfego da rede e ajudará na entrega mais rápida da página. A compressão pode ser configurada usando o símbolotapestry.min-gzip-sizeem AppModule.java. O valor padrão é 100 bytes. A tapeçaria compactará a resposta assim que o tamanho da resposta ultrapassar 100 bytes.
Segurança
O Tapestry oferece muitas opções para proteger o aplicativo contra vulnerabilidades de segurança conhecidas no aplicativo da web. Algumas dessas opções estão listadas abaixo -
HTTPS - As páginas de tapeçaria podem ser anotadas com @Secure para torná-la uma página segura e acessível pelo https protocol só.
Page access control - Controlar a página a ser acessada por um determinado usuário apenas.
White-Listed Page - As páginas de tapeçaria podem ser anotadas com um @WhitelistAccessOnly para torná-lo acessível apenas por meio do localhost.
Asset Security- Sob a tapeçaria, apenas certos tipos de arquivos estão acessíveis. Outros podem ser acessados apenas quando oMD5 hash do arquivo é fornecido.
Serialized Object Date - Tapestry integra um HMAC em dados de objeto Java serializados e os envia ao cliente para evitar adulteração de mensagens.
Cross Site Request Forgery- Tapeçaria fornece a 3 rd módulo parte chamada tapeçaria-csrf-protecção para evitar ataques CSRF.
Security Framework integration- Tapestry não trava em uma única implementação de autenticação / autorização. O Tapestry pode ser integrado a qualquer estrutura de autenticação popular.
Exploração madeireira
Tapestry fornece amplo suporte para registro, a gravação automática do andamento do aplicativo enquanto ele é executado. Tapestry usa a biblioteca de registro Java de fato,SLF4J. A anotação@Logpode estar em qualquer método de componente para emitir a entrada e saída do método e também a possível exceção. Além disso, o objeto logger fornecido pela Tapestry pode ser injetado em qualquer componente usando o@Inject anotação conforme mostrado abaixo -
public class MyPage {
@Inject
private Logger logger;
// . . .
void onSuccessFromForm() {
logger.info("Changes saved successfully");
}
@Log
void onValidateFromForm() {
// logic
}
}
Finalmente, podemos agora dizer que o Apache Tapestry traz as melhores maneiras de construir aplicativos concisos, escaláveis, sustentáveis, robustos e habilitados para Ajax. Tapestry pode ser integrado a qualquer aplicativo Java de terceiros. Também pode ajudar na criação de um grande aplicativo da web, pois é muito fácil e rápido.