是用Java编写的服务器端程序。其主要功能在于交互式地浏览和修改数据,生成动态Web内容。
HttpServlet类实现了GenericServlet接口,而GenericServlet接口又继承了Servlet接口,因此我们只需要使用继承了HttpServlet的类即可。
public class HelloServlet extends HttpServlet { @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { //super.doPost(req, resp); } @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { } }
存放资源的主机域名都是相对固定的如:http://localhost:8080/,通过设置请求别名就可以做到访问我们不同资源文件(Servlet实现类)。请求别名配置项位于web.xml文件。配置格式如下。
<servlet> <!--名称--> <servlet-name>HelloServlet</servlet-name> <!--接口实现类完整路径--> <servlet-class>com.han.servlet.HelloServlet</servlet-class> </servlet> <!-- 可以拥有多个请求别名 可以使用通配符定义 --> <servlet-mapping> <!--与servlet名称对应--> <servlet-name>HelloServlet</servlet-name> <!--请求别名 以 '/' 开头--> <url-pattern>/HelloServlet</url-pattern> </servlet-mapping>
servlet-name的设置支持使用通配符,因此可以将所有不存在的页面设置为一个特殊的错误界面。
<!--404--> <servlet> <servlet-name>error</servlet-name> <servlet-class>com.han.servlet.ErrorServlet</servlet-class> </servlet> <servlet-mapping> <servlet-name>error</servlet-name> <url-pattern>/*</url-pattern> </servlet-mapping>
在web.xml配置文件中,如果使用通配符的话要将其放在最后,因为顺序会影响识别的顺序。
调用响应(resp)中的getWriter方法,获得相应流并输出内容。
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { System.out.println("doGet方法执行了"); PrintWriter writer= resp.getWriter();//获得相应流 writer.println("hello,servlet"); }
ServletContext可以实现页面之间的相互通信。
首先在properties文件夹下创建一个静态文件,命名为db.properties,内容为username=xxx password=123456
获取属性路径下的流,申请一个Properties对象,并加载之前获取的属性流,使用pro.getProperty读取属性值并输出。
类似的可以通过此方法访问静态资源中的属性。
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { InputStream is=this.getServletContext().getResourceAsStream("/WEB-INF/classes/db.properties"); Properties pro=new Properties(); pro.load(is); String user=pro.getProperty("username"); String pwd=pro.getProperty("password"); resp.getWriter().println(user+"\n"+pwd); }
请求转发的实现,使用requestDispatcher的方法,首先利用转发的目标路径(“/gp”)创造requestDispatcher对象,之后使用该对象的forward方法,将请求和响应作为参数传入,完成转发。
当访问通过别名访问Servlet_request_demo01类时,会转发到/gp的页面下。
public class Servlet_request_demo01 extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { ServletContext i=this.getServletContext(); RequestDispatcher requestDispatcher=i.getRequestDispatcher("/gp");//转发的请求路径 requestDispatcher.forward(req,resp);//转发请求 } }
重点是要使用resp.setHeader方法设置响应的头信息,并通过流下载
resp.setHeader(“Content-Disposition”,“attachment;filename=”+FileName);
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { String RealPath="D:\\javaweb-project\\javaweb-project-servlet\\target\\javaweb-project-servlet\\WEB-INF\\1.jpg"; //获取下载的对象 System.out.println("下载文件的路径是"+RealPath); //获取下载文件的名字 String FileName=RealPath.substring(RealPath.lastIndexOf("\\")+1);// /的下一个开始到结尾的字串一定是文件名。 //设置相应头 resp.setHeader("Content-Disposition","attachment;filename="+FileName);//这里是分号 //获取下载文件的输入流 FileInputStream in=new FileInputStream(RealPath); //缓冲区 byte[] bytes=new byte[1024]; int len=0; ServletOutputStream out=resp.getOutputStream(); //响应的输出流 while((len=in.read(bytes))!=-1){ out.write(bytes,0,len); } out.close(); in.close(); }
使用setHeader将refresh属性设置为3,设置自动刷新时间。
BufferedImage创建一个空的图片对象,将生成的随机数画在图片中。
为了优化,禁止浏览器缓存,通过setHeader设置,resp.setDateHeader(“expires”,-1);
resp.setHeader(“Cache-Control”,“no-cache”);
resp.setHeader(“Pragma”,“no-cache”);
并告知浏览器接下来,以图片的形式打开,resp.setContentType(“image/jpeg”);
并将其输出到浏览器中。
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { //设置浏览器每3秒刷新一次 resp.setHeader("refresh","3"); //在内存中创建一个图片 //图片类的使用 BufferedImage bufferedImage=new BufferedImage(80,20,BufferedImage.TYPE_INT_RGB); Graphics2D g=(Graphics2D) bufferedImage.getGraphics();//创建笔。 g.setColor(Color.white); //填充图片 g.fillRect(0,0,80,20); //给图片写数据 g.setColor(Color.blue); g.setFont(new Font(null,Font.BOLD,20)); g.drawString(makeNum(),0,20); //告诉浏览器这个请求的方式用浏览器打开 resp.setContentType("image/jpeg"); //禁止浏览器缓存 resp.setDateHeader("expires",-1); resp.setHeader("Cache-Control","no-cache"); resp.setHeader("Pragma","no-cache"); //把图片写给浏览器 boolean write=ImageIO.write(bufferedImage,"jpg",resp.getOutputStream()); } private String makeNum(){ Random random=new Random(); String num=random.nextInt(9999999)+""; StringBuffer sb=new StringBuffer(); for(int i=0;i<7-num.length();i++){ sb.append("0"); } num=sb.toString()+num; return num; }
类似的也可以实现倒计时的功能。
使用sendRedirect方法
resp.setHeader("Location","/javaweb_project_servlet_war/img"); resp.setStatus(HttpServletResponse.SC_MOVED_TEMPORARILY);//等价于302 //上两行等价于下面的一行. resp.sendRedirect("/javaweb_project_servlet_war/img");
重定向与转发都是跳转到新的页面,但重定向会改变URL,转发不改变URL。
1、cookie数据存放在客户的浏览器上,session数据放在服务器上.
当你登录一个网站的时候,如果web服务器端使用的是session,那么所有的数据都保存在服务器上面,客户端每次请求服务器的时候会发送 当前会话的session_id,服务器根据当前session_id判断相应的用户数据标志,以确定用户是否登录,或具有某种权限。
Session是由应用服务器维持的一个服务器端的存储空间,用户在连接服务器时,会由服务器生成一个唯一的SessionID,用该SessionID 为标识符来存取服务器端的Session存储空间。而SessionID这一数据则是保存到客户端,用Cookie保存的,用户提交页面时,会将这一 SessionID提交到服务器端,来存取Session数据。
2.设置cookie时间可以使cookie过期。但是使用session-destory,我们将会销毁会话。
3.单个cookie保存的数据不能超过4K,很多浏览器都限制一个站点最多保存20个cookie。(Session对象没有对存储的数据量的限制,其中可以保存更为复杂的数据类型)
建立一个页面,显示上次访问的时间。
package com.han.cookie; import javax.servlet.ServletException; import javax.servlet.http.Cookie; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import java.io.IOException; import java.io.PrintWriter; import java.util.Date; public class CookieDemo01 extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { resp.setContentType("text/html;charset=UTF-8"); resp.setCharacterEncoding("utf-8"); req.setCharacterEncoding("utf-8");//解决乱码问题 PrintWriter out=resp.getWriter(); Cookie[] cookies= req.getCookies();//通过请求获取cookie if(cookies!=null){ out.write("上一次访问的时间"); for(int i=0;i<cookies.length;i++){ Cookie cookie=cookies[i];//找到cookie中lastlogintime属性 if(cookie.getName().equals("lastlogintime")){ //获取cookie中的数值 //getvalue获取的是一个string数值,目标是转化成date类的时间,可以先通过long的parselong方法转化为long,在创建date对象。 long lastlogintime=Long.parseLong(cookie.getValue()); Date date=new Date(lastlogintime); out.write(date.toLocaleString()); } } } else{ out.println("第一次访问"); } //如果需要存储中文,可以使用URLEncoder.encode("中文","utf-8"),并且取出的时候使用URLDecoder.urldecode解码输出。 //每次访问的时候,将当前时间的键值对作为参数构造一个新的cookie对象,通过请求 Cookie cookie=new Cookie("lastlogintime",System.currentTimeMillis()+""); cookie.setMaxAge(24*60*60);//设置cookie有效期 resp.addCookie(cookie); } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { } }
服务器会给每一个用户(浏览器)创建一个Session对象
一个Session独占一个浏览器,只要浏览器没有关闭,这个Session就存在
用户登录之后,整个网站都可以访问!—>保存用户的信息;保存购物车的信息。
package com.han.cookie; public class SessionDemo01 extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { //1.解决乱码问题 resp.setCharacterEncoding("utf-8"); req.setCharacterEncoding("utf-8"); resp.setContentType("text/html;charset=utf-8"); //2.创建并设置session HttpSession session= req.getSession(); session.setAttribute("name","张兵"); String sessionid=session.getId(); PrintWriter writer= resp.getWriter(); if(session.isNew()){ writer.println("session创建成功,id为"+sessionid); } else{ writer.println("session已经创建了,id为"+sessionid); } } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { super.doPost(req, resp); } }
package com.han.cookie; public class SessionDemo02 extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { resp.setCharacterEncoding("utf-8"); req.setCharacterEncoding("utf-8"); resp.setContentType("text/html;charset=utf-8"); //获取session中的信息。 HttpSession session=req.getSession(); String name=(String) session.getAttribute("name"); PrintWriter writer= resp.getWriter(); writer.println(name); //注销session,直接注销id,会生成新的sessionid。 session.removeAttribute("name"); session.invalidate(); //也可以通过设置web.xml配置进行 /*<session-config> <session-timeout>15</session-timeout> </session-config>*/ } }