Java Servlet简介
Servlet什么是ServletServlet是基于Java技术的Web组件,由容器管理并产生动态的内容。Servlet引擎作为WEB服务器的扩展提供支持Servlet的功能。Servlet与客户端通过Servlet容器实现的请求/响应模型进行交互。注意:Servlet不是从命令行启动的,而是由包含Java虚拟机的Web服务器进行加载Servlet是按照Servlet规范编写的Java类。Ser
文章目录
Servlet
什么是Servlet
Servlet是基于Java技术的Web组件,由容器管理并产生动态的内容。Servlet引擎作为WEB服务器的扩展提供支持Servlet的功能。Servlet与客户端通过Servlet容器实现的请求/响应模型进行交互。
注意:
Servlet不是从命令行启动的,而是由包含Java虚拟机的Web服务器进行加载
Servlet是按照Servlet规范编写的Java类。
Servlet应用请求/响应模型,扩展了服务器的功能。
Servlet是WEB应用程序中的一个组件。
Servlet是在JSP之前就存在的运行在服务端的一种Java技术,它是用Java语言编写的服务器端程序在JSP技术出现之前,Servlet被广泛地应用来开发动态的Web应用程序.如今在J2EE项目的开发中,Servlet仍然被广泛的使用。
Servlet是一种独立于平台和协议的服务器端的Java技术,可以用来生成动态的Web页面与传统的CGI(公共网关接口)和许多其他类似CGI技术相比,Servlet具有更好的可移植性、更强大的功能,更少的投资,更高的效率,更好的安全性等特点。
Servlet的运行过程
⒈、客户端发送请求至服务器端;
⒉、服务器端根据web.xml文件中的Servlet相关配置信息,将客户端请求转发到相应的Servlet
⒊、 Servlet引擎调用Service()方法,根据request对象中封装的用户请求与数据库进行交互,返回数据之后,Servlet会将返回的数据封装到response对象中;
⒋、 Servlet生成响应内容并将其传给服务器。响应内容动态生成,通常取决于客户端的请求
⒌、 服务器将响应返回给客户端
Servlet的生命周期
1、 加载和实例化;在第一次请求Servlet时,Servlet容器将会创建Servlet实例;
2、 初始化;Servlet容器加载完成Servlet之后,必须进行初始化,此时,init方法将被调用;
3、Servlet初始化之后,就处于响应请求的就绪状态,此时如有客户端请求发送,就会调用Servlet实例的service()方法,并且根据用户的请求方式,调用doPost或者doGet方法;
4、 最后,Servlet容器负责将Servlet实例进行销毁,调用destroy方法实现;
对于更多的客户端请求,Server创建新的请求和响应对象,仍然激活此Servlet的service()方法,将这两个对象作为参数传递给它。如此重复以上的循环,但无需再次调用init()方法。
一般Servlet只初始化一次(只有一个对象),当Server不再需要Servlet时(一般当Server关闭时),Server调用Servlet的Destroy()方法。
实例演示
html代码–客户端浏览器
1、注册页面
<html>
<head>
<title>注册页面</title>
</head>
<body>
<form action="/Create">
<p>用户名:<input type="text" name="user"></p>
<p>密码:<input type="password" name="pwd"></p>
<p>确认密码:<input type="password" name="cfmPwd"></p>
<p><input type="submit" name="注册"></p>
</form>
</body>
</html>
2、登录页面
<html>
<head>
<title>登录首页</title>
</head>
<body>
<form action="/doLogin">
<p>请输入用户名:<input type="text" name="user"></p>
<p>请输入密码:<input type="password" name="pwd"></p>
<p><input type="submit"></p>
</form>
</body>
</html>
3、配置web.xml文件
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"
version="4.0">
<servlet>
<servlet-name>userServlet</servlet-name>
<servlet-class>servlet.UserServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>userServlet</servlet-name>
<url-pattern>/Create</url-pattern>
</servlet-mapping>
</web-app>
配置文件
1、User类
public class User {
private int user_id;
private String user_name;
private String password;
@Override
public String toString() {
return "User{" +
"user_id=" + user_id +
", user_name='" + user_name + '\'' +
", password='" + password + '\'' +
'}';
}
public int getUser_id() {
return user_id;
}
public void setUser_id(int user_id) {
this.user_id = user_id;
}
public String getUser_name() {
return user_name;
}
public void setUser_name(String user_name) {
this.user_name = user_name;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
}
2、UserDao接口
public interface UserDao {
//注册
boolean createUser(String username,String password);
//登录
boolean login(String username,String password);
//根据用户名查询数据库是否有重复用户
boolean QueryUserByName(String username);
//展示所有用户
ArrayList<User> querAll();
//修改密码
void changePassword(String username,String password);
//删除用户
void deleteUserById(String username,String password);
}
3、UserDao接口的实现类
public class UserDaoImpl extends BaseDAOImpl implements cn.kgc.kb11.dao.impl.UserDao {
private final String Driver= "com.mysql.jdbc.Driver";
private final String url="jdbc:mysql://localhost/bank";
private final String name="root";
private final String pwd="1";
@Override
public boolean createUser(String username, String password) {
String sql="insert into user(user_name,password) values(?,?)";
getConn(Driver,url,name,pwd);
return update(sql,username,password);
}
@Override
public boolean login(String username, String password) {
String sql="select * from user where user_name=? and password=?" ;
getConn(Driver,url,name,pwd);
query(sql,username,password);
try {
if (getRs().next()) {
return true;
}
} catch (SQLException e) {
e.printStackTrace();
}
return false;
}
@Override
public boolean QueryUserByName(String username) {
String sql="select * from user where user_name=?";
getConn(Driver,url,name,pwd);
query(sql,username);
try {
if (getRs().next()) {
return true;
}
} catch (SQLException e) {
e.printStackTrace();
}
return false;
}
@Override
public ArrayList<User> querAll() {
return null;
}
@Override
public void changePassword(String username, String password) {
}
@Override
public void deleteUserById(String username, String password) {
}
}
4、BaseDao接口
public interface BaseDAO {
void getConn(String driver,String url,String user,String pwd);
void query(String sql,String... params);
boolean update(String sql,String... params);
void close();
}
5、BaseDao接口的实现类
public class BaseDAOImpl implements BaseDAO {
private Connection conn;
private PreparedStatement pst;
private ResultSet rs;
public ResultSet getRs() {
return rs;
}
@Override
public void getConn(String driver, String url, String user, String pwd) {
try {
Class.forName(driver);
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
try {
conn = DriverManager.getConnection(url,user,pwd);
} catch (SQLException e) {
e.printStackTrace();
}
}
@Override
public void query(String sql, String... params) {
try {
pst=conn.prepareStatement(sql);
for (int i = 0; params!=null && i < params.length; i++) {
pst.setObject(i+1,params[i]);
}
rs=pst.executeQuery();
}
catch (SQLException e) {
e.printStackTrace();
}
}
@Override
public boolean update(String sql, String... params) {
int num=0;
try {
pst=conn.prepareStatement(sql);
for (int i = 0; params!=null && i < params.length; i++) {
pst.setObject(i+1,params[i]);
}
num=pst.executeUpdate();
}
catch (SQLException e) {
e.printStackTrace();
}
return num>0;
}
@Override
public void close() {
try {
if (rs!=null)
rs.close();
if (pst!=null)
pst.close();
if (conn!=null)
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
}
6、UserService接口
public interface UserService {
boolean register(String username,String password,String cfmPwd);
boolean login(String username,String password);
ArrayList<User> queryALL();
void modify(String username,String password);
void delete(String username,String password);
}
7、UserService接口的实现类
public class UserServiceImpl implements UserService {
UserDao dao=new UserDaoImpl();
@Override
public boolean register(String username, String password,String cfmPwd) {
if (username==null ||password==null||cfmPwd==null)
return false;
boolean exists=dao.QueryUserByName(username);
if (exists)
return false;
if (!password.equals(cfmPwd))
return false;
if ("mahuateng".equals(username))
return false;
return dao.createUser(username,password);
}
@Override
public boolean login(String username, String password) {
if (username==null ||password==null)
return false;
boolean exists=dao.login(username,password);
return exists;
}
@Override
public ArrayList<User> queryALL() {
return null;
}
@Override
public void modify(String username, String password) {
}
@Override
public void delete(String username, String password) {
}
}
servlet处理过程
1、UserServlet类
public class UserServlet extends HttpServlet {
UserService service=new UserServiceImpl();
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// String name=req.getParameter("user");
////// String pwd=req.getParameter("pwd");
////// String cfmPwd=req.getParameter("cfmPwd");
////// boolean isSuccess = service.register(name, pwd, cfmPwd);
//////// System.out.println(isSuccess?"注册成功":"注册失败");
////// //页面跳转
////// if (isSuccess){
////// resp.sendRedirect("/login/home.jsp");
////// }else {
////// req.getRequestDispatcher("/login/createUser.jsp").forward(req,resp);
////// }
////// }
String name=req.getParameter("user");
String pwd=req.getParameter("pwd");
boolean isSuccess = service.login(name, pwd);
if (isSuccess){
req.getRequestDispatcher("/login/doLogin.jsp").forward(req,resp);
}else{
resp.sendRedirect("/login/home.jsp");
}
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
super.doPost(req, resp);
}
@Override
protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
super.service(req, resp);
}
}
Servlet如何同时处理多个请求?
Servlet采用多线程来处理多个请求的同时访问。Servlet容器通过线程池来管理维护服务请求。所谓线程池,相当于数据库连接池,实际上是等待执行代码的一组线程,叫做工作者线程。Servlet容器通过一个调度线程来管理工作者线程。
1、当容器收到一个Servlet的访问请求,调度者线程就从线程池中选出一个工作者线程,将用户请求传递给该线程,然后由该线程处理Servlet的service()方法;
2、 当这个线程在执行的时候,容器收到一个新的请求,调度者线程再次从线程池中选出一个新的工作者线程;
3、当容器同时收到对同一个Servlet的多个请求时,那么Servlet的service方法将在多线程中并发执行。
注:
1.Servlet容器默认采用单实例多线程的方式来处理请求。这样减少了产生Servlet实例的开销,提升了对请求的响应时间;
2.对于Tomcat容器来讲,可以在其server.xml中通过中设置线程池中的线程数目。
如何开发线程安全的Servlet?
Servlet容器采用多线程来处理请求,提高性能的同时也造成了线程安全问题。要开发线程安全的Servlet应该从一下几个方面进行:
1、变量的线程安全; 多线程并不共享局部变量,所以我们要尽可能的在Servlet中使用局部变量;
2、代码块的线程安全; 使用同步块Synchronized,防止可能调用的代码块;但是要注意的是,要尽可能得缩小同步代码的方范围,不要在service方法和响应方法上直接使用同步,这会严重影响性能。
3、属性的线程安全; ServletContext,HttpSession,ServletRequest对象中属性;
4、使用同步集合; 使用Vector代替ArrayList,使用HashTable代替HashMap;
5、不要在Servlet中创建自己的线程来完成某个功能; Servlet本身就是多线程的,如果再创建新的线程,将会导致线程执行复杂化,出现线程安全问题;
6、在多个Servlet中,对外部对象,比如:文件;进行修改操作一定要加锁,做到互斥访问;
总结
一个servlet就是Java编程语言中的一个类,它被用来扩展服务器的性能,服务器上驻留着可以通过“请求-响应”编程模型来访问的应用程序。Servlet通过解析http请求,取得客户端的参数来进行下一步操作。其实简单来说,servlet就是一个控制器,取参数,调用业务逻辑。
而在.net 中HttpHandler是一个HTTP请求的真正处理中心,也正是在这个HttpHandler容器中,ASP.NET Framework才真正地对客户端请求的服务器页面做出编译和执行,并将处理过后的信息附加在HTTP请求信息流中再次返回到HttpModule中。
今天的分享就到这里,谢谢!
更多推荐



所有评论(0)