Como evitar o código Java nos arquivos JSP?

1673

Eu sou novo no Java EE e sei que algo como as três linhas a seguir

<%= x+1 %>
<%= request.getParameter("name") %>
<%! counter++; %>

é uma maneira antiga de codificação e, na versão 2 do JSP, existe um método para evitar o código Java nos arquivos JSP. Alguém pode me dizer as linhas alternativas JSP 2, e como essa técnica é chamada?

chmoelders
fonte
22
@Koray Tugay, enquanto a variável do contador é declarado em algum lugar antes da sua utilização, então é certamente válida ...
Sheldon R.
@SheldonR. Isso é válido: <% = counter ++%> ou isso: <%! contador int = 0; int x = contador ++; %> mas não: <%! contador int = 0; counter ++; %>
Koray Tugay
@KorayTugay, o que eu quis dizer foi que, se o contador de variáveis ​​for declarado em um bloco de script anterior, ele deverá ser válido em um bloco posterior. Mas, afinal, J2EE programadores estes dias deve estar usando variáveis EL vez de scriptlets, de qualquer maneira ...
Sheldon R.

Respostas:

1972

O uso de scriptlets (essas <% %>coisas) no JSP é realmente altamente desencorajado desde o nascimento de taglibs (como JSTL ) e EL ( Expression Language , essas ${}coisas) em 2001.

As principais desvantagens dos scriptlets são:

  1. Reutilização: você não pode reutilizar scripts.
  2. Substituição: você não pode tornar os scriptlets abstratos.
  3. Capacidade OO: você não pode usar herança / composição.
  4. Depuração: se o scriptlet lança uma exceção até a metade, tudo o que você obtém é uma página em branco.
  5. Testabilidade: os scriptlets não podem ser testados por unidade.
  6. Manutenção: por saldo, é necessário mais tempo para manter a lógica de código mesclada / confusa / duplicada.

O próprio Sun Oracle também recomenda nas convenções de codificação JSP evitar o uso de scriptlets sempre que a mesma funcionalidade for possível pelas classes (tag). Aqui estão várias citações de relevância:

Na Especificação JSP 1.2, é altamente recomendável que a JSTL (JSP Standard Tag Library) seja usada em seu aplicativo da web para ajudar reduzir a necessidade de scriptlets JSP em suas páginas. As páginas que usam JSTL são, em geral, mais fáceis de ler e manter.

...

Sempre que possível, evite scripts JSP sempre que as bibliotecas de tags fornecerem funcionalidade equivalente. Isso facilita a leitura e a manutenção das páginas, ajuda a separar a lógica de negócios da lógica de apresentação e facilita a evolução das páginas para páginas no estilo JSP 2.0 (a JSP 2.0 Specification suporta, mas não enfatiza o uso de scriptlets).

...

No espírito de adotar o padrão de design do MVC (Model-View-Controller) para reduzir o acoplamento entre a camada de apresentação da lógica de negócios, os scriptlets JSP não devem ser usados para escrever a lógica de negócios. Em vez disso, os scriptlets JSP são usados, se necessário, para transformar dados (também chamados de "objetos de valor") retornados do processamento das solicitações do cliente em um formato adequado para o cliente. Mesmo assim, isso seria melhor com um servlet do controlador frontal ou uma tag personalizada.


Como substituir scriptslet depende inteiramente do único objetivo do código / lógica. Com mais freqüência, esse código deve ser colocado em uma classe Java totalmente válida:

  • Se você deseja chamar o mesmo código Java em todas as solicitações, menos ou mais, independentemente da página solicitada, por exemplo, verificando se um usuário está logado, implemente um filtro e escreva o código de acordo com o doFilter()método. Por exemplo:

    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws ServletException, IOException {
        if (((HttpServletRequest) request).getSession().getAttribute("user") == null) {
            ((HttpServletResponse) response).sendRedirect("login"); // Not logged in, redirect to login page.
        } else {
            chain.doFilter(request, response); // Logged in, just continue request.
        }
    }

    Quando mapeado em uma <url-pattern>cobertura apropriada das páginas JSP de interesse, você não precisa copiar novamente o mesmo trecho de código nas páginas JSP gerais.


  • Se você deseja chamar algum código Java para pré - processar uma solicitação, por exemplo, pré-carregando alguma lista de um banco de dados para exibir em alguma tabela, se necessário com base em alguns parâmetros de consulta, implemente um servlet e escreva o código de acordo com o doGet()método. Por exemplo:

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        try {
            List<Product> products = productService.list(); // Obtain all products.
            request.setAttribute("products", products); // Store products in request scope.
            request.getRequestDispatcher("/WEB-INF/products.jsp").forward(request, response); // Forward to JSP page to display them in a HTML table.
        } catch (SQLException e) {
            throw new ServletException("Retrieving products failed!", e);
        }
    }

    Dessa forma, lidar com exceções é mais fácil. O banco de dados não é acessado no meio da renderização JSP, mas muito antes da exibição do JSP. Você ainda tem a possibilidade de alterar a resposta sempre que o acesso ao banco de dados lança uma exceção. No exemplo acima, a página de erro padrão 500 será exibida e você poderá personalizar de qualquer maneira com um <error-page>in web.xml.


  • Se você deseja chamar algum código Java para pós - processar uma solicitação, por exemplo, processar uma submissão de formulário, implemente um servlet e escreva o código de acordo com o doPost()método. Por exemplo:

    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        String username = request.getParameter("username");
        String password = request.getParameter("password");
        User user = userService.find(username, password);
    
        if (user != null) {
            request.getSession().setAttribute("user", user); // Login user.
            response.sendRedirect("home"); // Redirect to home page.
        } else {
            request.setAttribute("message", "Unknown username/password. Please retry."); // Store error message in request scope.
            request.getRequestDispatcher("/WEB-INF/login.jsp").forward(request, response); // Forward to JSP page to redisplay login form with error.
        }
    }

    Desta forma, lidar com diferentes destinos página de resultados é mais fácil: reexibir o formulário com erros de validação no caso de um erro (neste exemplo em particular, você pode exibi-la novamente usando ${message}em EL ), ou apenas tomar para a página de destino desejado em caso de sucesso.


  • Se você desejar chamar algum código Java para controlar o plano de execução e / ou o destino da solicitação e da resposta, implemente um servlet de acordo com o Front Controller Pattern do MVC . Por exemplo:

    protected void service(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        try {
            Action action = ActionFactory.getAction(request);
            String view = action.execute(request, response);
    
            if (view.equals(request.getPathInfo().substring(1)) {
                request.getRequestDispatcher("/WEB-INF/" + view + ".jsp").forward(request, response);
            } else {
                response.sendRedirect(view);
            }
        } catch (Exception e) {
            throw new ServletException("Executing action failed.", e);
        }
    }

    Ou apenas adote uma estrutura MVC como JSF , Spring MVC , Wicket , etc, para que você acabe com apenas uma página JSP / Facelets e uma classe JavaBean sem a necessidade de um servlet personalizado.


  • Se você deseja chamar algum código Java para controlar o fluxo dentro de uma página JSP, precisará pegar um taglib de controle de fluxo (existente) como o núcleo JSTL . Por exemplo, exibindo List<Product>em uma tabela:

    <%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
    ...
    <table>
        <c:forEach items="${products}" var="product">
            <tr>
                <td>${product.name}</td>
                <td>${product.description}</td>
                <td>${product.price}</td>
            </tr>
        </c:forEach>
    </table>

    Com tags no estilo XML que se encaixam perfeitamente em todo esse HTML, o código é melhor legível (e, portanto, melhor de manter) do que um monte de scriptlets com várias chaves de abertura e fechamento ( "Onde diabos essa chave de fechamento pertence?" ). Uma ajuda fácil é configurar seu aplicativo da web para gerar uma exceção sempre que scriptslet ainda forem usados, adicionando a seguinte parte a web.xml:

    <jsp-config>
        <jsp-property-group>
            <url-pattern>*.jsp</url-pattern>
            <scripting-invalid>true</scripting-invalid>
        </jsp-property-group>
    </jsp-config>

    No Facelets , o sucessor do JSP, que faz parte do JSF da estrutura MVC fornecida pelo Java EE , já não é possível usar scripts . Dessa forma, você é automaticamente forçado a fazer as coisas "do jeito certo".


  • Se você desejar chamar algum código Java para acessar e exibir dados de "back-end" dentro de uma página JSP, precisará usar EL (Expression Language), essas ${}coisas. Por exemplo, exibindo novamente os valores de entrada enviados:

    <input type="text" name="foo" value="${param.foo}" />

    O ${param.foo}exibe o resultado de request.getParameter("foo").


  • Se você desejar chamar algum código Java utilitário diretamente na página JSP (normalmente public staticmétodos), será necessário defini-los como funções EL. Há um taglib de funções padrão no JSTL, mas você também pode criar funções facilmente . Aqui está um exemplo de como o JSTL fn:escapeXmlé útil para evitar ataques XSS .

    <%@ taglib uri="http://java.sun.com/jsp/jstl/functions" prefix="fn" %>
    ...
    <input type="text" name="foo" value="${fn:escapeXml(param.foo)}" />

    Observe que a sensibilidade do XSS não está de forma alguma especificamente relacionada a Java / JSP / JSTL / EL / qualquer que seja, esse problema precisa ser levado em consideração em todos os aplicativos da Web que você desenvolver. O problema dos scriptlets é que ele não fornece meios de prevenção interna, pelo menos não usando a API Java padrão. O Facelets sucessor do JSP já possui escape HTML implícito, portanto você não precisa se preocupar com os buracos XSS no Facelets.

Veja também:

BalusC
fonte
117
+1 ótima resposta. Mas não seja dogmático; em algum momento, usar scriptlets está OK, mas essa deve ser a exceção que comprova a regra.
svachon
26
@svachon: Scriptlets são úteis para prototipagem / teste rápidos. Até onde eu sei, há apenas um uso de produção "legítimo" de um scriptlet, ou seja, <% response.getWriter().flush(); %>entre o </head>e o <body>para melhorar o desempenho de análise de página da web no navegador da web. Mas esse uso é completamente insignificante quando o tamanho do buffer de saída no lado do servidor é baixo (1 ~ 2 KB). Veja também este artigo .
BalusC
5
@BalusC Algumas vezes estive preso a classes java que não seguiam o padrão getter / setter. IMHO que é um caso em que um scripltet faz o trabalho.
svachon 6/07/10
41
@svachon: Eu envolvia essas classes com classes javabean próprias e as usava.
BalusC
31
Foi uma resposta muito boa, mas as partes doGet e doPost são enganosas. Esses métodos são para lidar com métodos de solicitação específica (HEAD, GET e POST) e não para solicitações de "pré-processamento" ou "pós-processamento"!
MetroidFan2002
225

Como salvaguarda: desative scripts para sempre

Como outra pergunta está sendo discutida, você pode e sempre deve desativar os scriptlets no web.xmldescritor do aplicativo da web.

Eu sempre faria isso para impedir que qualquer desenvolvedor adicionasse scriptlets, especialmente em empresas maiores, nas quais você perderá a visão geral mais cedo ou mais tarde. oweb.xml configurações são assim:

<jsp-config>
  <jsp-property-group>
    <url-pattern>*.jsp</url-pattern>
     <scripting-invalid>true</scripting-invalid>
  </jsp-property-group>
</jsp-config>
Stefan Schubert-Peters
fonte
4
Isso também desativa os comentários do scriptlet ?: <%-- comment that i don't want in the final HTML --%>. Acho útil usá-los em vez de comentários em HTML.
David Lavender
16
A @MrSpoon localizou uma resposta para você. De acordo com esta resposta + comentário , isso desativa os scriptlets <% %>, expressões de <%! %>scriptlet e declarações de scriptlet <%= %>. Isso significa que diretrizes <%@ %>e comentários <%-- --%>permanecem ativados e utilizáveis, para que você ainda possa fazer comentários e inclusões.
Martin Carney
3
A desativação das diretivas de scriptlet seria terrível - o espaço em branco aparado é inestimável para interagir com sistemas legados que surtam com espaço em branco extra.
CorsiKa # 6/15
108

O JSTL oferece tags para condicionais, loops, sets, gets, etc. Por exemplo:

<c:if test="${someAttribute == 'something'}">
   ...
</c:if>

JSTL trabalha com atributos de solicitação - eles são configurados com mais freqüência na solicitação por um Servlet, que encaminha para o JSP.

Bozho
fonte
2
Por que você diz que o JSTL trabalha com atributos de solicitação? Eles podem trabalhar com atributos em qualquer escopo, não é?
precisa
60

Não tenho certeza se estou certo.

Você deve ler algo sobre o MVC. Spring MVC & Struts 2 são as duas soluções mais comuns.

tzim
fonte
29
O MVC pode ser implementado com servlets / jsp usando muitas das técnicas acima, sem Spring ou Struts.
stepanian
18
Como responde a pergunta?
xyz
54

Você pode usar tags JSTL junto com expressões EL para evitar a mistura de código Java e HTML:

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<%@ taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt" %>
<html>
    <head>
    </head>
    <body>

        <c:out value="${x + 1}" />
        <c:out value="${param.name}" />
        // and so on

    </body>
</html>
Behrang Saeedzadeh
fonte
34

Também existem estruturas baseadas em componentes, como o Wicket, que geram muito do HTML para você. As tags que terminam no HTML são extremamente básicas e praticamente não há lógica misturada. O resultado são páginas HTML quase vazias, com elementos HTML típicos. A desvantagem é que há muitos componentes na API do Wicket para aprender e algumas coisas podem ser difíceis de alcançar sob essas restrições.

tsand
fonte
33

No padrão MVC Architectural, JSPs representam a camada View. A incorporação de código java em JSPs é considerada uma má prática. Você pode usar JSTL , FreeMarker , a velocidade com JSP como "modelo de motor". O provedor de dados para essas tags depende das estruturas com as quais você está lidando. Struts 2e webworkcomo implementação do MVC Pattern, o OGNL usa "técnica muito interessante para expor as propriedades do Beans ao JSP".

Sami Jmii
fonte
27

A experiência mostrou que os JSPs têm algumas deficiências, sendo uma delas difícil de evitar misturar a marcação com o código real.

Se puder, considere usar uma tecnologia especializada para o que você precisa fazer. No Java EE 6, há o JSF 2.0, que fornece muitos recursos interessantes, incluindo a colagem de beans Java junto com as páginas JSF através da #{bean.method(argument)}abordagem.

Thorbjørn Ravn Andersen
fonte
3
Resposta antiga, mas não resisto a dizer que o JSF é uma das mais horrendas invenções do espaço Java. Tente criar um único link (como HTTP GET) e você entenderá o porquê.
Alex
@ Alex, mas ainda melhor. Sinta-se livre para recomendar algo ainda melhor.
Thorbjørn Ravn Andersen
26

se você simplesmente deseja evitar as desvantagens da codificação Java no JSP, pode fazê-lo mesmo com scriplets. Basta seguir alguma disciplina para ter Java mínimo em JSP e quase nenhum cálculo e lógica na página JSP.

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%//instantiate a JSP controller
MyController clr = new MyController(request, response);

//process action if any
clr.process(request);

//process page forwaring if necessary

//do all variable assignment here
String showMe = clr.getShowMe();%>

<html>
    <head>
    </head>
    <body>
        <form name="frm1">
            <p><%= showMe %>
            <p><% for(String str : clr.listOfStrings()) { %>
            <p><%= str %><% } %>

            // and so on   
        </form>
    </body>
</html>
dipu
fonte
26

Aprenda a personalizar e escrever suas próprias tags usando JSTL

Observe que EL é EviL (exceções de tempo de execução, refatoração) O
wicket também pode ser ruim (desempenho, trabalhoso para aplicativos pequenos ou camada de visualização simples)

Exemplo de java2s ,

Isso deve ser adicionado ao web.xml do aplicativo Web

<taglib>
    <taglib-uri>/java2s</taglib-uri>
    <taglib-location>/WEB-INF/java2s.tld</taglib-location>
</taglib>

crie File: java2s.tld no / WEB-INF /

<!DOCTYPE taglib
  PUBLIC "-//Sun Microsystems, Inc.//DTD JSP Tag Library 1.2//EN"
   "http://java.sun.com/dtd/web-jsptaglibrary_1_2.dtd">

<!-- a tab library descriptor -->
<taglib xmlns="http://java.sun.com/JSP/TagLibraryDescriptor">
    <tlib-version>1.0</tlib-version>
    <jsp-version>1.2</jsp-version>
    <short-name>Java2s Simple Tags</short-name>

    <!-- this tag manipulates its body content by converting it to upper case
    -->
    <tag>
        <name>bodyContentTag</name>
        <tag-class>com.java2s.BodyContentTag</tag-class>
        <body-content>JSP</body-content>
        <attribute>
          <name>howMany</name>
        </attribute>
    </tag>
</taglib>

compile o seguinte código em WEB-INF \ classes \ com \ java2s

package com.java2s;

import java.io.IOException;
import javax.servlet.jsp.JspWriter;
import javax.servlet.jsp.tagext.BodyContent;
import javax.servlet.jsp.tagext.BodyTagSupport;

public class BodyContentTag extends BodyTagSupport{
    private int iterations, howMany;

    public void setHowMany(int i){
        this.howMany = i;
    }

    public void setBodyContent(BodyContent bc){
        super.setBodyContent(bc);
        System.out.println("BodyContent = '" + bc.getString() + "'");
    }

    public int doAfterBody(){
        try{    
            BodyContent bodyContent = super.getBodyContent();
            String bodyString  = bodyContent.getString();
            JspWriter out = bodyContent.getEnclosingWriter();

            if ( iterations % 2 == 0 ) 
                out.print(bodyString.toLowerCase());
            else
                out.print(bodyString.toUpperCase());

            iterations++;
            bodyContent.clear(); // empty buffer for next evaluation
        }
        catch (IOException e) {
            System.out.println("Error in BodyContentTag.doAfterBody()" + e.getMessage());
            e.printStackTrace();
        } // end of catch

        int retValue = SKIP_BODY;

        if ( iterations < howMany ) 
            retValue = EVAL_BODY_AGAIN;

        return retValue;
    }
}

Inicie o servidor e carregue o bodyContent.jsp no navegador

<%@ taglib uri="/java2s" prefix="java2s" %>
<html>
    <head>
        <title>A custom tag: body content</title>
    </head>
    <body>
        This page uses a custom tag manipulates its body content.Here is its output:
        <ol>
            <java2s:bodyContentTag howMany="3">
            <li>java2s.com</li>
            </java2s:bodyContentTag>
        </ol>
    </body>
</html>
tomasb
fonte
embora a reutilização de componentes é bem ele atinge algum campo
tomasb
25

O Wicket também é uma alternativa que separa completamente o java do html, para que um designer e programador possam trabalhar juntos e em diferentes conjuntos de códigos com pouco entendimento um do outro.

Veja o Wicket.

msj121
fonte
23

Você levantou uma boa pergunta e, embora tenha boas respostas, sugiro que você se livre do JSP. É uma tecnologia ultrapassada que acabará por morrer. Use uma abordagem moderna, como mecanismos de modelo. Você terá uma separação muito clara das camadas de negócios e de apresentação, e certamente nenhum código Java nos modelos, para poder gerar modelos diretamente a partir do software de edição de apresentações na Web, na maioria dos casos utilizando o WYSIWYG.

E certamente fique longe de filtros e pré e pós-processamento, caso contrário, você poderá lidar com dificuldades de suporte / depuração, pois nem sempre sabe onde a variável obtém o valor.

Dmitriy R
fonte
9
JSP é um mecanismo de template
WarFox 13/07/11
1
-1 - Existem muitos motivos válidos para usar filtros, pré-processadores e pós-processadores. Sim, você pode acabar com valores que parecem misteriosos, mas não se você entender sua arquitetura.
precisa saber é o seguinte
21

para evitar o código java nos arquivos JSP, o java agora fornece bibliotecas de tags como o JSTL e o java criou o JSF no qual você pode escrever todas as estruturas de programação na forma de tags

mahesh
fonte
21

Não importa o quanto tente evitar, quando você trabalha com outros desenvolvedores, alguns deles ainda preferem scriptlet e, em seguida, inserem o código incorreto no projeto. Portanto, a configuração do projeto no primeiro sinal é muito importante se você realmente deseja reduzir o código do scriptlet. Existem várias técnicas para superar isso (incluindo várias estruturas mencionadas anteriormente). No entanto, se você preferir a maneira JSP pura, use o arquivo de tag JSTL. O bom disso é que você também pode configurar páginas mestras para o seu projeto, para que as outras páginas possam herdar as páginas mestras.

Crie uma página mestre chamada base.tag em suas tags WEB-INF / com o seguinte conteúdo

<%@tag description="Overall Page template" pageEncoding="UTF-8"%>

<%@attribute name="title" fragment="true" %>

<html>
  <head>
    <title>  
       <jsp:invoke fragment="title"></jsp:invoke>
    </title>

  </head>
  <body>
    <div id="page-header">
       ....
    </div>
    <div id="page-body">
      <jsp:doBody/>
    </div>
    <div id="page-footer">
      .....
    </div>
  </body>
</html>

Nesta página de material, criei um fragmento chamado "title", para que na página filha pudesse inserir mais códigos nesse local da página mestre. Além disso, a tag <jsp:doBody/>será substituída pelo conteúdo da página filha

Crie a página filho (child.jsp) na sua pasta WebContent:

<%@ taglib prefix="t" tagdir="/WEB-INF/tags" %>

<t:base>
    <jsp:attribute name="title"> 
        <bean:message key="hello.world" />
    </jsp:attribute>

    <jsp:body>
    [Put your content of the child here]
    </jsp:body>   
</t:base>

<t:base>é usado para especificar a página mestre que você deseja usar (que é base.tag no momento). Todo o conteúdo dentro da tag <jsp:body>aqui substituirá o <jsp:doBody/>da sua página mestre. Sua página filha também pode incluir qualquer tag lib e você pode usá-la normalmente como a outra mencionada. No entanto, se você usar qualquer código de scriptlet aqui ( <%= request.getParameter("name") %>...) e tentar executar esta página, receberá um JasperException because Scripting elements ( &lt;%!, &lt;jsp:declaration, &lt;%=, &lt;jsp:expression, &lt;%, &lt;jsp:scriptlet ) are disallowed here. Portanto, não há como outras pessoas incluírem o código incorreto no arquivo jsp

Chamando esta página do seu controlador:

Você pode facilmente chamar o arquivo child.jsp do seu controlador. Isso também funciona bem com o framework struts

Thai Tran
fonte
"Não importa o quanto tente evitar, quando você trabalha com outros desenvolvedores, alguns deles ainda preferem o scriptlet e depois inserem o código incorreto no projeto". Consulte a resposta "Como salvaguarda: desabilite o scriptlets para sempre".
Lluis Martinez
19

Use JSTL Tag librariesno JSP, que funcionará perfeitamente.

Chandra Sekhar
fonte
18

Basta usar a tag JSTL e a expressão EL.

tanglei
fonte
17

Se alguém é realmente contra a programação em mais de um idioma , sugiro o GWT. Teoricamente, você pode evitar todos os elementos JS e HTML, porque o Google Toolkit transforma todo o cliente e o código compartilhado em JS, e você não terá problemas com eles. você tem um serviço da web sem codificar em nenhum outro idioma. Mesmo você pode usar algum CSS padrão de algum lugar, pois é fornecido por extensões (smartGWT ou Vaadin). Você não precisa aprender dezenas de anotações.

Obviamente, se você quiser, poderá invadir as profundezas do código e injetar JS e enriquecer sua página HTML, mas, na verdade, você pode evitá-la se quiser, e o resultado será bom, como foi escrito em outras estruturas. Eu digo que vale a pena tentar, e o GWT básico está bem documentado.

E, é claro, muitos colegas programadores descrevem ou recomendam várias outras soluções. O GWT é para pessoas que realmente não querem lidar com a Web Part ou minimizá-la.

CsBalazsHungary
fonte
1
Realmente não responde à pergunta do OP.
Evan Donovan
1
@EvanDonovan bem, praticamente dá uma resposta. Você não precisa mexer nos códigos Java que se misturam com outras linguagens. Admito que ele usa Java para codificação, mas será traduzido para JS sem chamadas Java. Mas o escopo da pergunta é como evitar o caos do JSP clássico. E a tecnologia GWT resolve isso. Eu adicionei esta resposta, já que ninguém a mencionou, mas é relevante, pois é uma alternativa ao JSP. Eu não queria responder a todo o escopo da pergunta, mas adicionar uma informação valiosa para as pessoas que estão procurando alternativas.
precisa saber é o seguinte
16

Uma idéia interessante do mundo Python são as linguagens de atributo do modelo ; O TAL foi introduzido pelo Zope (também conhecido como "Zope Page Templates", ZPT) e é um padrão, com implementações em PHP, XSLT e Java também (usei as encarnações Python / Zope e PHP). Nesta classe de linguagens de modelos, um exemplo acima pode ser assim:

<table>
    <tr tal:repeat="product products">
        <td tal:content="product/name">Example product</td>
        <td tal:content="product/description">A nice description</td>
        <td tal:content="product/price">1.23</td>
    </tr>
</table>

O código se parece com HTML comum (ou XHTML), além de alguns atributos especiais em um espaço para nome XML; Ele pode ser visualizado em um navegador e ajustado com segurança por um designer. Há suporte para macros e também para i18n:

<h1 i18n:translate="">Our special offers</h1>
<table>
    <tr tal:repeat="product products">
        <td tal:content="product/name"
            i18n:translate="">Example product</td>
        <td tal:content="product/description"
            i18n:translate="">A nice description</td>
        <td tal:content="product/price">1.23</td>
    </tr>
</table>

Se traduções do conteúdo estiverem disponíveis, elas serão usadas.

Eu não sei muito sobre a implementação Java , no entanto.

Tobias
fonte
1
Desde dezembro de 2009, o JSP foi sucedido pelo Facelets, que suporta esse material. Facelets também é baseado em XML. Veja também, entre outros, o capítulo Facelets no tutorial do Java EE 6 e as ui:xxxtags no Facelts VDL .
BalusC
Não conheço muito bem o Facelets, mas o IIRC trata de escrever classes que implementam elementos XML personalizados. A maneira TAL / ZPT é ter modelos que contenham HTML (X) verdadeiro com atributos especiais que preenchem ou substituem os elementos originais; assim, você pode visualizar o modelo de trabalho e ver um protótipo com bom conteúdo fictício. Não tenho certeza se o Facelets permite ajustar os elementos HTML originais (sem um espaço de nome adicional) usando atributos personalizados.
Tobias
Acabei de dar outra olhada nesse material do Facelets. Ele contém todos os tipos de instalações de validação, etc., e segue uma filosofia completamente diferente da TAL. A maneira do TAL é: "Mantenha a lógica fora do modelo o mais limpo possível; faça com que todo o material complicado seja feito pelo controlador que o alimenta". Você nunca dará um modelo do Facelets a um designer para que ele o ajuste; simplesmente não é possível. Em relação ao conteúdo gerado - é como usar tal:replace="structure (expression)"atributos o tempo todo.
Tobias
14

Claro, substitua <%! counter++; %> por uma arquitetura produtor-consumidor de eventos, onde a camada de negócios é notificada sobre a necessidade de incrementar o contador, ela reage de acordo e notifica os apresentadores para que atualizem as visualizações. Diversas transações de banco de dados estão envolvidas, pois, no futuro, precisaremos conhecer o valor novo e antigo do contador, quem o incrementou e com que objetivo em mente. Obviamente, a serialização está envolvida, uma vez que as camadas são totalmente dissociadas. Você poderá incrementar seu contador em RMI, IIOP, SOAP. Mas apenas HTML é necessário, que você não implementa, pois é um caso tão mundano. Seu novo objetivo é atingir 250 incrementos por segundo em seu novo servidor brilhante E7 de 64 GB de RAM.

Tenho mais de 20 anos em programação, a maioria dos projetos falha antes do sexteto: Reutilização Substituibilidade Capacidade OO Capacidade Debuggability Testabilidade A manutenção é necessária. Outros projetos, executados por pessoas que se preocupavam apenas com a funcionalidade, foram extremamente bem-sucedidos. Além disso, a estrutura rígida de objetos, implementada muito cedo no projeto, torna o código incapaz de ser adaptado às mudanças drásticas nas especificações (também conhecido como ágil).

Portanto, considero como procrastinação a atividade de definição de "camadas" ou estruturas de dados redundantes no início do projeto ou quando não for especificamente necessário.  

Razvan
fonte
11

Tecnicamente, o JSP é todo convertido em Servlets durante o tempo de execução . O JSP foi criado inicialmente com o objetivo de dissociar a lógica de negócios e a lógica de design, seguindo o padrão MVC. Portanto, JSP tecnicamente são todos os códigos Java durante o tempo de execução. Mas, para responder à pergunta, as bibliotecas de tags geralmente são usadas para aplicar lógica (remover códigos Java) às páginas JSP.

mel3kings
fonte
8

Se usarmos o seguinte em um aplicativo da web java, o código java poderá ser eliminado do primeiro plano do JSP.

  1. Usar arquitetura MVC para aplicativo da web

  2. Usar tags JSP

    uma. Tags padrão

    b. Tags personalizadas

  3. Linguagem de Expressão

Ajay Takur
fonte
8

Como evitar o código Java nos arquivos JSP?

Você pode usar tags da biblioteca de guias como JSTL , além do Expression Language ( EL ). Mas o EL não funciona bem com o JSP. Portanto, é provavelmente melhor deixar o JSP completamente e usar o Facelets .

Facelets é a primeira linguagem de declaração de página não JSP projetada para JSF (Java Server Faces) que forneceu um modelo de programação mais simples e mais poderoso aos desenvolvedores JSF do que o JSP. Ele resolve problemas diferentes que ocorrem no JSP para o desenvolvimento de aplicativos da web.

insira a descrição da imagem aqui

Fonte

Yster
fonte
Definitivamente, sou a segunda a responder. JSF com ou sem Facelets. Eu pensei que o desenvolvimento no JSP havia cessado em grande parte há mais de 10 anos. Eu escrevi JSPs pela última vez em 2000!
casgage
4

O uso de Scriptlets é uma maneira muito antiga e não recomendada. Se você deseja produzir algo diretamente em suas páginas JSP, use o Expression Language (EL) junto com o JSTL .

Existem também outras opções, como o uso de um mecanismo de modelagem, como Velocity, Freemarker, Thymeleaf etc.

Além disso, observe que não é uma prática recomendada executar lógica de negócios na camada de visualização, você deve executar suas lógicas de negócios na camada Serviço e passar o resultado da saída para suas visualizações através de um Controlador.

adn.911
fonte
3

Nada disso é mais usado meu amigo, meu conselho é desacoplar a visualização (css, html, javascript, etc) do servidor.

No meu caso, eu faço meus sistemas lidando com a visualização com Angular e todos os dados necessários são trazidos do servidor usando serviços de descanso.

Acredite, isso mudará a maneira como você cria

Eduardo
fonte
3

Use o backbone, estrutura de javascript angular como para o design da interface do usuário e busque os dados usando a API restante. Isso removerá completamente a dependência do java da interface do usuário.

Sumesh TG
fonte
3

O JSP 2.0 possui um recurso chamado "Arquivos de tags" , você pode escrever tags sem javacódigo externo e tld. Você precisa criar um .tagarquivo e colocá-lo emWEB-INF\tags Você pode até criar uma estrutura de diretórios para empacotar suas tags.

Por exemplo:

/WEB-INF/tags/html/label.tag

<%@tag description="Rensders a label with required css class" pageEncoding="UTF-8"%>
<%@attribute name="name" required="true" description="The label"%>

<label class="control-label control-default"  id="${name}Label">${name}</label>

Use-o como

<%@ taglib prefix="h" tagdir="/WEB-INF/tags/html"%>
<h:label  name="customer name" />

Além disso, você pode ler o corpo da tag facilmente

/WEB-INF/tags/html/bold.tag
<%@tag description="Bold tag" pageEncoding="UTF-8"%>
<b>
  <jsp:doBody/>
</b>

Use-o

<%@ taglib prefix="h" tagdir="/WEB-INF/tags/bold"%>
<h:bold>Make me bold</h:bold>

As amostras são muito simples, mas você pode executar muitas tarefas complicadas aqui. Por favor, considere que você pode usar outras tags (por exemplo: JSTLque controlam marcas como if/forEcah/chosenmanipulação de texto como format/contains/uppercaseou mesmo etiquetas de SQL select/update), passar todos os parâmetros tipo, por exemplo Hashmap, o acesso session, request... no seu arquivo de tag também.

O Tag File é tão fácil de desenvolver que você não precisa reiniciar o servidor ao alterá-lo, como arquivos JSP. Isso os torna fáceis para o desenvolvimento.

Mesmo se você usar uma estrutura como o Struts 2, que possui muitas boas tags, você pode achar que ter suas próprias tags pode reduzir muito o seu código. Você pode passar seus parâmetros de tag para struts e, dessa forma, personalizar sua tag de estrutura.

Você pode usar a tag não apenas para evitar java, mas também para minimizar seus códigos HTML. Eu mesmo tento revisar códigos HTML e criar muitas tags assim que as duplicatas de código começarem em minhas páginas.

(Mesmo se você acabar usando o java no seu código JSP, o que espero não, você pode encapsular esse código em uma tag)

Alireza Fattahi
fonte
1

Como muitas respostas dizem, use JSTL ou crie suas próprias tags personalizadas. Aqui está uma boa explicação sobre a criação de tags personalizadas

Code_Mode
fonte
1
  1. Faça seus valores e parâmetros dentro de suas classes de servlet
  2. Busque esses valores e parâmetros em seu JSP usando JSTL / Taglib

O lado bom dessa abordagem é que seu código também é como código HTML!

Mehdi
fonte
0

Usando tags JSTL junto com a expressão EL, você pode evitar isso. Coloque o seguinte na sua página jsp:

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<%@ taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt" %>
bhanwar rathore
fonte