zoukankan      html  css  js  c++  java
  • Servlet开发详解

    什么是servlet? 
    servlet技术是在java ee出现之前就存在了,在开发动态网页中得到广泛的应用,直到现在的java ee项目中也是非常重要的,同时jsp也是在servlet的基础上发展起来的。
    servlet(java服务器小程序)是用java编写的服务器程序,它的特点: 
     1.由服务器调用和执行 
     2.用java语言编写的 
     3.按照servlet规范开发 
     4.功能强大,可以完成几乎所有的网站功能 
     5.是学习jsp的基础
    
    
    
    
    开发servlet有三种方法:
    1.实现servlet接口案例如下:

    //这是我的第一个Serlvet,使用实现servlet接口的方式来开发


    package com.tsinghua;

    import javax.servlet.*;
    import java.io.*;
    import javax.servlet.Servlet;
    import javax.servlet.ServletConfig;
    import javax.servlet.ServletException;
    import javax.servlet.ServletRequest;
    import javax.servlet.ServletResponse;
    import java.io.IOException;

    public class Hello implements Servlet {

    //该函数用于初始化该serlvet(类似于类的构造函数)
    //该函数只会被调用一次(当用户第一次访问该servlet时被调用)
    public void init(ServletConfig parm1) throws ServletException {
    // TODO: Add your code here
    System.out.println ("init it");
    }

    //
    public ServletConfig getServletConfig() {
    // TODO: Add your code here
    return null;
    }

    //这个函数用于处理业务逻辑
    //程序员应当把业务逻辑代码写在这里
    //当用户每访问该servlet是,都会调用
    //req: 用于获得客户端(浏览器)的信息
    //res: 用于向客户端(浏览器)返回信息
    public void service(ServletRequest req, ServletResponse res) throws ServletException, IOException {
    // TODO: Add your code here

    System.out.println ("service it");
    //从res中得到PrintWriter
    PrintWriter pw=res.getWriter();
    pw.println("hello,world");
    }

    //
    public String getServletInfo() {
    // TODO: Add your code here
    return "";
    }

    //销毁servlet实例(释放内存)
    //1.reload 该serlvet(webApps) //2.关闭tomcat //3.关机
    public void destroy() {
    System.out.println ("destroy!");
    // TODO: Add your code here
    }

    }

     
    2.继承GenericServlet案例如下:
     

    //这是第二种开发servlet的方法(继承GenericServlet开发)

    package com.tsinghua;

    import javax.servlet.GenericServlet;
    import javax.servlet.*;

    import java.io.*;

    public class HelloGen extends GenericServlet{

    //重写service方法即可

    public void service (ServletRequest req,ServletResponse res){


    //返回hello,world! generic

    try {

    PrintWriter pw=res.getWriter();
    pw.println("hello,world! generic");
    }
    catch (Exception ex) {

    ex.printStackTrace();
    }

    }

    }

    3.继承HttpServlet案例如下:
     

    //这是第三种开发servlet的方法(通过继承HttpServlet)


    package com.tsinghua;

    import javax.servlet.http.*;
    import java.io.*;
    import javax.servlet.*;

    public class HelloHttp extends HttpServlet {

    //处理get请求
    //req: 用于获得客户端(浏览器)的信息
    //res: 用于向客户端(浏览器)返回信息
    public void doGet(HttpServletRequest req,HttpServletResponse res){

    //业务逻辑

    try {

    PrintWriter pw=res.getWriter();
    pw.println("hello,http");

    }
    catch (Exception ex) {

    ex.printStackTrace();
    }
    }

    //处理post请求
    //req: 用于获得客户端(浏览器)的信息
    //res: 用于向客户端(浏览器)返回信息
    public void doPost(HttpServletRequest req,HttpServletResponse res){

    this.doGet(req,res);

    }

    }

    Servlet开发流程:
    1.在%TOMCAT_HOME%/webapps下WEB-INF的文件夹,写一个文件web.xml(该网站的配置信息),建立一个classes的子文件夹,也可以从别的目录ROOT下拷贝
     
    2.开发servlet(引入Tomcat文件夹下lib文件夹里的servlet-api.jar)
     
    3.部署你的servlet(servlet开发流程)
     
    4.启动Tomcat,访问你的servlet,在浏览器的地址栏中输入:http://127.0.0.1:8080/MyWebSite/Jasxu回车就可以看到servlet的输出
     部署Servlet文件:
    注意:127.0.0.1是服务器所在的IP,8080是端口号,要根据实际情况定。
    在web.xml文件中添加如下代码:
    <servlet>
    <!—给servlet取名,可以随意取名-->
    <servlet-name>hello</servlet-name>
    <!—指明servlet的路径,就是servlet的包+类名-->
    <servlet-class>com.test.Hello</servlet-class>
    </servlet>
    <servlet-mapping>
    <!—给servlet取名,可以随意取名-->
    <servlet-name>hello</servlet-name>
    <!—浏览器中输入的url,可以随意取名-->
    <url-pattern>/hello<url-pattern>
    </servlet-mapping>
    Servlet的生命周期:
    servlet部署在容器里(我们使用的是Tomcat,也可是别的,比如jboss,weblogic。。。),它的生命周期由容器来管理。
     
    servlet的生命周期分为以下几个阶段:
    1.装载servlet,由相应的容器来完成
    2.创建一个servlet实例
    3.调用servlet的init()方法,该方法只会在第一次访问servlet时被调用一次
    4.服务:调用servlet的service()方法,一般业务逻辑在这里处理,该方法在访问该servlet时,会被调用
    5.销毁:调用servlet的destroy()方法,销毁该servlet实例,该方法在以下情况被调用:
    a)tomcat重新启动
    b)reload该webapps
    c)重新启动电脑
    同一用户的不同页面共享数据:
    四种方法:
    1. cookie技术
    2.sendRedirect()跳转
    3.隐藏表单提交(form)
    4.session技术
     
    什么是cookie?
    服务器在客户端保存用户的信息,比如登录名、密码……就是cookie
     
    这些信息就像是小甜饼一样,数据量并不大,服务器端在需要的时候可以从客户端读取
    cookie可以用来做什么?
    1.保存用户名、密码,在一定时间不用重新登录
    2.记录用户访问网站的喜好,比如有无背景音乐、网页的背景色是什么
    3.网站的个性化,比如定制网站的服务、内容
    COOKIE使用?
    1.cookie有点像一张表,分两列,一个是名字,一个是值,数据类型都是String
    2.如何创建一个cookie(在服务器端创建的)
    Cookie c=new Cookie(String name, String val);
    3.如何将一个cookie添加到客户端
    response.addCookie(c);
    4。如何读取cookie(从客户端读到服务器)
    request.getCookie();
    COOKIE其它说明?
    1.可以通过IE——工具——internet选项——隐私——高级来启用或是禁用cookie
     
    2.由于cookie的信息是保存在客户端的,因此安全性不高
     
    3.cookie信息的生命周期可以在创建时设置(比如30s),从创建那一时刻起,就开始计时,到时该cookie的信息就无效了
    sendRedirect()方法?
    通过该方法可以将一个页面的信息传送给另外的页面,比如:
    sendRedirect(“welcome?uname=aaa”);
    优点:传送信息的速度比较快
    缺点:它只能传送字符串,而不能传送一个对象
    sendRedirect(“welcome?uname=aaa”);
    注意点:
    1.welcome代表你要跳转的那个servlet的url
    2.servlet url名和变量之间有个?
    3.如要传递两个以上的值,它们之间要用符号&分开,比如sendRedirect(“welcome?uname=aaa&passwd=123”);
    4.如果传递的是中文,那你将得到乱码,需要处理一下res.setContentType(“text/html,charset=gbk”);
    隐藏表单?
    这是最常见的一种方式,也是最简单的,但有时该技巧非常管用,形如:
    <form action=login>
    <input type=hidden name=a value=b>
    </form>
    通过隐藏表单,我们也可以将一个页面信息,传递给另外的页面。
     
    什么是session?
    当用户打开浏览器,访问某个网站时,服务器就会在服务器的内存为该浏览器分配一个空间,该空间被这个浏览器独占。这个空间就是session空间,该空间中的数据默认存在时间为30min,你也可以修改该值。
    session可以用来做什么?
    1.网上商城中的购物车
    2.保存登陆用户的信息
    3.将某些数据放入到session中,供同一用户的各个方面使用
    4.防止用户非法登陆到某个页面
    ……
     
    如何理解session?
    可以把session看做一张表,这张表有两列,而表有多少行理论上没有限制,每一行就是session的一个属性。每个属性包含有两个部分,一个是该属性的名字String,另外一个是它的值Object。
    如何使用session?
    1.得到session
    HttpSession hs=request.getSession(true);
    2.向session添加属性
    hs.setAttribute(String name,Object val);
    3.从session得到某个属性
    String name=hs.getAttribute(String name);
    4.从session中删除掉某个属性
    hs.removeAttribute(String name);
    5.注销session中的内容(比较安全的一种方式)
    ht.setMaxInactiveInterval(0);
     
    session的注意事项:
    1.session中属性存在的默认时间是30min,你也可修改它存在的时间:(a)修改web.xml    (b)在程序中修改
     
    2.上面说的这个30min指的是用户的发呆时间,而不是累计时间
     
    3.当某个浏览器访问网站时,服务器会给浏览器分配一个唯一的session id,并以此来区分不同的浏览器(即客户端)
     
    4.因为session的各个属性要占用服务器的内存,因此软件公司都是在迫不得已的情况下才使用
     
    Cookie VS Session:
    1.存在的位置
    cookie保存在客户端,session保存在服务器端
    2.安全性
    比较而言,cookie的安全性比session要弱
    3.网络传输量
    cookie通过网络在客户端与服务器端传输,而session保存在服务器端,不需要传输
     
    servlet操作数据库注意事项:
    需要将连接数据库的jar包,拷贝到tomcat服务器
    具体有两种方法:
    1)将jar包拷贝到tomcat目录下的lib文件夹里
    2)在webapps目录的WEB-INF文件下建立一个lib文件夹,然后将jar包拷贝到该文件夹下
     
    两种方法的区别:
    1)所有webapps都可以使用jar【公用lib库】
    2)只有放入jar的那个webapps能使用jar【私用lib库】
    SQL注入漏洞:
    select * from users where username=‘abc’ and passwd=‘123’ or 1=‘1’
     
    在Servlet中显示图片:
    在你的webapps下建立一个文件夹,比如images,然后将图片拷贝到该文件夹中,再在servlet中添加:
    <img src=*.images/图片名/>即可。
    Servlet中的分页的算法:
    需要定义四个变量,它们有各自的用处
    int pageSize:每页显示多少条记录
    int pageNow:希望显示第几页
    int pageCount:一共有多少页
    int rowCount:一共有多少条记录
     
    说明:
    pageSize是指定,pageNow是用户选择的。
    rowCount是从表中查询得到的。
    pageCount是计算出来的,该计算公式为:
    if(rowCount%pageSize==0) {
    pageCount=rowCount/pageSize;
    } else {
    pageCount=rowCount/pageSize+1;
    }
    针对前面提出的问题,我们可能很自然的想到,用
    select 字段名列表 from 表名 where id between ? and ?
    这个sql语句确实比较快,但是存在一个问题,即如果表的id被删除了,那么某页可能就会少一条记录。
     
    因此,我们的最终方法是如下语句:
    select top pageSize 字段名列表 from 表名 where id not in(select top pageSize*(pageNow-1) id from 表名)
     
    测试效率
    当表的记录超过100万条时,它的翻页就很慢,原因是它查询的结果是整张表。在实际的项目中,一张表超过100万是非常常见的,一些大型项目中一些表到达T级别也是有的。
    增加表的记录的语句可用:
    insert into 表名 (字段1,,2…) select 字段1,2… from 表名
    Servlet网站框架:
    问题分析:
    界面和业务逻辑放在一起(model1模式)存在以下问题:
    1.在LoginCheck.java文件和Welcome.java文件中都去操作了数据库,他们的逻辑相似,代码重复
    2.整个框架没有清晰的层次关系,显得非常乱
    3.代码一点也不优雅,可读性差,可维护性差
    问题改进:
    通过对问题的分析,我们可以对程序进行改进:
    1.进行分层(界面层、业务逻辑层)
    【mv模式】m:model   v:view
    2.将常用的代码(比如连接数据库)封装到类中
    ServletContext讲解:
    什么是ServletContext?
     
    要理解ServletContext,就必须和cookie、session做一个对比,如右图所示:
    可以把它想象成是一个共用的空间,可以被所有的用户访问,也就是说:A客户可以访问D,B客户也能访问D,C客户也能访问D。
    如何使用ServletContext?
    1.如何得到ServletContext实例
    this.getServletContext();
    2.你可以把它想象成一张表,这个和session非常相似,每一行就是一个属性:
    添加属性setAttribute(String name, Object ob);
    得到值getAttribute(String name); 返回Object
    删除属性removeAttribute(String name);
    3.生命周期
    ServletContext中的生命周期从创建开始,到服务器关闭而结束。
    使用ServletContext的注意事项:
    因为存在ServletContext中的数据会长时间保存在服务器,会占用内存,因此我们建议不要向ServletContext中添加过大的数据,切忌。
     
    使用ServletContext实例:
    在网站开发中,有很多功能需要使用ServletContext,比如:
    1.网站计数器
    2.网站在线用户显示
    3.简单的聊天系统
    总之,如果是涉及到不同用户共享数据,而这些数据量不大,同时又不希望写入数据库中,我们就可以考虑使用ServletContext来实现。
    Servlet中操作文件:
    因为servlet本来就是一个.java文件,因此,servlet中操作文件和普通java文件操作文件是一样的。
     
    // 创建一个FileReader
    FileReader fr=new FileReader(“d:\myCounter.txt”);
    BufferedReader br=new BufferedReader(fr);
    // 读出一行数据
    String numVal=bw.readLine();
    // 关闭文件流
    bw.close();
     
    创建一个FileWriter
    内存数据→磁盘文件(写入、输出)
    内存数据←磁盘文件(读入,输入)
    如何修改TOMCAT的端口???
    在某些情况下,可能需要修改Tomcat监听的端口8080,比如:
    1)需要启动两份Tomcat
    2)某个服务占用了8080端口(1433,1521,3306)
    找到Tomcat目录下的conf文件夹里的server.xml,对其端口号进行修改。
     
    查看本机所有端口的命令: netstat -an
    设置TOMCAT虚拟目录???
    为什么要设置虚拟目录?
    目前,我们的网站站点都是放在默认的目录下tomcat/webapps下,但是,在某些情况下,可能需要把站点放在别的目录下,比如:
    1)tomcat所在的磁盘空间不够用了
    2)为了统一管理,希望放在某个特定的目录下,而不是放在默认的tomcat/webapps下
     
    如何设置虚拟目录?
    打开tomcat安装目录下的conf子目录,修改其中的serve.xml文件,在适当的位置添加如下信息:
    <Context path=“/yourside” docBase=“c:mysite” debug=“0”/>
     
    设置TOMCAT管理员密码????
    为什么要设置管理员密码?
    在Tomcat安装目录下的conf/users.xml文件中可以设置密码,密码设置可以防止非法用户远程登录到tomcat。
    1)默认情况下,管理员的密码是空密码,这样不法分子可能远程发布一个站点,并在某个servlet中加入一些可怕的语句(比如重启、关机)
    2)安全演示:sql注入漏洞
    Select * from users where name=‘’ and password=‘’;
    利用密码为空破坏过程:
    1.利用jdk自带的jar工具将有搞破坏的站点打包成*.war文件,打包命令:jar –cvf war文件名*.*
    2.通过tomcat管理页面将站点发布到tomcat
    3.访问有破坏代码的servlet,这样你就被黑了
     
     
     
     
  • 相关阅读:
    Android 进程生命周期 Process Lifecycle
    .NET Core微服务之基于IdentityServer建立授权与验证服务(续)
    .NET Core微服务之基于IdentityServer建立授权与验证服务
    .NET Core微服务之基于Ocelot实现API网关服务(续)
    .NET Core微服务之基于Ocelot实现API网关服务
    .NET Core微服务之基于Polly+AspectCore实现熔断与降级机制
    .NET Core微服务之基于Consul实现服务治理(续)
    .NET Core微服务之基于Consul实现服务治理
    一朝入梦,终生不醒:再看红楼梦,也谈石头记
    月光下的凤尾竹—彩云之南西双版纳游记
  • 原文地址:https://www.cnblogs.com/Jasxu/p/servlet.html
Copyright © 2011-2022 走看看