JSP+Servlet+JavaBean的一个注册登录小项目

遵守javaweb开发的MVC模式。

已知问题:

1.不能注册中文用户(并没有用pattern约束)

2.没有注册输入格式不对的提示,但是可以写入Map集合并且跳转到regist.jsp。点击注册后输入框清空,因为是转发所以地址栏没变正常。


问题已解决。

1.开始时注册用户名为中文的时候认为是账号密码错误无法登陆。原因是问题分析错误:LoginServlet.java类中写的是一个响应跳转,而实际是需要请求转发到login.jsp中的,而非仅仅跳转过去。并不是由于中文用户注册引起的。

 2.注册失败时没有提示的总是回抛出一个在com.aloha.domain.UserForm中找不到msg属性的异常。最后发现是由于存放异常信息的Map集合的set/get方法忘记添加了,抛出的异常。

3.BeanUtils的populate方法是可以校验日期是否越界的。如果越界会通过Exception 的对象抛出这个异常,将这个异常同样以一个错误的回显形式请求转发给regist.jsp个面,可以对应提示生日的不合常理问题,如2月30日。


 下面是问题代码,修改后的代码在网盘中:

https://pan.baidu.com/s/1UKnt1Ch27rompcONI4NdSQ

JSP+Servlet+JavaBean的一个注册登录小项目_第1张图片

UserDao.java

package com.aloha.dao;

import com.aloha.domain.User;

/**
 * 这是用户数据库连接的接口
 * @author malaganguo
 *
 */
public interface UserDao {
	/**
	 * 添加用户信息
	 * @param user 用户对象
	 * @throws Exception 
	 */
	void addUser(User user) throws Exception;
	/**
	 * 在数据库中核对用户
	 * @param user
	 * @return
	 * @throws Exception
	 */
	User findUser(User user) throws Exception;
	/**
	 * 根据用户名查找用户是否存在
	 * @param name
	 * @return
	 */
	boolean findUserByName(String name);
}

UserDaoImpl.java

package com.aloha.dao.impl;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.text.SimpleDateFormat;

import javax.persistence.PrePersist;

import com.aloha.dao.UserDao;
import com.aloha.domain.User;
import com.aloha.utils.DBUtils;
/**
 * 这是数据库接口的实现类
 * @author malaganguo
 *
 */
public class UserDaoImpl implements UserDao{

	public void addUser(User user) throws Exception {
		Connection conn = null;
		PreparedStatement pstmt = null;
		try {
			conn = DBUtils.getConnection();
			pstmt = conn.prepareStatement("INSERT INTO users(username,PASSWORD,email,birthday) VALUES(?,?,?,?)");
			pstmt.setString(1, user.getUsername());
			pstmt.setString(2, user.getPassword());
			pstmt.setString(3, user.getEmail());
			SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
			String date = sdf.format(user.getBirthday());
			pstmt.setString(4, date);
			
			System.out.println(pstmt.executeUpdate());//返回的是几行受影响的值
			
		} catch (Exception e) {
			e.printStackTrace();
			throw new RuntimeException("添加失败!");
		}finally{
			DBUtils.closeAll(null, pstmt, conn);
		}
	}

	public User findUser(User user) throws Exception {
		
		Connection conn = null;
		PreparedStatement pstmt = null;
		ResultSet rs = null;
		User u = null;
		
		try {
			conn = DBUtils.getConnection();
			pstmt = conn.prepareStatement("SELECT * FROM users WHERE username=? AND PASSWORD=?");
			pstmt.setString(1, user.getUsername());
			pstmt.setString(2, user.getPassword());
			
			rs = pstmt.executeQuery();
			if(rs.next()){//如果返回的结果集中有值
				u =new User();
				u.setId(rs.getInt(1));
				u.setUsername(rs.getString(2));
				u.setPassword(rs.getString(3));
				u.setEmail(rs.getString(4));
				u.setBirthday(rs.getDate(5));
			}
		} catch (Exception e) {
			e.printStackTrace();
		}finally{
			DBUtils.closeAll(rs, pstmt, conn);
		}
		
		return u;
	}
	/**
	 * 如果当前用户名已存在,则返回true,否则返回false
	 */
	public boolean findUserByName(String name) {
		
		Connection conn = null;
		PreparedStatement pstmt = null;
		ResultSet rs = null;
		
		try {
			conn = DBUtils.getConnection();
			pstmt = conn.prepareStatement("SELECT * FROM users WHERE username=?");
			pstmt.setString(1, name);
			
			rs = pstmt.executeQuery();
			if(rs.next()){//如果这个名字存在
				return true;
			}
		} catch (SQLException e) {
			e.printStackTrace();
		}finally{
			DBUtils.closeAll(rs, pstmt, conn);
		}
		return false;
	}

}

User.java

package com.aloha.domain;

import java.io.Serializable;
import java.util.Date;

public class User implements Serializable{
	private int id;
	private String username;
	private String password;
	private String email;
	private Date birthday;

	public int getId() {
		return id;
	}
	public void setId(int id) {
		this.id = id;
	}
	public String getUsername() {
		return username;
	}
	public void setUsername(String username) {
		this.username = username;
	}
	public String getPassword() {
		return password;
	}
	public void setPassword(String password) {
		this.password = password;
	}
	public String getEmail() {
		return email;
	}
	public void setEmail(String email) {
		this.email = email;
	}
	public Date getBirthday() {
		return birthday;
	}
	public void setBirthday(Date birthday) {
		this.birthday = birthday;
	}
	
	
}

UserForm.java

package com.aloha.domain;

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.HashMap;
import java.util.Map;

public class UserForm {

	private int id;
	private String username;
	private String password;
	private String repassword;
	private String email;
	private String birthday;
	
	Map msg = new HashMap();
	/*用户名:必须输入,且3~8位的字母组成
密码:必须输入,3~8位的数组组成
确认密码:和密码保持一致
邮箱:必须输入,且要符合邮箱的格式
生日:必须输入,符合yyyy-MM-dd的格式
*/ /** * 这是一个规范输入的方法 * @return 符合规范返回true,不符合规范返回false */ public boolean validate(){ if("".equals(username)){ msg.put("username", "用户名不能为空!"); } if("".equals(password)){ msg.put("password", "密码不能为空!"); } if(!repassword.equals(password)){ msg.put("repassword", "两次密码不一致!"); } if("".equals(email)){ msg.put("email", "邮箱不能为空!"); }else if(!email.matches("\\b^['_a-z0-9-\\+]+(\\.['_a-z0-9-\\+]+)*@[a-z0-9-]+(\\.[a-z0-9-]+)*\\.([a-z]{2}|aero|arpa|asia|biz|com|coop|edu|gov|info|int|jobs|mil|mobi|museum|name|nato|net|org|pro|tel|travel|xxx)$\\b")){ msg.put("email", "邮箱格式不正确!"); } if("".equals(birthday)){ msg.put("birthday", "生日不能为空!"); }else { SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd"); try { sdf.parse(birthday); } catch (ParseException e) { msg.put("birthday", "生日格式不正确!"); } } //所有不符合规范的输入都将输入键入Map集合中。所以当完全符合规范的时候,msg是为null的。 return msg.isEmpty(); } public int getId() { return id; } public void setId(int id) { this.id = id; } public String getUsername() { return username; } public void setUsername(String username) { this.username = username; } public String getPassword() { return password; } public void setPassword(String password) { this.password = password; } public String getRepassword() { return repassword; } public void setRepassword(String repassword) { this.repassword = repassword; } public String getEmail() { return email; } public void setEmail(String email) { this.email = email; } public String getBirthday() { return birthday; } public void setBirthday(String birthday) { this.birthday = birthday; } }

UsersException.java

package com.aloha.exception;

public class UsersException extends Exception {

	/**
	 * 此类无参构造访问父类无参构造
	 */
	public UsersException() {
		super();
	}
	/**
	 * 以下都是子类有参构造访问父类
	 * @param message
	 * @param cause
	 */
	public UsersException(String message, Throwable cause) {
		super(message, cause);
	}

	public UsersException(String message) {
		super(message);
	}

	public UsersException(Throwable cause) {
		super(cause);
	}

	
}

UsersExistException.java

package com.aloha.exception;
/**
 * 这是用户退出异常类
 * @author malaganguo
 *
 */
public class UsersExistException extends Exception {

	public UsersExistException() {
		super();
	}

	public UsersExistException(String message, Throwable cause) {
		super(message, cause);
	}

	public UsersExistException(String message) {
		super(message);
	}

	public UsersExistException(Throwable cause) {
		super(cause);
	}

	
}

UserService.java

package com.aloha.service;

import com.aloha.domain.User;
import com.aloha.exception.UsersException;
import com.aloha.exception.UsersExistException;
/**
 * 这是根据用户需求写的接口
 * @author malaganguo
 *
 */
public interface UserService {
	/**
	 * 添加用户信息
	 * @param user
	 * @throws Exception
	 */
	void register(User user) throws Exception;
	/**
	 * 根据用户名和密码查找用户信息
	 * @param user
	 * @return
	 * @throws UsersException
	 */
	User login(User user) throws UsersException;
	
	public boolean findUserByName(String name) throws UsersExistException;
	
}

UserServiceImpl.java

package com.aloha.service.impl;

import com.aloha.dao.UserDao;
import com.aloha.dao.impl.UserDaoImpl;
import com.aloha.domain.User;
import com.aloha.exception.UsersExistException;
import com.aloha.service.UserService;

public class UserServiceImpl implements UserService {

	UserDao ud = new UserDaoImpl();
	
	public void register(User user) throws Exception {
		ud.addUser(user);
	}
	
	public User login(User user) {
		User u = null;
		try {
			u=ud.findUser(user);
		} catch (Exception e) {
			e.printStackTrace();
		}
		return u;
	}

	public boolean findUserByName(String name) throws UsersExistException {
		boolean b = ud.findUserByName(name);
		if(b){
			throw new UsersExistException("此用户已存在");
		}
		return b;
	}
	

}

DBUtils.java

package com.aloha.utils;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.ResourceBundle;

public class DBUtils {
	private static String driverClass;
	private static String url;
	private static String username; 
	private static String password;
	/**
	 * properties文件传值以及反射加载jdbc连接驱动
	 */
	static{
		ResourceBundle rb = ResourceBundle.getBundle("dbinfo");
		driverClass = rb.getString("driverClass");
		url = rb.getString("url");
		username = rb.getString("username");
		password = rb.getString("password");
		
		try {
			Class.forName(driverClass);
		} catch (ClassNotFoundException e) {
			e.printStackTrace();
		}
	}
	/**
	 * 这是简化后的创建获取连接的工具
	 * @return 获取到的连接对象
	 * @throws SQLException
	 */
	public static Connection getConnection() throws SQLException{
		return DriverManager.getConnection(url, username, password);
		
	}
	/**
	 * 这是关闭资源的工具
	 * @param rs 这是返回结果集对象
	 * @param stmt 这是执行SQL语句对象
	 * @param conn 这是获取连接对象
	 */
	public static void closeAll(ResultSet rs, Statement stmt, Connection conn){
		if(rs != null){
			try {
				rs.close();
			} catch (SQLException e) {
				e.printStackTrace();
			}
			rs = null;
		}
		if(stmt != null){
			try {
				stmt.close();
			} catch (SQLException e) {
				e.printStackTrace();
			}
			stmt = null;
		}
		if(conn != null){
			try {
				conn.close();
			} catch (SQLException e) {
				e.printStackTrace();
			}
			conn = null;
		}
	}
}

LoginOutServlet.java

package com.aloha.web.servlet;

import java.io.IOException;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class LoginOutServlet extends HttpServlet {

	public void doGet(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {
		request.getSession().invalidate();//注销:销毁session
		
		response.sendRedirect(request.getContextPath()+"/index.jsp");
		
		//这样写就不会跳转
//		response.getWriter().write("注销成功,2秒后跳转到主页");
//		response.setHeader("refresh", "2;url="+request.getContextPath()+"/index.jsp");
	}

	public void doPost(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {
		doGet(request, response);
	}

}

LoginServlet.java
 

package com.aloha.web.servlet;

import java.io.IOException;
import java.lang.reflect.InvocationTargetException;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.beanutils.BeanUtils;

import com.aloha.domain.User;
import com.aloha.service.UserService;
import com.aloha.service.impl.UserServiceImpl;

public class LoginServlet extends HttpServlet {

	public void doGet(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {
		//服务器和客户端共同约定使用UTF-8编码格式
		response.setContentType("text/html;charset=UTF-8");
		User u = new User();
		
		try {
			BeanUtils.populate(u, request.getParameterMap());
			UserService us = new UserServiceImpl();
			User user = us.login(u); //重新创建对象,如果在数据库中查找不到,那么u就为空了
			
			if(user != null){
				request.getSession().setAttribute("user", u);//如果登录成功就把user对象放到session对象中
				request.getRequestDispatcher("/index.jsp").forward(request, response);
			}else{
				response.getWriter().write("用户名或者密码错误,2秒后跳转到主页!");
//				response.sendRedirect(request.getContextPath()+"/login.jsp");//如果登录失败跳回到登录页面
				response.setHeader("refresh", "2;url="+request.getContextPath()+"/login.jsp");
			}
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

	public void doPost(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {
		doGet(request, response);
	}

}

RegServlet.java

package com.aloha.web.servlet;

import java.io.IOException;
import java.lang.reflect.InvocationTargetException;
import java.util.Date;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.beanutils.BeanUtils;
import org.apache.commons.beanutils.ConvertUtils;
import org.apache.commons.beanutils.locale.converters.DateLocaleConverter;

import com.aloha.domain.User;
import com.aloha.domain.UserForm;
import com.aloha.exception.UsersExistException;
import com.aloha.service.UserService;
import com.aloha.service.impl.UserServiceImpl;

public class RegServlet extends HttpServlet {

	public void doGet(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {
		request.setCharacterEncoding("UTF-8");
		response.setContentType("text/html;charset=UTF-8");
		//验证操作
		UserForm uf = new UserForm();
		try {
			BeanUtils.populate(uf, request.getParameterMap());
		} catch (Exception e1) {
			e1.printStackTrace();
		}
		if(!uf.validate()){//如果map集合不为空,说明格式有误
			request.setAttribute("uf", uf);
			System.out.println("map集合不为空");
			request.getRequestDispatcher("/regist.jsp").forward(request, response);
			System.out.println("已完成请求转发");
			return; //这个空的return语句可以让格式错误的表单不提交到服务器中,即下面的代码不执行了
		}
		//获取表单数据
		User u = new User();
		try {
			ConvertUtils.register(new DateLocaleConverter(), Date.class);//这里给提交的Date类型数据提供注册
			BeanUtils.populate(u, request.getParameterMap());//使用apache提供的Bean工具类获取表单数据,支持四类八种数据的转换,但是Date不包含在内,所以会报错
			
			//处理业务逻辑
			UserService us = new UserServiceImpl();
			us.findUserByName(u.getUsername());
			us.register(u);
			
		} catch (UsersExistException e) {
			request.setAttribute("error", "用户名已存在");
			request.getRequestDispatcher("/regist.jsp").forward(request, response);
		} catch (Exception e) {
			e.printStackTrace();
		}
		//分发转向
		response.getWriter().write("注册成功,1秒后进入主页。");
		response.setHeader("refresh", "1;url="+request.getContextPath()+"/index.jsp");

	}

	public void doPost(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {
		doGet(request, response);
	}

}

dbinfo.properties

driverClass=com.mysql.jdbc.Driver
url=jdbc:mysql://localhost:3306/jdbctest
username=root
password=root

web.xml



  
  
    RegServlet
    com.aloha.web.servlet.RegServlet
  
  
    LoginServlet
    com.aloha.web.servlet.LoginServlet
  
  
    LoginOutServlet
    com.aloha.web.servlet.LoginOutServlet
  






  
    RegServlet
    /servlet/regServlet
  
  
    LoginServlet
    /servlet/loginServlet
  
  
    LoginOutServlet
    /servlet/loginOutServlet
  
  
    index.jsp
  

index.jsp

<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
<%
String path = request.getContextPath();
String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";
%>
<%@taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>



  
    
    
    My JSP 'index.jsp' starting page
	
	
	    
	
	
	
  
  
  
	
	登录
	注册
  	
  	
  		欢迎你:${user.username } 注销
  	
  

login.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>




登录页面


	
用户名:
密码:

regist.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8" 
	pageEncoding="UTF-8"%>




Insert title here


	<%-- 这里使用了EL表达式来给html标签的value传递真实的值,在输入框后面打印校验信息。因为EL表达式具有很强的容错能力,即找不到值就不打印,所以很方便 --%>
	
用户名:${uf[msg][username] }${error }
密码:${uf[msg][password] }
确认密码:${uf[msg][repassword] }
邮箱:${uf[msg][email] }
生日:${uf[msg][birthday] }

 

你可能感兴趣的:(JSP+Servlet+JavaBean的一个注册登录小项目)