Servlet与JSP学习笔记(六) JSP进阶

系列写到这里也差不多可以收尾了,本文将是系列的最后一篇。主要的参考资料是《Tomcat与Java Web开发技术详解》和 菜鸟笔记。菜鸟笔记的问题在于,学完之后还是觉得什么都不会,因为没有人指导去做个项目,因而对真正的项目没有概念。而《Tomcat》则提供了一些项目的感觉。

没错,JSP已经不再流行了,但是想学习Java Web,JSP和Servlet的基本功的修行是必不可少的。何况,很多技术都是触类旁通的。我会继续加油的!

表达式语言EL

这个还是蛮简单的。阅读菜鸟笔记就可以。回想起来,第一遍看它,还觉得它跟WPF中的属性绑定很像(也许是“.”号的提醒)。但其实用点号表示属性还是比较普遍的。

自定义标签

自定义标签就是对JSP内置标签的扩展,可以让开发人员创建可重用的第三方标签,帮助处理复杂的逻辑和事物,让JSP代码更加简洁。

例如,下面是一些自定义标签的用法:

<mm:hello/>
<mm:message key="hello.hi" />
<mm:greeting>How are you. </mm:greeting>

自定义标签是从JSP 1.1版本出现的,后来在JSP 2.0中又加入了简单标签。下面先来看看传统的自定义标签。

要让JSP容器理解自定义标签的含义,很显然需要定义一些约定和接口。通常会把一组功能相关的标签放在同一个标签库中。开发标签库的步骤如下:

  1. 创建自定义标签的处理类(Tag Handler),实现标签的具体功能。

  2. 创建TLD标签库描述文件,描述标签的用法等。

自定义标签处理类要继承Tag接口:

方法描述
setPageContext()由容器调用,传入当前的PageContext对象
setParent()由容器调用,传入此标签的父标签的处理对象
getParent()得到父标签的处理对象
doStartTag()容器解析到标签的起始标志时调用
doEndTag()容器解析到标签的结束标志时调用
release()释放Tag资源时调用。

为了帮助编写Tag Handler,JSP还提供了TagSupportBodyTagSupport两个具体类,可以继承其中之一。

使用自定义标签时,需要把Tag Handler的class文件以及TLD文件拷到WEB-INF下,然后在web.xml中指明引入标签库:

  <jsp-config>
    <taglib>
      <taglib-uri>/mytaglib</taglib-uri>
      <taglib-location>/WEB-INF/mytaglib.tld</taglib-location>
    </taglib>
  </jsp-config>

在JSP中使用自定义标签前用<%@taglib>指令声明对标签库的生命。属性prefix指明前缀。

<%@page contentType="text/html; charset=GB2312" %>
<%@taglib uri="/mytaglib" prefix="mm" %>

<html><head><title>greet</title></head>
<body>  
  <mm:greet count="3">
    <font size="<%=size++ %>">
      Hi,${param.username} <br>
    </font>
  </mm:greet>  

</body></html>
简单标签

传统自定义标签的编写还是太复杂了,因此JSP 2.0推出了简单标签(SimpleTag)。这个接口基本上只需要你实现doTag()方法来完成主要工作。更棒的是,还可以让你用采用JSP语法的标签文件制作标签,其原理和思想就像用JSP写Servlet一样。一个简单的greetings.tag示例:

<%@ tag pageEncoding="UTF8" %>
朋友们,大家好!

和编译JSP文件一样,容器也会编译标签文件,生成Tag Handler类。标签文件甚至也有隐含对象和指令,确实和JSP异曲同工。

标准标签库JSTL

既然可以随意自定义JSP标签,那往往会有一套官方标准库。一般标签库往往把所有文件打成JAR包,内含所有的class和TLD文件。对于官方标准库,只需要把JAR包放入WEB-INF/lib目录下,在JSP文件中使用时先用<%@ taglib>的uri属性指定具体的库就行了。如:

<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>

JSTL主要包括以下五个部分:

  1. Core标签库。包括常用的功能,以及条件、迭代等标签。如:

    标签描述
    <c:out>用于在JSP中显示数据,就像<%= ... >
    <c:set>用于保存数据
    <c:if>与我们在一般程序中用的if一样
    <c:forEach>基础迭代标签,接受多种集合类型
  2. 格式标签库。用来格式化并输出文本、日期、时间、数字,提供国际化支持。

  3. SQL标签库。与数据库交互的标签。现在肯定没人用。

  4. XML标签库。操作XML文档。

  5. Functions标签库。包含一系列标准函数,大部分是通用的字符串处理函数。

设计网站模板

这里说的模板可不是后来出现的FreeMarker这样的模板引擎。这里说的是,同一个Web应用的页面往往需要保持外观上的统一的风格,因而可以定义统一的网页模板,不同的页面通过模板来动态生成。这里介绍的是利用自定义的JSP标签来实现。

假设对于一个bookstore应用,所有的网页都有如下结构:

<html>
<head>
<title>
    <!-- title -->
</title>
</head>
<body>
    <!-- banner -->
    <!-- body -->
</body>
</html>

所有网页都有title、banner、body这三部分。可以创建一个template.jsp文件,当客户请求某个网页时,采用某种方法把这三个部分动态地填充进去,生成客户所需的网页。
因此就需要让所有的请求都被template.jsp文件处理。这里是使用一个DispatcherServlet类,接受所有的客户请求,然后把URL保存到request中,再转发给template.jsp。

流程1

模板JSP文件的内容是这样的:

<!-- template.jsp -->
<%@ page contentType="text/html; charset=GB2312" %>
<%@ taglib uri="/mytaglib" prefix="mm" %>
<%@ page errorPage="errorpage.jsp" %>
<%@ page import="java.util.*" %>
<%@ include file="screendefinitions.jsp" %>
<html>
<head>
<title>
        <mm:insert definition="bookstore" parameter="title"/>
</title>
</head>
        <mm:insert definition="bookstore" parameter="banner"/>
        <mm:insert definition="bookstore" parameter="body"/>
</body>
</html>

自定义的<insert>标签在其他自定义标签的帮助下,可以根据客户请求的具体URL,把对应的内容JSP文件包含进来。

图片描述

以上就完成了主要功能。其实介绍这个项目是为后面的MVC话题做个铺垫。

引入MVC

MVC的概念和优点就不介绍了,直接进入主题。

JSP Model 1和JSP Model 2

早期的JSP页面把业务逻辑和控制网页流程的事情都干了,造成代码非常混乱。为了解决问题,SUN公司先后制定了两种设计模式,分别为JSP Model 1和JSP Model 2。

下图为Model 1. 它采用了JavaBean处理业务逻辑(Model),但JSP仍要干 View + Controller的活。只适应简单应用的需要。

Model 1

Model 2模式则联合使用了JSP和Servlet,吸取了它们各自的优点,用JSP生成表示层的内容,让Servlet完成深层次的处理任务。在这里,Servlet充当控制器的角色,负责处理客户请求,创建JSP页面需要使用的JavaBean对象,并返回合适的JSP页面给客户。JSP页面没有流程控制的逻辑,只负责把由Servlet创建的JavaBean对象包含的数据作为动态内容插入到静态模板中。下面为结构图:

Model 2

Struts框架

Struts是一个经典的Web MVC框架,是在JSP Model 2的基础上实现的。下面是其结构图:

Struts结构

Struts框架是利用其核心过滤器FilterDispatcher来拦截所有的客户请求,然后映射到不同的Action模块中处理。Action类继承自Action接口,核心是用execute()方法来处理客户请求。为方便,可以继承Struts的实现类ActionSupport

Action类调用Model组件(JavaBean等)处理业务并返回结果,核心过滤器再根据映射配置转发到具体的视图(如JSP),视图页面生成响应内容返回给核心过滤器,后者再把响应发送到客户端。

Struts流程

以上过程解释了如何根据请求定位到具体页面。可是如何用视图页面返回动态内容呢?也就是如何让JSP页面获得JavaBean的数据?
有两种方法。

  1. Struts提供的自定义标签。Struts 2甚至不需要你的Action类继承Action接口,只需要在类中定义一些属性和get/set方法,在JSP中使用Struts标签<s:property>就能访问到。使用<s:text>标签则能够访问struts资源文件中的属性。

  2. 在Action中访问Servlet API中的各种对象,就可以在对象中设置各种Attributes。通过ActionContext.getContext()可以得到HttpServletRequest的一个封装类。实现ServletContextAware、ServletRequestAware等接口则可以直接获得Servlet API的核心对象。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值