文章目录
使用IDEA配置Tomcat和连接MySQL数据库(JDBC)详细步骤_tomcat配置文件查找jdbc链接-优快云博客
Servlet
概念:用Java编写的线程安全的由Java编写的WEB组件,它在MVC设计模式中起到控制层的作用。
作用:
-
CGI—通用网关接口:从WEB容器中取得数据(内置对象)的能力。
-
创建表单bean,收集表单数据。
-
分析请求,分发请求,
-
根据业务层返回的转向信息,转到视图组件。
JavaServlet框架(工作流程)
这里的web组件其实有两个,一个是视图组件jsp,一个是控制组件servlet
JavaBean也有两个:业务bean,持久bean
启动tomcat,servlet就创建了
tomcat启动以后,用户发请求【例如,查找姓名为Tom的学生的信息,这个请求通过浏览器,通过
表单发出去】,这个请求发送到http协议上,首先给tomcat服务器,tomcat服务器接收这个请求,
为这个请求创建request,response内置对象;request内置对象存放请求字符串,请求参数,IP地址
和cookie;tomcat通过配置【必须配置】把请求转给控制层【医导】servlet组件,同时把request内置
对象,response内置对象注入给servlet;servlet调用相应的方法后,创建表单bean,从request中拿到
请求参数封装到表单bean;servlet拿到请求参数,对请求参数进行分析,把请求分发给业务层【给
业务层request,response,表单bean】;业务组件如果需要到数据库里查找信息,业务层又把请求
交给了JavaBean的持久层,调用持久层对象的方法【业务层已经把表单bean传给了持久层,持久层
拿到了表单bean,就拿到了用户的请求参数】,持久层通过sql语句访问数据库,最后会拿到结果
【Tom的姓名,年龄等一些信息】,持久层拿到了用户Tom的一些信息,持久层创建结果bean,然
后把结果信息封装到结果bean里面,紧接着持久层把结果bean返回给业务层;业务层会把这个结果
bean设到一个request内置对象,然后业务层又向控制层返回一个转向信息;控制层对我的转向信息
进行分析,转向了相应的视图组件jsp【视图组件不一定是jsp】;视图组件从request内置对象当中拿
到了我的结果信息,用el表达式或者标签进行处理【这个过程叫渲染】;最后渲染的结果通过
response放到HTTP协议返回给浏览器
Servlet语法
-
包声明
包声明【web组件都要实现分包管理的原则】【servlet的字节码文件应该放到WEBINF classes
下的以包对应的目录结构下】 -
包导入import
-
类继承HttpServlet
-
重写doGet,doPost,形参HttpServletRequest接口
【当我的请求是get请求的时候,tomcat一
旦调用servlet,它就调用servlet的doGet方法,来处理我们的get请求,同时servlet会把封
装请求参数的对应的request,response注入给这个方法,这个方法就要用相应的形参来
接收所注入进来的request和response内置对象的地址【对象的传递传的是地址】】,doPost方法【类似】
部署Servlet类
先要配置servlet,再把 SimpleServlet.java放在WEBINF下的classes下进行打包编译
-
SimpleServlet.java
package cn.zte.pxb.servlet ; //IOException属于java.io包下 import java.io.* ; // ServletException属于javax.servlet包下 import javax.servlet.* ; // HttpServletRequest、HttpServletResponse存放在javax.servlet.http包下 // HttpServlet属于javax.servlet.http包下 import javax.servlet.http.* ; public class SimpleServlet extends HttpServlet { // 表示处理get请求 public void doGet(HttpServletRequest req,HttpServletResponse resp) throws IOException,ServletException { System.out.println("doGet方法被调用"); PrintWriter out = resp.getWriter() ; out.println("<HTML>") ; out.println("<HEAD>") ; out.println("<TITLE>THE FIRST SERVLET</TITLE>") ; out.println("</HEAD>") ; out.println("<BODY>") ; out.println("<H1>Hello World!!!</H1>") ; out.println("</BODY>") ; out.println("</HTML>") ; out.close() ; } public void doPost(HttpServletRequest req,HttpServletResponse resp) throws IOException,ServletException {System.out.println("doPost方法被调用"); this.doGet(req,resp) ; } }
在Tomcat上配置Servlet(支持jdk1.8 Tomcat 8 \9)
-
把tomcat下的lib文件夹下的servlet-api.jar复制到jdk1.8.0_71\jre\lib\ext下。
-
servlet配置 配置时最好只有一个,可以有多个
servlet组件是不能通过文件名访问的,必须要通过映射名访问 <servlet-name>simple</servlet-name> <servlet-class>cn.mldn.lxh.servlet.SimpleServlet</servlet-class> //tomcat一启动就会读取项目的web.xml文件,检查servlet标签,看看里面有没有load-on- startup //如果有,马上按照servlet-class的指示到WEBINF的classes下,找到servlet的class //然后用无参的构造方法创建出servlet对象 //如果没有配load-on-startup,它就不会创建servlet对象;没配,只会在用户第一次访问servlet 的时候他才会创建 //一个项目不一定有只有一个servlet,他可以有多个 // <load-on-startup>0</load-on-startup> 中 '0'代表优先级【0~9】,越小优先级越高 */ <servlet> <servlet-name>simple</servlet-name> <servlet-class>cn.zte.pxb.servlet.SimpleServlet</servlet-class> <load-on-startup>0</load-on-startup> </servlet> <servlet-mapping> <servlet-name>simple</servlet-name> <url-pattern>/demo</url-pattern> </servlet-mapping>
配置servlet时,jdk11.0.1以上(ps:如果上面的配置配置不了,那就试试这个)
在电脑的新建一个名字为CLASSPATH的系统变量,把tomcat下的lib文件夹下的servlet-api.jar的路径加
上去
比如:.;C:\some\other\path;C:\Program Files\Apache Software Foundation\Tomcat 9.0\lib\servlet-api.jar
servlet生命周期
有1 则Tomcat一启动就创建,如果没有,则Servlet在第一次访问时才创建(Servlet创建)--------->Servlet创建后,立刻初始化(初始化)---------->doget/doPost ,处理get/post请求。在这个方法里,通常创建表单bean接收请求参数,把参数传递给业务层,业务层调用持久层来访问数据库,(请求的处理)----------->Tomcat关闭,调用Servlet的destory()方法(销毁)----------->把销毁的servlet移除内存(垃圾回收机制)
数据库 | 用户名 | 密码 | 端口号 |
---|---|---|---|
Mysql | root | 123456 | 3306 |
Oracle | scott | tiger | 1521 |
SqlSever | sa | 123 | 1433 |
servlet一般有四个方法:
package cn.mldn.lxh.servlet ;
import java.io.* ;
import javax.servlet.* ;
import javax.servlet.http.* ;
public class LifeCycleServlet extends HttpServlet{
// 初始化
/*
public void init() throws ServletException
System.out.println("** Servlet 初始化...") ;
{
}
{
}
*/
// 初始化
public void init(ServletConfig config) throws ServletException
System.out.println("** ServletConfig 初始化...") ;
{
}
// 表示处理get请求
public void doGet(HttpServletRequest req,HttpServletResponse resp) throws
IOException,ServletException
System.out.println("** Servlet doGet处理...") ;
{
}
// 处理post请求
public void doPost(HttpServletRequest req,HttpServletResponse resp) throws
IOException,ServletException
System.out.println("** Servlet doPost处理...") ;
{
}
// 销毁
//servlet不知道用户什么时候发请求,所以一般情况下servlet不会关闭
//一般服务器关闭或修改配置后servlet销毁
public void destroy()
System.out.println("** Servlet 销毁...") ;
{
}
//servlet对象一创建就调用init方法,就把封装servlet组件的配置信息的config内置对象注入进来
}
-
LifeCycleServlet.java
package cn.zte.pxb.servlet ; import java.io.* ; import javax.servlet.* ; import javax.servlet.http.* ; public class LifeCycleServlet extends HttpServlet { // 初始化 public void init(ServletConfig config) throws ServletException { System.out.println("** Servlet 初始化 ...") ; } // 表示处理get请求 public void doGet(HttpServletRequest req,HttpServletResponse resp) throws IOException,ServletException { System.out.println("** Servlet doGet处理 ...") ; } // 处理post请求 public void doPost(HttpServletRequest req,HttpServletResponse resp) throws IOException,ServletException { this.doGet(req,resp); //System.out.println("** Servlet doPost处理 ...") ; } // 销毁 public void destroy() { System.out.println("** Servlet 销毁 ...") ; } } /* <servlet> <servlet-name>life</servlet-name> <servlet-class>cn.zte.pxb.servlet.LifeCycleServlet</servlet-class> <load-on-startup>1</load-on-startup> </servlet> <servlet-mapping> <servlet-name>life</servlet-name> <url-pattern>/lc</url-pattern> </servlet-mapping> */
servlet的注解
-
HelloServlet
package com.zte.servlet; import java.io.IOException; import javax.servlet.ServletException; import javax.servlet.annotation.WebServlet; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; //@WebServlet("/hello") /* 这个注解相当于以下配置 <servlet> <servlet-name>life</servlet-name> <servlet-class>cn.zte.pxb.servlet.HelloServlet</servlet-class> <load-on-startup>1</load-on-startup> </servlet> <servlet-mapping> <servlet-name>life</servlet-name> <url-pattern>/lc</url-pattern> </servlet-mapping> <servlet-mapping>: 这个是用来接受用户请求的,doget,dopost方法 */ @WebServlet(urlPatterns="/hello",loadOnStartup=1) public class HelloServlet extends HttpServlet { public void init()throws ServletException { System.out.println("Servlet对象被创建,执行init()方法"); } public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { response.getWriter().write("Hello Servlet3.0"); } public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { this.doGet(request, response); } }
servlet初始化
-
LifeCycleServlet1.java
package cn.zte.pxb.servlet ; import java.io.* ; import javax.servlet.* ; import javax.servlet.http.* ; public class LifeCycleServlet1 extends HttpServlet { // 初始化 public void init() throws ServletException { System.out.println("** Servlet使用 init() 初始化 ...") ; } // 初始化 public void init(ServletConfig config) throws ServletException { System.out.println("** Servlet 使用 init(ServletConfig config)初始化 ...") ; } } /* <servlet> <servlet-name>life</servlet-name> <servlet-class>cn.zte.pxb.servlet.LifeCycleServlet1</servlet-class> <load-on-startup>0</load-on-startup> </servlet> */
servlet初始化参数的获取
package cn.mldn.lxh.servlet ;
import java.io.* ;
import javax.servlet.* ;
import javax.servlet.http.* ;
public class InitParameterServlet extends HttpServlet
{ private String usename=null; //实例全局变量
private String password=null; //实例全局变量
// 初始化
// 要取得初始化参数,必须使用以下初始化方法
public void init(ServletConfig config) throws ServletException
{
// config对象中有取得初始化参数的方法:getInitParameter("参数名称")
this.usename= config.getInitParameter("usename") ;
this.password = config.getInitParameter("password") ;
String dd = config.getInitParameter("DBDRIVER") ;
System.out.println("usename => "+this.usename) ;
System.out.println("password => "+this.password) ;
System.out.println("DBDRIVER => "+dd) ;
}
// 表示处理get请求
public void doGet(HttpServletRequest req,HttpServletResponse resp) throws IOException,ServletException
{
System.out.println("** Servlet doGet处理 ...") ;
System.out.println("usename="+this.usename) ;
System.out.println("password="+this.password) ;
}
// 处理post请求
public void doPost(HttpServletRequest req,HttpServletResponse resp) throws IOException,ServletException
{
// System.out.println("** Servlet doPost处理 ...") ;
}
// 销毁
public void destroy()
{
// System.out.println("** Servlet 销毁 ...") ;
}
}
/*
<servlet>
<servlet-name>param</servlet-name>
<servlet-class>cn.mldn.lxh.servlet.InitParameterServlet</servlet-class>
<load-on-startup>0</load-on-startup>
<init-param>
<param-name>usename</param-name>
<param-value>scott</param-value>
</init-param>
<init-param>
<param-name>password</param-name>
<param-value>tiger</param-value>
</init-param>
<init-param>
<param-name>DBDRIVER</param-name>
<param-value>oracle.jdbc.driver.OracleDriver</param-value>
</init-param>
</servlet>
<servlet-mapping>
<servlet-name>param</servlet-name>
<url-pattern>/init</url-pattern>
</servlet-mapping>
*/
线程安全问题
进程、线程、携程
只要对实例全局变量做操作会造成给线程不安全,因为其他方法可能会调用被修改的全局变量。
表单访问servlet
http://localhost:8080/classCode/02_servlet/formServlet1 --------->Servlet doGet处理提交参数 ,直接访问 URL,一般默认是get请求
http://localhost:8080/classCode/02_servlet/form.htm --------->Servlet doPost处理提交参数 ,因为直接通过表单来访问的。如果表单是post
-
form.html
<form action="formServlet1" method="post"> 用户名:<input type="text" name="uname"> <input type="submit" value="提交"> </form>
-
FormServlet.java
package cn.cx.servlet ; import java.io.* ; import javax.servlet.* ; import javax.servlet.http.* ; public class FormServlet extends HttpServlet { private ServletConfig config = null ; public void init(ServletConfig config) throws ServletException { this.config= config ; } // 表示处理get请求 public void doGet(HttpServletRequest req,HttpServletResponse resp) throws IOException,ServletException { System.out.println("** Servlet doGet处理提交参数 ...") ; req.getRequestDispatcher("demo.jsp").forward(req,resp); //this.doPost(req,resp) ; } // 处理post请求 public void doPost(HttpServletRequest req,HttpServletResponse resp) throws IOException,ServletException { String name = req.getParameter("uname") ; // 取得一个session对象 HttpSession session = req.getSession() ; session.setAttribute("sname",name) ; //以下方法拿application,依赖于init方法。 // 取得application对象-没有config // ServletContext app = this.getServletContext() ; 无参 // 取得application对象-有config //ServletContext app = this.config.getServletContext() ; 有参 ServletContext app=req.getSession().getServletContext();// 取得application对象 app.setAttribute("addr","www.zte.cn") ; System.out.println("** Servlet doPost处理提交参数 ...") ; System.out.println("name = "+name) ; // 重 //resp.sendRedirect("demo.jsp") ; req.getRequestDispatcher("demo.jsp").forward(req,resp); } }; /* <servlet> <servlet-name>form</servlet-name> <servlet-class>cn.cx.servlet.FormServlet</servlet-class> <load-on-startup>0</load-on-startup> </servlet> <servlet-mapping> <servlet-name>form</servlet-name> <url-pattern>/02_servlet/formServlet1</url-pattern> </servlet-mapping> */
-
demo.jsp
<h1><%=session.getAttribute("sname")%></h1> <h1><%=this.getServletContext().getAttribute("addr")%></h1> <h1><%=application.getAttribute("addr")%></h1>