SMBMS(超市订单管理系统)
数据库:
项目如何搭建?
考虑使用不使用Maven?用,则添加依赖,否则,导入jar包
项目搭建(准备工作)
- 搭建一个maven web项目
- 配置Tomcat
- 测试项目是否能够跑起来
- 导入项目需要的jar包
- 创建项目包架构
-
编写实体类
ORM映射:表-类映射
-
编写基础公共类
-
数据库配置文件
driver=com.mysql.jdbc.Driver url=jdbc:mysql://localhost:3306?useUnicode=true&characterEncoding=utf-8 username=root password=123456
-
编写数据库的公共类
package com.edgar.dao; import com.mysql.jdbc.Driver; import java.io.IOException; import java.io.InputStream; import java.sql.*; import java.util.Properties; public class BaseDao { private static String driver; private static String url; private static String username; private static String password; //静态代码块,类加载的时候就初始化 static { //通过类加载器加载对应的资源 InputStream in = BaseDao.class.getResourceAsStream("/db.properties"); Properties prop = new Properties(); try { prop.load(in); } catch (IOException e) { e.printStackTrace(); } driver=prop.getProperty("driver"); url=prop.getProperty("url"); username=prop.getProperty("username"); password=prop.getProperty("password"); } //获取数据库的链接 public static Connection getConnection() { Connection connection = null; try { Class.forName(driver); connection = DriverManager.getConnection(url, username, password); } catch (Exception e) { e.printStackTrace(); } return connection; } //编写查询公共方法 public static ResultSet execute(Connection connection,String sql,Object[] params,ResultSet resultSet, PreparedStatement preparedStatement) throws SQLException { preparedStatement = connection.prepareStatement(sql); //setObject占位符从1开始,当时我们的数组从0开始 for (int i = 0; i < params.length; i++) { preparedStatement.setObject(i+1,params[i]); } resultSet = preparedStatement.executeQuery(); return resultSet; } //编写增删改公共方法 public static int execute(Connection connection,String sql,Object[] params,PreparedStatement preparedStatement) throws SQLException { preparedStatement = connection.prepareStatement(sql); //setObject占位符从1开始,当时我们的数组从0开始 for (int i = 0; i < params.length; i++) { preparedStatement.setObject(i+1,params[i]); } int updateRows = preparedStatement.executeUpdate(); return updateRows; } //释放资源 public static boolean closeResource(Connection connection,PreparedStatement preparedStatement,ResultSet resultSet){ boolean flag=true; if(resultSet!=null){ try { resultSet.close(); //GC回收 resultSet=null; } catch (SQLException e) { flag=false; e.printStackTrace(); } } if(preparedStatement!=null){ try { preparedStatement.close(); //GC回收 preparedStatement=null; } catch (SQLException e) { flag=false; e.printStackTrace(); } } if(connection!=null){ try { connection.close(); //GC回收 connection=null; } catch (SQLException e) { flag=false; e.printStackTrace(); } } return flag; } }
-
编写字符编码过滤器
-
-
导入静态资源
登录功能实现
思路:
-
编写前端
-
设置首页 web.xml配置
<!--设置欢迎页面--> <welcome-file-list> <welcome-file>login.jsp</welcome-file> </welcome-file-list>
-
编写dao层登录用户的接口
package com.edgar.dao.user; import com.edgar.pojo.User; import java.sql.Connection; import java.sql.SQLException; public interface UserDao { //得到登录用户 User getLoginUser(Connection connection,String userCode,String userPassword) throws SQLException; }
-
编写dao层的实现类
package com.edgar.dao.user; import com.edgar.dao.BaseDao; import com.edgar.pojo.User; import java.sql.Connection; import java.sql.PreparedStatement; import java.sql.ResultSet; import java.sql.SQLException; public class UserDaoImpl implements UserDao { public User getLoginUser(Connection connection, String userCode, String userPassword) throws SQLException { PreparedStatement pstm = null; ResultSet rs = null; User user = null; if (connection != null) { String sql = "select * from smbms_user where userCode=? and userPassword=?"; Object[] params = {userCode, userPassword}; rs = BaseDao.execute(connection, pstm, rs, sql, params); if (rs.next()) { user = new User(); user.setId(rs.getInt("id")); user.setUserCode(rs.getString("userCode")); user.setUserName(rs.getString("userName")); user.setUserPassword(rs.getString("userPassword")); user.setGender(rs.getInt("gender")); user.setBirthday(rs.getDate("birthday")); user.setPhone(rs.getString("phone")); user.setAddress(rs.getString("address")); user.setUserRole(rs.getInt("userRole")); user.setCreateBy(rs.getInt("createdBy")); user.setCreationDate(rs.getTimestamp("creationDate")); user.setModifyBy(rs.getInt("modifyBy")); user.setModifyDate(rs.getDate("modifyDate")); } BaseDao.closeResource(null, pstm, rs); } return user; } }
-
业务层接口
package com.edgar.service.user; import com.edgar.pojo.User; public interface UserService { //用户登录 User login(String userCode, String password); }
-
业务层实现
package com.edgar.service.user; import com.edgar.dao.BaseDao; import com.edgar.dao.user.UserDao; import com.edgar.dao.user.UserDaoImpl; import com.edgar.pojo.User; import org.junit.Test; import java.sql.Connection; import java.sql.SQLException; public class UserServiceImpl implements UserService { //业务层都会调用Dao层,所以我们要引入Dao层; private UserDao userDao; public UserServiceImpl() { userDao = new UserDaoImpl(); } public User login(String userCode, String password) { Connection connection = null; User user = null; try { connection = BaseDao.getConnection(); //通过业务层调用对应的具体的数据库操作 user = userDao.getLoginUser(connection, userCode, password); } catch (SQLException e) { e.printStackTrace(); } finally { BaseDao.closeResource(connection, null, null); } return user; } @Test public void test() { UserService userService = new UserServiceImpl(); User admin = userService.login("admin", "123456"); System.out.println(admin.getUserPassword()); } }
-
编写Servlet
package com.edgar.servlet.user; import com.edgar.pojo.User; import com.edgar.service.user.UserService; import com.edgar.service.user.UserServiceImpl; import com.edgar.util.Constants; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import java.io.IOException; public class LoginServlet extends HttpServlet { //Servlet:控制层,调用业务层代码 @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { System.out.println("LoginServlet--start...."); //获取用户名和密码 String userCode = req.getParameter("userCode"); String userPassword = req.getParameter("userPassword"); //和数据库中的密码进行对比,调用业务层 UserService userService = new UserServiceImpl(); User user = userService.login(userCode, userPassword); //这里已经把登录的人查出来了 if (user != null) { //查有此人,可以登录 //将用户的信息放到Session中 req.getSession().setAttribute(Constants.USER_SESSION, user); //跳转到主页 resp.sendRedirect("jsp/frame.jsp"); } else {//查无此人,无法登录 //转发回登陆页面,顺带提示它,用户名或者密码错误 req.setAttribute("error", "用户名或者密码不正确"); req.getRequestDispatcher("/login.jsp").forward(req, resp); } } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { doGet(req, resp); } }
-
注册Servlet
<servlet> <servlet-name>LoginServlet</servlet-name> <servlet-class>com.edgar.servlet.user.LoginServlet</servlet-class> </servlet> <servlet-mapping> <servlet-name>LoginServlet</servlet-name> <url-pattern>/login.do</url-pattern> </servlet-mapping>
-
测试访问,确保以上功能成功!
登录功能优化(Filter)
注销功能
思路:移除session,返回登陆页面
package com.edgar.servlet.user;
import com.edgar.util.Constants;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
public class LogoutServlet extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
//用处用户的Constants.USER_SESSION
req.getSession().removeAttribute(Constants.USER_SESSION);
resp.sendRedirect(req.getContextPath() + "/login.jsp"); //返回登陆页面
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
doGet(req, resp);
}
}
注册到web.xml
<servlet>
<servlet-name>LogoutServlet</servlet-name>
<servlet-class>com.edgar.servlet.user.LogoutServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>LogoutServlet</servlet-name>
<url-pattern>/logout.do</url-pattern>
</servlet-mapping>
登录拦截优化
编写一个拦截器,并注册到web.xml
package com.edgar.filter;
import com.edgar.pojo.User;
import com.edgar.util.Constants;
import javax.servlet.*;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
public class SysFilter implements Filter {
public void init(FilterConfig filterConfig) throws ServletException {
}
public void doFilter(ServletRequest req, ServletResponse resp, FilterChain chain) throws IOException, ServletException {
HttpServletRequest request = (HttpServletRequest) req;
HttpServletResponse response = (HttpServletResponse) resp;
//过滤器,从Session中获取用户
User user = (User) request.getSession().getAttribute(Constants.USER_SESSION);
if (user == null) {//已经被注销了,或者没登陆
response.sendRedirect(request.getContextPath() + "/error.jsp");
} else {
chain.doFilter(req, resp);
}
}
public void destroy() {
}
}
<!--用户登录过滤器-->
<filter>
<filter-name>SysFilter</filter-name>
<filter-class>com.edgar.filter.SysFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>SysFilter</filter-name>
<url-pattern>/jsp/*</url-pattern>
</filter-mapping>
密码修改
思路:
-
导入前端素材
<li><a href="${pageContext.request.contextPath }/pwdmodify.jsp">密码修改</a></li>
-
写项目,建议从底层往上写
dao-->service-->servlet
-
UserDao接口
//修改当前用户密码 int updatePwd(Connection connection,int id,String passWord) throws SQLException;
-
UserDao实现类
//修改当前用户密码 public int updatePwd(Connection connection, int id, String passWord) throws SQLException { PreparedStatement pstm = null; int execute=0; if (connection != null) { String sql = "update smbms_user set userPassword= ? where id= ? "; Object[] params = {passWord, id}; execute = BaseDao.execute(connection, pstm, sql, params); BaseDao.closeResource(null, pstm, null); } return execute; }
-
UserService层
//修改用户ID修改密码 boolean updatePwd(int id, String passWord);
-
UserService实现类
public boolean updatePwd(int id, String passWord) { Connection connection = null; boolean flag = false; try { connection = BaseDao.getConnection(); int i = userDao.updatePwd(connection, id, passWord); if (i > 0) { flag = true; } } catch (SQLException e) { e.printStackTrace(); } finally { BaseDao.closeResource(connection, null, null); } return flag; }
-
编写Servlet,记得实现复用,需要提取出方法!
package com.edgar.servlet.user; import com.alibaba.fastjson.JSONObject; import com.edgar.pojo.User; import com.edgar.service.user.UserService; import com.edgar.service.user.UserServiceImpl; import com.edgar.util.Constants; import com.mysql.jdbc.StringUtils; import javax.servlet.ServletException; 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.HashMap; //实现Servlet复用 public class UserServlet extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { String method = req.getParameter("method"); if ("updatePwd".equals(method)) { // 修改密码 this.updatePwd(req, resp); } else if ("checkOldPwd".equals(method)) { //校验旧密码 this.checkOldPwd(req, resp); } } public void updatePwd(HttpServletRequest req, HttpServletResponse resp) { //从Session里面拿ID Object o = req.getSession().getAttribute(Constants.USER_SESSION); String newpassword = req.getParameter("newpassword"); boolean flag = false; if (o != null && !StringUtils.isNullOrEmpty(newpassword)) { UserService userService = new UserServiceImpl(); flag = userService.updatePwd(((User) o).getId(), newpassword); if (flag) { req.setAttribute("message", "修改密码成功,请退出,使用新密码登录"); //密码修改成功,移除当前Session req.getSession().removeAttribute(Constants.USER_SESSION); } else { req.setAttribute("message", "密码修改失败"); } } else { req.setAttribute("message", "新密码有问题"); } try { req.getRequestDispatcher("/jsp/pwdmodify.jsp").forward(req, resp); } catch (ServletException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } } //校验旧密码,session中有旧密码 public void checkOldPwd(HttpServletRequest req, HttpServletResponse resp) { String oldPwd = req.getParameter("oldPassword"); Object o = req.getSession().getAttribute(Constants.USER_SESSION); //万能的Map:结果集 HashMap<String, Object> resultMap = new HashMap<String, Object>(); if (o == null) { // session失效,session过期了 resultMap.put("result", "sessionerror"); } else if (StringUtils.isNullOrEmpty(oldPwd)) { // 输入的密码为空 resultMap.put("result", "error"); } else { String userPassword = ((User) o).getUserPassword(); //session中的用户密码 if (oldPwd.equals(userPassword)) { resultMap.put("result", "true"); } else { resultMap.put("result", "false"); } } try { resp.setContentType("application/json"); PrintWriter writer = resp.getWriter(); // JSONObject 阿里巴巴的JSON工具类,转换格式 String jsonString = JSONObject.toJSONString(resultMap); writer.write(jsonString); writer.flush(); writer.close(); } catch (IOException e) { e.printStackTrace(); } } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { doGet(req, resp); } }
-
Servlet注册到web.xml
<servlet> <servlet-name>UserServlet</servlet-name> <servlet-class>com.edgar.servlet.user.UserServlet</servlet-class> </servlet> <servlet-mapping> <servlet-name>UserServlet</servlet-name> <url-pattern>/jsp/user.do</url-pattern> </servlet-mapping>
-
测试访问
密码修改优化(Ajax)
使用Ajax校验旧密码
前端代码:
oldpassword.on("blur",function(){
$.ajax({
type:"GET",
url:path+"/jsp/user.do",
data:{method:"checkOldPwd",oldPassword:oldpassword.val()},
dataType:"json",
success:function(data){
if(data.result == "true"){//旧密码正确
validateTip(oldpassword.next(),{"color":"green"},imgYes,true);
}else if(data.result == "false"){//旧密码输入不正确
validateTip(oldpassword.next(),{"color":"red"},imgNo + " 原密码输入不正确",false);
}else if(data.result == "sessionerror"){//当前用户session过期,请重新登录
validateTip(oldpassword.next(),{"color":"red"},imgNo + " 当前用户session过期,请重新登录",false);
}else if(data.result == "error"){//旧密码输入为空
validateTip(oldpassword.next(),{"color":"red"},imgNo + " 请输入旧密码",false);
}
},
error:function(data){
//请求出错
validateTip(oldpassword.next(),{"color":"red"},imgNo + " 请求错误",false);
}
});
后台代码:
//校验旧密码,session中有旧密码
public void checkOldPwd(HttpServletRequest req, HttpServletResponse resp) {
String oldPwd = req.getParameter("oldPassword");
Object o = req.getSession().getAttribute(Constants.USER_SESSION);
//万能的Map:结果集
HashMap<String, Object> resultMap = new HashMap<String, Object>();
if (o == null) { // session失效,session过期了
resultMap.put("result", "sessionerror");
} else if (StringUtils.isNullOrEmpty(oldPwd)) { // 输入的密码为空
resultMap.put("result", "error");
} else {
String userPassword = ((User) o).getUserPassword(); //session中的用户密码
if (oldPwd.equals(userPassword)) {
resultMap.put("result", "true");
} else {
resultMap.put("result", "false");
}
}
try {
resp.setContentType("application/json");
PrintWriter writer = resp.getWriter();
// JSONObject 阿里巴巴的JSON工具类,转换格式
String jsonString = JSONObject.toJSONString(resultMap);
writer.write(jsonString);
writer.flush();
writer.close();
} catch (IOException e) {
e.printStackTrace();
}
}
用户管理实现(查询分页)
思路:
-
导入分页的工具类
-
用户列表页面导入
userlist.jsp
1、获取用户数量
-
UserDao
//查询用户总数 int getUserCount(Connection connection,String userName,int userRole) throws SQLException;
-
UserDaoImpl
//查询用户总数 public int getUserCount(Connection connection, String userName, int userRole) throws SQLException { PreparedStatement pstm = null; ResultSet rs = null; int count = 0; if (connection != null) { ArrayList<Object> list = new ArrayList<Object>();//存放我们的参数 StringBuffer stringBuffer = new StringBuffer(); stringBuffer.append("select count(1) as count from smbms_user u,smbms_role r where u.userRole=r.id"); if (userName != null) { stringBuffer.append(" and userName like ?"); list.add("%" + userName + "%");//index=0 } if (userRole > 0) { stringBuffer.append(" and userRole = ?"); list.add(userRole);//index=1 } //怎么把list转为数组? list.toArray() rs = BaseDao.execute(connection, pstm, rs, stringBuffer.toString(), list.toArray()); if (rs.next()) { count = rs.getInt("count");//从结果集中获取最终的数量 } BaseDao.closeResource(null, pstm, rs); } return count; }
-
UserService
//查询用户总 int getUserCount(String userName,int userRole);
-
UserServiceImpl
public int getUserCount(String userName, int userRole) { Connection conn = null; int count = 0; try { conn = BaseDao.getConnection(); count = userDao.getUserCount(conn, userName, userRole); } catch (SQLException e) { e.printStackTrace(); } finally { BaseDao.closeResource(conn, null, null); } return count; }
2、获取用户列表
-
UserDao
//查询用户信息 List<User> getUserList(Connection connection,String userName,int userRole,int currentPageNo,int pageSize) throws SQLException;
-
UserDaoImpl
public List<User> getUserList(Connection connection, String userName, int userRole, int currentPageNo, int pageSize) throws SQLException { PreparedStatement pstm = null; ResultSet rs = null; User user = null; List<User> userList = new ArrayList<User>(); if (connection != null) { ArrayList<Object> list = new ArrayList<Object>();//存放我们的参数 StringBuffer sql = new StringBuffer(); sql.append("select * from smbms_user u,smbms_role r where u.userRole=r.id"); if (userName != null) { sql.append(" and userName like ?"); list.add("%" + userName + "%");//index=0 } if (userRole > 0) { sql.append(" and userRole = ?"); list.add(userRole);//index=1 } sql.append(" order by creationDate DESC limit ?,?"); int startIndex = (currentPageNo - 1) * pageSize;//起始位置 list.add(startIndex); list.add(pageSize); //怎么把list转为数组? list.toArray() rs = BaseDao.execute(connection, pstm, rs, sql.toString(), list.toArray()); while (rs.next()) { user = new User(); user.setId(rs.getInt("id")); user.setUserCode(rs.getString("userCode")); user.setUserName(rs.getString("userName")); user.setUserPassword(rs.getString("userPassword")); user.setGender(rs.getInt("gender")); user.setBirthday(rs.getDate("birthday")); user.setPhone(rs.getString("phone")); user.setAddress(rs.getString("address")); user.setUserRole(rs.getInt("userRole")); user.setCreateBy(rs.getInt("createdBy")); user.setCreationDate(rs.getTimestamp("creationDate")); user.setModifyBy(rs.getInt("modifyBy")); user.setModifyDate(rs.getDate("modifyDate")); userList.add(user); } BaseDao.closeResource(null, pstm, rs); } return userList; }
-
UserService
//查询用户信息 List<User> getUserList(Connection connection, String userName, int userRole, int currentPageNo, int pageSize);
-
UserServiceImpl
//查询用户信息 public List<User> getUserList(Connection connection, String userName, int userRole, int currentPageNo, int pageSize) { Connection conn = null; List<User> userList = null; try { conn = BaseDao.getConnection(); userList = userDao.getUserList(conn, userName, userRole, currentPageNo, pageSize); } catch (SQLException e) { e.printStackTrace(); } finally { BaseDao.closeResource(conn, null, null); } return userList; }
3、获取角色操作
为了我们的职责统一,可以把角色的操作单独放在一个包中,和POJO类对应
-
RoleDao
//获取角色列表 List<Role> getRoleList(Connection connection) throws SQLException;
-
RoleDaoImpl
//获取角色列表 public List<Role> getRoleList(Connection connection) throws SQLException { PreparedStatement pstm = null; ResultSet rs = null; List<Role> roleList = new ArrayList<Role>(); if (connection != null) { String sql = "select * from smbms_role"; Object[] params = {}; rs = BaseDao.execute(connection, pstm, rs, sql, params); while (rs.next()) { Role role = new Role(); role.setId(rs.getInt("id")); role.setRoleCode(rs.getString("roleCode")); role.setRoleName(rs.getString("roleName")); roleList.add(role); } BaseDao.closeResource(null, pstm, rs); } return roleList; }
-
RoleService
//获取角色列表 List<Role> getRoleList();
-
RoleServiceImpl
//获取角色列表 public List<Role> getRoleList() { Connection conn = null; List<Role> roleList = null; try { conn = BaseDao.getConnection(); roleList = roleDao.getRoleList(conn); } catch (SQLException e) { e.printStackTrace(); } finally { BaseDao.closeResource(conn, null, null); } return roleList; }
4、用户显示的Servlet
-
获取用户前端的数据
-
判断参数的值的合理性,保证代码的健壮
-
为了实现分页,需要计算出当前页和总页面,页面大小
-
查询用户数据、角色数据、总页数、当前页
-
携带数据,返回前端
//重点 难点 public void query(HttpServletRequest req, HttpServletResponse resp) { //从前端获取数据 String queryUserName = req.getParameter("queryname"); String temp = req.getParameter("queryUserRole"); String pageIndex = req.getParameter("pageIndex"); int queryUserRole = 0; int pageSize = 5; int currentPageNo = 1; if (queryUserName == null) { queryUserName = ""; } if (temp != null && !temp.equals("")) { queryUserRole = Integer.parseInt(temp); } if (pageIndex != null) { currentPageNo = Integer.parseInt(pageIndex); } UserService userService = new UserServiceImpl(); //获取用户的总数 int totalCount = userService.getUserCount(queryUserName, queryUserRole); //总页数支持 PageSupport pageSupport = new PageSupport(); pageSupport.setPageSize(pageSize); pageSupport.setCurrentPageNo(currentPageNo); pageSupport.setTotalCount(totalCount); int totalPageCount = pageSupport.getTotalPageCount();// 总页数 //控制首页和尾页 if (currentPageNo < 1) { currentPageNo = 1; // 当前页比1小时,值为1 } else if (currentPageNo > totalPageCount) { currentPageNo = totalPageCount;//当前页大于总页数,值为总页数 } //获取用户列表 List<User> userList = userService.getUserList(queryUserName, queryUserRole, currentPageNo, pageSize); req.setAttribute("userList", userList); //获取角色列表 RoleService roleService = new RoleServiceImpl(); List<Role> roleList = roleService.getRoleList(); req.setAttribute("roleList", roleList); req.setAttribute("totalCount", totalCount); req.setAttribute("currentPageNo", currentPageNo); req.setAttribute("totalPageCount", totalPageCount); req.setAttribute("queryUserName", queryUserName); req.setAttribute("queryUserRole", queryUserRole); try { req.getRequestDispatcher("/jsp/userlist.jsp").forward(req, resp); } catch (ServletException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } }