Bem-vindo ao Tutorial de Exemplo JSP para Iniciantes. Nos últimos posts, escrevi bastante sobre Java Servlet e recebemos uma ótima resposta dos nossos leitores. Então, eu comecei outra série sobre tutoriais de JSP e este é o primeiro post da série.
Tutorial de Exemplo JSP
Neste tutorial de exemplo JSP, vamos examinar os conceitos básicos de JSP, vantagens do JSP sobre Servlets, Ciclo de Vida do JSP, interfaces e Classes da API JSP e onde podemos colocar arquivos JSP na aplicação web. Também iremos analisar os Comentários JSP, Scriptlets, Diretivas, Expressões, Declarações e atributos JSP de forma sucinta. Alguns desses tópicos são muito importantes e vamos explorá-los com mais detalhes em posts futuros.
Tutorial JSP
- O que é JSP e por que precisamos de JSP?
- Vantagens do JSP sobre Servlets?
- Ciclo de vida da página JSP
- Métodos do ciclo de vida do JSP
- Exemplo simples de JSP com Eclipse e Tomcat
- Localização dos arquivos JSP no arquivo WAR da aplicação web
- Interfaces e classes da API JSP
- Interface JspPage
- Interface HttpJspPage
- Classe abstrata JspWriter
- Classe abstrata JspContext
- Classe abstrata PageContext
- Classe abstrata JspFactory
- Classe abstrata JspEngineInfo
- Classe final ErrorData
- Classe JspException
- Classe JspTagException
- Classe SkipPageException
-
Código Fonte Transformado JSP e Localização do Arquivo de Classe no Tomcat
-
O que é JSP e por que precisamos de JSP?
O JSP (JavaServer Pages) é uma tecnologia do lado do servidor para criar aplicações web Java dinâmicas. O JSP pode ser considerado uma extensão da tecnologia servlet porque oferece recursos para criar facilmente visualizações de usuário. Uma página JSP consiste em código HTML e oferece a opção de incluir código Java para conteúdo dinâmico. Como as aplicações web contêm muitas telas de usuário, os JSPs são amplamente utilizados em aplicações web. Para preencher a lacuna entre o código Java e HTML em JSP, ele fornece recursos adicionais, como Tags JSP, Linguagem de Expressão, Tags Personalizadas. Isso facilita o entendimento e ajuda um desenvolvedor web a desenvolver rapidamente páginas JSP.
-
Vantagens do JSP sobre Servlets?
- Podemos gerar uma resposta HTML a partir de servlets, mas o processo é complicado e propenso a erros. Quando se trata de escrever uma resposta HTML complexa, escrever em um servlet pode ser um pesadelo. O JSP ajuda nessa situação e nos fornece flexibilidade para escrever uma página HTML normal e incluir nosso código Java apenas onde é necessário.
- O JSP oferece recursos adicionais, como bibliotecas de tags, linguagem de expressão, tags personalizadas que auxiliam no desenvolvimento mais rápido das visualizações do usuário.
- As páginas JSP são fáceis de implantar, precisamos apenas substituir a página modificada no servidor e o contêiner cuida da implantação. Para servlets, precisamos recompilar e implantar todo o projeto novamente. Na verdade, Servlets e JSPs se complementam. Devemos usar Servlet como controlador do lado do servidor e para se comunicar com as classes de modelo, enquanto JSPs devem ser usados para a camada de apresentação.
-
Ciclo de vida da página JSP
O ciclo de vida do JSP também é gerenciado pelo contêiner. Normalmente, todo contêiner da web que contém o contêiner de servlet também contém o contêiner JSP para gerenciar as páginas JSP. As fases do ciclo de vida das páginas JSP são:
- Tradução – As páginas JSP não se parecem com classes Java normais, na verdade, o contêiner JSP analisa as páginas JSP e as traduz para gerar o código-fonte do servlet correspondente. Se o nome do arquivo JSP for home.jsp, geralmente ele é nomeado como home_jsp.java.
- Compilação – Se a tradução for bem-sucedida, então o contêiner compila o arquivo de origem do servlet gerado para gerar o arquivo de classe.
- Carregamento de Classe – Uma vez que o JSP é compilado como classe de servlet, seu ciclo de vida é semelhante ao servlet e ele é carregado na memória.
- Criação de Instância – Após a classe JSP ser carregada na memória, seu objeto é instanciado pelo contêiner.
- Inicialização – A classe JSP é então inicializada e transforma-se de uma classe normal para servlet. Após a inicialização, os objetos ServletConfig e ServletContext tornam-se acessíveis para a classe JSP.
- Processamento de Requisição – Para cada solicitação do cliente, uma nova thread é criada com ServletRequest e ServletResponse para processar e gerar a resposta HTML.
- Destruição – Última fase do ciclo de vida do JSP onde é descarregado da memória.
-
Métodos de ciclo de vida do JSP
Os métodos de ciclo de vida do JSP são:
- jspInit() declarado na interface JspPage. Este método é chamado apenas uma vez no ciclo de vida do JSP para inicializar os parâmetros de configuração.
- _jspService(HttpServletRequest request, HttpServletResponse response) declarado na interface HttpJspPage e responsável por lidar com solicitações do cliente.
- jspDestroy() declarado na interface JspPage para descarregar o JSP da memória.
-
Exemplo Simples de JSP com Eclipse e Tomcat
We can use Eclipse IDE for building dynamic web project with JSPs and use Tomcat to run it. Please read [Java Web Applications](/community/tutorials/java-web-application-tutorial-for-beginners#first-web-app-servlet) tutorial to learn how can we easily create JSPs in Eclipse and run it in tomcat. A simple JSP example page example is: `home.jsp`
```
<%@ page language="java" contentType="text/html; charset=US-ASCII"
pageEncoding="US-ASCII"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "https://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
<title>First JSP</title>
</head>
<%@ page import="java.util.Date" %>
<body>
<h3>Hi Pankaj</h3><br>
<strong>Current Time is</strong>: <%=new Date() %>
</body>
</html>
```
If you have a simple JSP that uses only JRE classes, we are not required to put it as WAR file. Just create a directory in the tomcat webapps folder and place your JSP file in the newly created directory. For example, if your JSP is located at apache-`tomcat/webapps/test/home.jsp`, then you can access it in browser with URL `https://localhost:8080/test/home.jsp`. If your host and port is different, then you need to make changes in URL accordingly.
We can place JSP files at any location in the WAR file, however if we put it inside the WEB-INF directory, we wont be able to access it directly from client. We can configure JSP just like servlets in web.xml, for example if I have a JSP example page like below inside WEB-INF directory: `test.jsp`
```
<%@ page language="java" contentType="text/html; charset=US-ASCII"
pageEncoding="US-ASCII"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "https://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
<title>Test JSP</title>
</head>
<body>
Test JSP Page inside WEB-INF folder.<br>
Init Param "test" value =<%=config.getInitParameter("test") %><br>
HashCode of this object=<%=this.hashCode() %>
</body>
</html>
```
And I configure it in web.xml configuration as:
```
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="https://www.w3.org/2001/XMLSchema-instance" xmlns="https://java.sun.com/xml/ns/javaee" xsi:schemaLocation="https://java.sun.com/xml/ns/javaee https://java.sun.com/xml/ns/javaee/web-app_3_0.xsd" version="3.0">
<display-name>FirstJSP</display-name>
<servlet>
<servlet-name>Test</servlet-name>
<jsp-file>/WEB-INF/test.jsp</jsp-file>
<init-param>
<param-name>test</param-name>
<param-value>Test Value</param-value>
</init-param>
</servlet>
<servlet-mapping>
<servlet-name>Test</servlet-name>
<url-pattern>/Test.do</url-pattern>
</servlet-mapping>
<servlet>
<servlet-name>Test1</servlet-name>
<jsp-file>/WEB-INF/test.jsp</jsp-file>
</servlet>
<servlet-mapping>
<servlet-name>Test1</servlet-name>
<url-pattern>/Test1.do</url-pattern>
</servlet-mapping>
</web-app>
```
Then I can access it with both the URLs https://localhost:8080/FirstJSP/Test.do and https://localhost:8080/FirstJSP/Test1.do Notice that container will create two instances in this case and both will have their own servlet config objects, you can confirm this by visiting these URLs in browser. For Test.do URI, you will get response like below.
```
Test JSP Page inside WEB-INF folder.
Init Param "test" value =Test Value
HashCode of this object=1839060256
```
For Test1.do URI, you will get response like below.
```
Test JSP Page inside WEB-INF folder.
Init Param "test" value =null
HashCode of this object=38139054
```
Notice the init param value in second case is null because it's not defined for the second servlet, also notice the hashcode is different. If you will make further requests, the hashcode value will not change because the requests are processed by spawning a new thread by the container. Did you noticed the use of **config** variable in above JSP example but there is no variable declared, it's because its one of the 9 implicit objects available in JSP page, read more about them at [**JSP Implicit Objects**](/community/tutorials/jsp-implicit-objects "JSP Implicit Objects with Examples").
All the core JSP interfaces and classes are defined in `javax.servlet.jsp` package. Expression Language API interfaces are classes are part of `javax.servlet.jsp.el` package. JSP Tag Libraries interfaces and classes are defined in `javax.servlet.jsp.tagext` package. Here we will look into interfaces and classes of Core JSP API.
-
Interface JspPage
A interface JspPage estende a interface Servlet e declara os métodos do ciclo de vida jspInit() e jspDestroy() das páginas JSP.
-
Interface HttpJspPage
A interface HttpJspPage descreve a interação que uma Classe de Implementação de Página JSP deve satisfazer ao usar o protocolo HTTP. Esta interface declara o método de serviço da página JSP para o protocolo HTTP como public void _jspService(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException.
-
Classe Abstrata JspWriter
Similar ao PrintWriter em servlets com suporte adicional de buffering. Esta é uma das variáveis implícitas em uma página JSP com o nome “out”. Esta classe estende java.io.Writer e o contêiner fornece sua própria implementação para esta classe abstrata e a utiliza ao traduzir a página JSP para Servlet. Podemos obter seu objeto usando o método PageContext.getOut(). A classe concreta do Apache Tomcat para JspWriter é
org.apache.jasper.runtime.JspWriterImpl
. -
Classe Abstrata JspContext
JspContext serve como a classe base para a classe PageContext e abstrai todas as informações que não são específicas para servlets. O JspContext fornece um mecanismo para obter o JspWriter para saída, um mecanismo para trabalhar com atributos e uma API para gerenciar os vários namespaces escalonados.
-
Classe Abstrata PageContext
PageContext estende JspContext para fornecer informações de contexto úteis quando JSP é usada para aplicações web. Uma instância de PageContext fornece acesso a todos os namespaces associados a uma página JSP, fornece acesso a vários atributos da página, bem como uma camada acima dos detalhes de implementação. Objetos implícitos são adicionados ao pageContext automaticamente.
-
Classe Abstrata JspFactory
A JspFactory é uma classe abstrata que define uma série de métodos de fábrica disponíveis para uma página JSP em tempo de execução, com o propósito de criar instâncias de várias interfaces e classes utilizadas para suportar a implementação JSP.
-
Classe Abstrata JspEngineInfo
A JspEngineInfo é uma classe abstrata que fornece informações sobre o motor JSP atual.
-
Classe final ErrorData
Contém informações sobre um erro, para páginas de erro.
-
Classe JspException
Uma exceção genérica conhecida pelo contêiner JSP, similar a ServletException. Se as páginas JSP lançarem JspException, o mecanismo de página de erro é usado para apresentar informações de erro ao usuário.
-
Classe JspTagException
Exceção a ser usada por um Manipulador de Tag para indicar algum erro irreparável.
-
Classe SkipPageException
Exceção para indicar que a página de chamada deve interromper a avaliação. Lançada por um manipulador de tag simples para indicar que o restante da página não deve ser avaliado. Esta exceção não deve ser lançada manualmente em uma página JSP.
Since JSP is built on top of HTML, we can write comments in JSP file like html comments as `<-- This is HTML Comment -->` These comments are sent to the client and we can look it with view source option of browsers. We can put comments in JSP files as: `<%-- This is JSP Comment--%>` This comment is suitable for developers to provide code level comments because these are not sent in the client response.
Scriptlet tags are the easiest way to put java code in a JSP page. A scriptlet tag starts with `<%` and ends with `%>`. Any code written inside the scriptlet tags go into the `_jspService()` method. For example:
```
<%
Date d = new Date();
System.out.println("Current Date="+d);
%>
```
Since most of the times we print dynamic data in JSP page using _out.print()_ method, there is a shortcut to do this through JSP Expressions. JSP Expression starts with `<%=` and ends with `%>`. `<% out.print("Pankaj"); %>` can be written using JSP Expression as `<%= "Pankaj" %>` Notice that anything between `<%= %>` is sent as parameter to `out.print()` method. Also notice that scriptlets can contain multiple java statements and always ends with semicolon (;) but expression doesn't end with semicolon.
JSP Directives are used to give special instructions to the container while JSP page is getting translated to servlet source code. JSP directives starts with `<%@` and ends with `%>` For example, in above JSP Example, I am using _page_ directive to to instruct container JSP translator to import the Date class.
JSP Declarations are used to declare member methods and variables of servlet class. JSP Declarations starts with `<%!` and ends with `%>`. For example we can create an int variable in JSP at class level as `<%! public static int count=0; %>`
Once JSP files are translated to Servlet source code, the source code (.java) and compiled classes both are place in **Tomcat/work/Catalina/localhost/FirstJSP/org/apache/jsp** directory. If the JSP files are inside other directories of application, the directory structure is maintained. For JSPs inside WEB-INF directory, its source and class files are inside **Tomcat/work/Catalina/localhost/FirstJSP/org/apache/jsp/WEB\_002dINF** directory. Here is the source code generated for above test.jsp page. `test_jsp.java`
```
/*
* Generated by the Jasper component of Apache Tomcat
* Version: Apache Tomcat/7.0.32
* Generated at: 2013-08-21 03:40:59 UTC
* Note: The last modified time of this file was set to
* the last modified time of the source file after
* generation to assist with modification tracking.
*/
package org.apache.jsp.WEB_002dINF;
import javax.servlet.*;
import javax.servlet.http.*;
import javax.servlet.jsp.*;
public final class test_jsp extends org.apache.jasper.runtime.HttpJspBase
implements org.apache.jasper.runtime.JspSourceDependent {
private static final javax.servlet.jsp.JspFactory _jspxFactory =
javax.servlet.jsp.JspFactory.getDefaultFactory();
private static java.util.Map<java.lang.String,java.lang.Long> _jspx_dependants;
private javax.el.ExpressionFactory _el_expressionfactory;
private org.apache.tomcat.InstanceManager _jsp_instancemanager;
public java.util.Map<java.lang.String,java.lang.Long> getDependants() {
return _jspx_dependants;
}
public void _jspInit() {
_el_expressionfactory = _jspxFactory.getJspApplicationContext(getServletConfig().getServletContext()).getExpressionFactory();
_jsp_instancemanager = org.apache.jasper.runtime.InstanceManagerFactory.getInstanceManager(getServletConfig());
}
public void _jspDestroy() {
}
public void _jspService(final javax.servlet.http.HttpServletRequest request, final javax.servlet.http.HttpServletResponse response)
throws java.io.IOException, javax.servlet.ServletException {
final javax.servlet.jsp.PageContext pageContext;
javax.servlet.http.HttpSession session = null;
final javax.servlet.ServletContext application;
final javax.servlet.ServletConfig config;
javax.servlet.jsp.JspWriter out = null;
final java.lang.Object page = this;
javax.servlet.jsp.JspWriter _jspx_out = null;
javax.servlet.jsp.PageContext _jspx_page_context = null;
try {
response.setContentType("text/html; charset=US-ASCII");
pageContext = _jspxFactory.getPageContext(this, request, response,
null, true, 8192, true);
_jspx_page_context = pageContext;
application = pageContext.getServletContext();
config = pageContext.getServletConfig();
session = pageContext.getSession();
out = pageContext.getOut();
_jspx_out = out;
out.write("\n");
out.write("<!DOCTYPE html PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"https://www.w3.org/TR/html4/loose.dtd\">\n");
out.write("<html>\n");
out.write("<head>\n");
out.write("<meta http-equiv=\"Content-Type\" content=\"text/html; charset=US-ASCII\">\n");
out.write("<title>Test JSP</title>\n");
out.write("</head>\n");
out.write("<body>\n");
out.write("Test JSP Page inside WEB-INF folder.<br>\n");
out.write("Init Param \"test\" value =");
out.print(config.getInitParameter("test") );
out.write("<br>\n");
out.write("HashCode of this object=");
out.print(this.hashCode() );
out.write("\n");
out.write("</body>\n");
out.write("</html>");
} catch (java.lang.Throwable t) {
if (!(t instanceof javax.servlet.jsp.SkipPageException)){
out = _jspx_out;
if (out != null && out.getBufferSize() != 0)
try { out.clearBuffer(); } catch (java.io.IOException e) {}
if (_jspx_page_context != null) _jspx_page_context.handlePageException(t);
else throw new ServletException(t);
}
} finally {
_jspxFactory.releasePageContext(_jspx_page_context);
}
}
}
```
Notice following points in above servlet code;
- The package of class starts with org.apache.jsp and if JSPs are inside other folders, it includes directory hierarchy too. Usually we dont care about it.
- The generates servlet class is final and can't be extended.
- It extends `org.apache.jasper.runtime.HttpJspBase` that is similar to HttpServlet except that it's internal to Tomcat JSP Translator implementation. HttpJspBase extends HttpServlet and implements HttpJspPage interface.
- Notice the local variables at the start of \_jspService() method implementation, they are automatically added by JSP translator and available for use in service methods, i.e in scriptlets.As a java programmer, sometimes it helps to look into the generated source for debugging purposes.
We can define init parameters for the JSP page as shown in above example and we can retrieve them in JSP using **config** implicit object, we will look into implicit objects in JSP in more detail in future posts.
We can override JSP init method for creating resources to be used by JSP service() method using JSP Declaration tags, we can override jspInit() and jspDestroy() or any other methods also. However we should never override \_jspService() method because anything we write in JSP goes into service method.
Apart from standard servlet attributes with request, session and context scope, in JSP we have another scope for attributes, i.e Page Scope that we can get from pageContext object. We will look it's importance in custom tags tutorial. For normal JSP programming, we don't need to worry about page scope.
Isso é tudo para o tutorial de exemplo JSP para iniciantes. Espero que isso ajude você a entender os conceitos básicos de JSPs e a começar. Vamos explorar outros recursos do JSP em postagens futuras.
Source:
https://www.digitalocean.com/community/tutorials/jsp-example-tutorial-for-beginners