继往开来 吐故纳新
日历
网志分类
· 所有网志 (990)
· 个人作品 (62)
· 软件设计 (33)
· 面向对象编程 (22)
· JavaAPI (39)
· Java开源工具 (31)
· Swing (34)
· Java语法细节 (39)
· 样式表CSS (12)
· XML (10)
· J2EE(JavaEE) (23)
· 算法数据结构 (64)
· 正则表达式 (4)
· 软件知识 (6)
· Java线程 (9)
· Web开发.Jsp/Servlet/Struts (20)
· 程序随想录 (7)
· Spring (5)
· Hibernate (7)
· J2SE 高级 (2)
· J2SE 高级 (0)
· Web开发.Ajax (16)
· Web开发.JavaScript (43)
· DB4O (2)
· Web开发.CSS/Html (22)
· C# (20)
· ERP (4)
· JDBC (1)
· 编程资源 (16)
· 编程感悟 (29)
· DB/Sql (13)
· VB (29)
· VC (2)
· 桌面脚本 (3)
· 新兴软件 (3)
· 英语学习 (21)
· 网文转载 (159)
· 职场风云 (39)
· 诗词歌赋 (32)
· 生活感言 (77)
· 奇文共赏 (13)
· 财经纵横 (6)
· 未分类 (11)
站内搜索
友情链接
· 歪酷博客
· 我的歪酷 非非共享界
· 偶要雷锋
· 豆瓣
· nczonline
· 当当网
· easyjf中文站
· Donews
· 天极Java文章列表
· W3CSchool
· taiten的BLOG
· Dojo中国
· Dojo
· Extjs.com
· Lifehack中文网志
· JaveEye的一个AS专题
· Banq's JDon
· Java 中文网址大全
· 梦想Java
· 360Doc个人图书馆
· java开源大全
· 我在硅谷动力的软件下载站
· 站长中国
· 随意贴
· CSS教学素材站
· java 参考中文站
· 面向构件与SOA社区
· 彩字生成
· 派派小说论坛
· 如坐春风
· 英语学习网
· BBC CHina
· www.dlbang.com
· 古文竖排格式在线转化工具
· 免费家谱
· 图片上传基地
· 风景壁纸
· 和风细雨
· MyC#BlogInCsdn

订阅 RSS

0203522

歪酷博客

开此博一为经验积累,二为资料收集,三为同道交流,四为资源共享.
« 上一篇: 【原创】使用JavaScript操作表单 下一篇: 【原创】XML(Extensible Markup Language )综述 »
Junglesong @ 2008-04-05 14:36

Servlet与JSP综合讲述

Servlet和JSP的概念

Servlet是Sun推出的用于实现CGI(通用网关接口)的java语言版本,它不但具有跨平台的特性,而且还以多线程的方式为用户提供服务而不必为每个请求都启动一个线程,因此其效率要比传统的CGI程序要高很多.
JSP和MS的ASP类似,它把JSP标签嵌入到HTML格式的网页中,这样对程序员和网页编辑人员都很方便,JSP天生就是为表现层设计的.
实际上,Servlet只是继承了HttpRequest的Java类,而JSP最终也会被Servlet引擎翻译成Servlet并编译执行,JSP的存在主要是为了方便表现层.
Servlet与JSP之间的区别,决定了Servlet与JSP在MVC构架模式中的不同角色.Servlet一般作为MVC中的控制器,JSP一般作为MVC中的视图.

Servlet的生命周期

Servlet有三个生命周期:初始化,执行和结束,它们分别对应Servlet接口中的init,service和destroy三个函数.
初始化时期:当servlet被servlet容器(如tomcat)载入后,servlet的init函数就会被调用,在这个函数可以做一些初始化工作.init函数只会在servlet容器载入servlet执行一次,以后无论有多少客户端访问这个Servlet,init函数都不会被执行.
执行期:servlet采用多线程方式向客户提供服务,当有客户请求来到时, service会被用来处理它.每个客户都有自己的service方法,这些方法接受客户端请求,并且发挥相应的响应.程序员在实现具体的Servlet时,一般不重载service方法,服务器容器会调用service方法以决定doGet,doPost,doPut,doDelete中的一种或几种,因此应该重载这些方法来处理客户端请求.]
结束期:该时期服务器会卸载servlet,它将调用destroy函数释放占用的资源,注意Web服务器是有可能崩溃的,destroy方法不一定会被执行.

如何开发和部署一个Servlet

1)从java.servlet.http.HttpServlet继承自己的servlet类.
2)重载doGet或doPost方法来处理客户请求(一般是doPost,其安全性较好),如果要在加载Servlet时被加载时进行初始化操作,可以重载init方法.
3)在web.xml中配置这个servlet.其中servlet-class用来制定这个servlet的类全名,servlet-name用来标识这个servlet,它可以是任意的字符串,不一定要和类文件名一致.url-pattern用来表示servlet被映射到的url模式.

 <!– Servlet在Web.xml中的配置示例 -->
  <servlet>
    <servlet-name>ShowPageServlet</servlet-name>
    <servlet-class>
      com.sitinspring.action.ShowPageServlet
    </servlet-class>
  </servlet>

  <servlet-mapping>
    <servlet-name>ShowPageServlet</servlet-name>
    <url-pattern>/ShowPage</url-pattern>
  </servlet-mapping>

开发一个启动时就被执行的Servlet

一般的Servlet都是在有来自客户端请求时才会执行,要让它在启动时就执行需要在配置中进行一些特殊设置,如右.
右边的代码中, load-on-startup说明了服务器一启动就加载并初始化它,0代表了加载它的优先级,注意它必须是一个正数,而且值小的要比值大的先加载.debug制定输出调试信息的级别,0为最低.
这样的servlet在用于读取WebApp的一些初始化参数很有用处,如取得配置文件的地址,设置log4j和得到WebApp的物理路径等.右边配置的servlet就是用来初始化log4j的.

<!-- InitServlet -->
<servlet>
   <servlet-name>log4j-init</servlet-name>
   <servlet-class>
    com.sitinspring.action.Log4jInit
   </servlet-class>
   <init-param>
     <param-name>log4j</param-name>
     <param-value>WEB-INF/classes/log4j.properties</param-value>
   </init-param>
   <load-on-startup>1</load-on-startup>
</servlet>

Serlet中出现的线程不安全的问题

Servlet是运行在多线程的服务器上的,它对每个用户的请求创建的是线程而不是进程,因此在高效的同时也带来了数据同步和一致性的问题.
服务器值实例化一个Servlet/JSP实例,然后在多个处理线程中调用该实例的相关方法来处理请求,因此servlet的成员变量可能会被多个线程调用该实例的相关方法改变,将有可能带来问题.这也是大家在众多的Servlet中很少看到成员变量的原因.



public class ThreadUnsafeServlet extends HttpServlet {
  private String unsafeString="";

  public void doPost(HttpServletRequest request, HttpServletResponse response)
      throws ServletException, java.io.IOException {
    request.setCharacterEncoding("UTF-8");
   
    unsafeString=request.getParameter("str");
   
    try{
      Thread.sleep(5000);
    }
    catch(Exception ex){
      ex.printStackTrace();
    }
   
    PrintWriter out=response.getWriter();
    out.println(unsafeString);
  }
   
  public void doGet(HttpServletRequest request, HttpServletResponse response)
      throws ServletException, java.io.IOException {
    doPost(request, response);
  }
}

关于重定向的两种方法

在servlet中,重定向一般是通过HttpResponse的sendRedirect()方法或RequestDispatcher的forward方法来实现的.
sendRedirect的参数可以是相对或绝对地址,如果以/开头容器将认为相对于当前Web引用的根.这种请求将导致客户端浏览器请求URL跳转,而且从Browser的地址栏中可以看到新的Url地址.另外使用这个方法时,前一个页面的状态不会被带到下一个页面,通过request.getAttribute(“XXXX”)方法将得到空值.
RequestDispatcher是一个Web资源的包装器,可以用来把当前请求传递到该资源,而且客户端浏览器的地址栏也不会显示为转向后的地址.另外此方法还可以将请求发送到任意一个服务器资源.
如果两种方法都能达到要求,最好使用forward方法,它比sendRedirect安全而高效.

获取当前绝对路径

Servlet/JSP有时需要对拥有的资源进行操作,这就要求得到它们所在的绝对路径.此时可以使用ServletContext接口提供的方法来得到当前应用所在的绝对路径,代码如下:
ServletContext sct = getServletContext();
String realPath=sct.getRealPath("/");

注: ServletContext 用于Servlet和Servlet容器交换信息.




评论 / 个人网页 / 扔小纸条
* 昵称

已经注册过? 请登录

新用户请先注册 以便能显示头像及追踪评论回复

Email
网址
* 评论
表情
 


 

分类小组论坛
杂谈 , 娱乐、八卦 , 文学、艺术 , 体育 , 旅游、同城 , 象牙塔 , 情感 , 时尚、生活 , 星座 , 科技

请注意遵守中华人民共和国法律法规, 如威胁到本站生存, 将依法向有关部门报告, 同时本站的相关记录可能成为对您不利的证据.

相关法律法规
全国人大常委会关于维护互联网安全的决定
中华人民共和国计算机信息系统安全保护条例
中华人民共和国计算机信息网络国际联网管理暂行规定
计算机信息网络国际联网安全保护管理办法
计算机信息系统国际联网保密管理规定