2023年新版JavaWeb图书管理系统完整版
项目地址:(包括项目代码、sql文件、功能文档、配置说明、博客地址)
可另付费4元让博主对该项目配置运行,包一次售后+问答,可走平台。
增值服务仅接受简单修改,不能改功能、删功能。不能写报告、论文、设计说明等。
闲鱼用户“程序zz”闲鱼公开实名上官霖泽(福建、2001年生)、闲鱼用户“juntangguo”,高价倒卖该我原创的项目,注意不要高价购买。
功能概述
JavaWeb图书管理系统完整版遵循MVC编程模式,基于Servlet、Bootstrap、MySQL等主要技术,实现了用户、管理员登录、用户注册、图书管理、图书类别管理、用户管理、借阅、归还书籍、借阅信息记录、退出登录等功能。项目涉及联表查询、图书-图书类别表拆分、session等技术。整个项目使用到14个JSP页面,功能相对完备,且功能操作方式符合逻辑、人性化。项目使用了Bootstrap前端ui框架,前端页面整洁美观。详情请参见“详细功能示例”部分。
数据库表展示
数据库共五张表,详情如下
![](https://i-blog.csdnimg.cn/blog_migrate/bed15585dae067d4896d92365553eaf6.png)
![](https://i-blog.csdnimg.cn/blog_migrate/d7046c4b559a0818afbf6719faee939e.png)
![](https://i-blog.csdnimg.cn/blog_migrate/11eaf9105dd9bbdb5e10ec8bca98dec9.png)
![](https://i-blog.csdnimg.cn/blog_migrate/0870939e904acd0833355a5c4a7a6822.png)
![](https://i-blog.csdnimg.cn/blog_migrate/8e0a1eac124e85cba79d02bf8bcdd0f7.png)
![](https://i-blog.csdnimg.cn/blog_migrate/ac59c42e89e9ee8b6d71f67f639c4b94.png)
![](https://i-blog.csdnimg.cn/blog_migrate/6208b4fec223643b9fac51180b49b7f7.png)
开发环境
Windwos、IDEA、MySQL、Tomcat、JDK1.8、JSP、JavaWeb、Bootstrap4
运行效果
![](https://i-blog.csdnimg.cn/blog_migrate/d56cb570faf65a2dad9a0e5e72416ae5.png)
![](https://i-blog.csdnimg.cn/blog_migrate/e6be1c59343436aa5676574c4d4b4359.png)
详细功能示例
用户管理
用户管理特指管理员对用户信息进行操作,包括用户添加、用户删除、用户信息修改、用户查询功能。其中用户添加为单独一个页面,其余三个页面则统一集成在用户管理页面。管理员可默认查询全部用户信息或通过用户名查询用户,这里作为查询条件的用户名无需和数据库中的用户名完全一致,只需其中的一部分即可,这里查询sql语句的where条件使用了like,即使用了模糊查询。
![](https://i-blog.csdnimg.cn/blog_migrate/fc7b60af3bdc3a086f5f65f8f19ce890.png)
![](https://i-blog.csdnimg.cn/blog_migrate/5e7d26fbe2cb290321e8442ee3514f59.png)
图书管理
图书管理即直接对数据库中图书表信息进行管理,图书作为整个管理系统的核心,在数据表的设计上仿照真实商业项目的要求,为图书表设置了较多的字段,虽然依旧不完备,但已经对一本书的基本信息作出了大致的描述。
图书管理功能和用户管理类似,增删改查四种功能,其中删改查被统一集成在同一页面,即图书管理页面,而增,即图书添加功能则被单独做成了一个页面,这种设计的方式是符合现实中的用户操作的逻辑和习惯的,同时这种设计方式还节省了开发的成本。一般而言,添加页面或者单位作为一个页面,或者作为管理页面中的一个默认被隐藏的元素,通过按钮来激活,而这里则选择了前种做法,这同样是符合逻辑和习惯的。
由下图可见,由于图书表字段较多,图书添加页面功能较其他表相对复杂,这表现在“描述”字段的文字内容较多与“是否被借阅”字段为布尔类型。但项目并没有为了节省开发成本而使用一贯的添加模板,而是根据图书表的具体情况,对图书表进行了具体分析,在添加模板的基础上,针对“描述”字段、“是否被借阅”字段在保证原有功能正常运行的基础之上,进行了单独的页面样式上的优化,这符合一般的现实中的项目的开发逻辑和习惯,大大方便了用户(广义)的使用。
![](https://i-blog.csdnimg.cn/blog_migrate/865556cfbf389bcd869e94aebeeefaae.png)
![](https://i-blog.csdnimg.cn/blog_migrate/9e30edd6437590a79de47b2c44392b3c.png)
登陆注册
登录注册功能作为进入系统后,用户(广义)体验到的首个功能,是能够决定用户的第一印象的,其无论是功能上还是交互、样式上都非常重要。
功能上,登录模块分为用户(狭义)登录和管理员登录,用户(狭义)所使用到的权限和管理员肯定是有所区别的,所以登录就需要区分是用户登录还是管理员登录,这在数据库中对应的就是用户表和管理员表。注册功能作为一项面向较多人数使用的功能,仅对用户(狭义)开放即可满足项目的需求,因为管理员人数较少,而无需为这些较少人数的管理员单独开发一个管理员注册功能,此功能和可通过直接操作数据库实现,或使用数据库中已有的管理员账户代替管理员注册功能。
样式上,虽然登录注册页面和系统内部功能页面有所不同,但同样使用了Bootstrap前端ui框架,因而也得以使得整个项目的所有页面都保持了一贯的统一的整洁美观的设计风格。
![](https://i-blog.csdnimg.cn/blog_migrate/892834561f620d58a94db9c4560e13b7.png)
![](https://i-blog.csdnimg.cn/blog_migrate/49c2a943be59e3f3ba1caacd4def1321.png)
用户登录后进入的页面:
![](https://i-blog.csdnimg.cn/blog_migrate/291718f380a2c1dc0b7c3e0036f4ba4d.png)
借阅记录页面
下面两张图分别为user这个用户名的用户(狭义)在自己以用户(狭义)身份登录管理系统时,和admin这个用户名的管理员在以管理员身份登录管理系统时查询借阅记录所查询出来的。这两个人查询出来的信息的不一致并不表明系统出现了问题,而是因为系统内部对于登录的账户有所判断,对于普通用户来讲,他无需也不能查询到其他用户的借阅记录,而是只需要查询他自己的记录,对于管理员用户而言,他则不可能针对自己,查询自己的借阅记录,因为管理员对于图书只有修改图书信息的功能,而没有借阅归还图书的功能,他也不需要这样的功能。而这样的条件则给出了普通用户和管理员的不同的规定性,也就是他们各自的特点。所以,将系统功能设计为普通用户只能查询自己的借阅记录,而管理员则可查询全部人的借阅记录,则是十分合理的了。
![](https://i-blog.csdnimg.cn/blog_migrate/f5a97b01941aed27be2eacec2b3d70b6.png)
![](https://i-blog.csdnimg.cn/blog_migrate/ce76e35db7cae18161f24dfa5e691217.png)
该项目中,代码的一般执行顺序为:entity -> vo -> utils -> dao -> service -> controller -> filter -> jsp
代码示例
BookServlet
package com.demo.main.controller;
import com.demo.main.entity.Book;
import com.demo.main.entity.Borrowing;
import com.demo.main.service.BookService;
import com.demo.main.service.BorrowingService;
import com.demo.main.utils.CommonUtil;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.sql.Timestamp;
import java.util.Date;
@WebServlet("/book")
public class BookServlet extends HttpServlet {
BookService bookService = new BookService();
BorrowingService borrowingService = new BorrowingService();
@Override
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doPost(request, response);
}
@Override
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
String method = request.getParameter("method");
switch (method) {
case "condition":
String author = request.getParameter("author");
String name = request.getParameter("name");
Book book = new Book();
book.setAuthor(author);
book.setName(name);
request.setAttribute("books", bookService.selectCondition(book));
request.getRequestDispatcher("/router?page=book").forward(request, response);
break;
case "borrow":
int id = Integer.parseInt(request.getParameter("id"));
// 借阅
if (bookService.selectOne(id).getIsBorrowed()) {
throw new RuntimeException("借阅失败");
}
bookService.bookBorrow(id, true);
// 插入借阅记录
Borrowing borrowing = new Borrowing();
borrowing.setUserId(CommonUtil.getUserId());
borrowing.setBookId(id);
borrowing.setType("borrowing");
borrowing.setDatetime(new Timestamp(new Date().getTime()));
borrowingService.insertOne(borrowing);
// 跳转
request.getRequestDispatcher("/router?page=book").forward(request, response);
break;
case "return":
int returnId = Integer.parseInt(request.getParameter("id"));
// 借阅
if (!bookService.selectOne(returnId).getIsBorrowed()) {
throw new RuntimeException("归还失败");
}
bookService.bookBorrow(returnId, false);
// 插入借阅记录
borrowing = new Borrowing();
borrowing.setUserId(CommonUtil.getUserId());
borrowing.setBookId(returnId);
borrowing.setType("returning");
borrowing.setDatetime(new Timestamp(new Date().getTime()));
borrowingService.insertOne(borrowing);
// 跳转
request.getRequestDispatcher("/router?page=book").forward(request, response);
break;
case "add":
book = new Book();
book.setName(request.getParameter("name"));
book.setAuthor(request.getParameter("author"));
book.setPublisher(request.getParameter("publisher"));
book.setIsbn(request.getParameter("isbn"));
book.setInfo(request.getParameter("info"));
book.setPricing(Double.parseDouble(request.getParameter("pricing")));
book.setIsBorrowed(request.getParameter("is_borrowed").equals("是"));
bookService.insertOne(book);
request.getRequestDispatcher("/router?page=admin_book_management").forward(request, response);
break;
case "delete":
id = Integer.parseInt(request.getParameter("id"));
bookService.deleteOne(id);
request.getRequestDispatcher("/router?page=admin_book_management").forward(request, response);
break;
case "update":
book = new Book();
book.setId(Integer.parseInt(request.getParameter("id")));
book.setName(request.getParameter("name"));
book.setAuthor(request.getParameter("author"));
book.setPublisher(request.getParameter("publisher"));
book.setIsbn(request.getParameter("isbn"));
book.setInfo(request.getParameter("info"));
book.setPricing(Double.parseDouble(request.getParameter("pricing")));
book.setIsBorrowed(request.getParameter("is_borrowed").equals("是"));
bookService.update(book);
request.getRequestDispatcher("/router?page=admin_book_management").forward(request, response);
break;
}
}
}
RouterServlet
package com.demo.main.controller;
import com.demo.main.entity.Book;
import com.demo.main.entity.BookType;
import com.demo.main.entity.User;
import com.demo.main.service.BookService;
import com.demo.main.service.BookTypeService;
import com.demo.main.service.BorrowingService;
import com.demo.main.service.UserService;
import com.demo.main.utils.CommonUtil;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
@WebServlet("/router")
public class RouterServlet extends HttpServlet {
BookService bookService = new BookService();
BorrowingService borrowingService = new BorrowingService();
UserService userService = new UserService();
BookTypeService bookTypeService = new BookTypeService();
@Override
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doGet(request, response);
}
@Override
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
String page = request.getParameter("page");
// 设置权限
request.setAttribute("permissions", CommonUtil.permissions.get(CommonUtil.getIdentity()));
switch (page) {
// /router?page=book
case "book":
if (request.getAttribute("books") == null) {
request.setAttribute("books", bookService.selectAll());
}
request.getRequestDispatcher("/WEB-INF/views/book.jsp").forward(request, response);
break;
case "borrowing":
request.setAttribute("borrowings", CommonUtil.getIdentity().equals("admin") ? borrowingService.selectVoAll() : borrowingService.selectVoByCurrentUser());
request.getRequestDispatcher("/WEB-INF/views/borrowing.jsp").forward(request, response);
break;
case "user_profile":
request.getRequestDispatcher("/WEB-INF/views/user_profile.jsp").forward(request, response);
break;
case "admin_user_management":
if (request.getAttribute("users") == null) {
request.setAttribute("users", userService.selectAll());
}
request.getRequestDispatcher("/WEB-INF/views/admin_user_management.jsp").forward(request, response);
break;
case "admin_add_user":
request.getRequestDispatcher("/WEB-INF/views/admin_add_user.jsp").forward(request, response);
break;
case "admin_user_update":
int id = Integer.parseInt(request.getParameter("id"));
User user = userService.selectOne(id);
request.setAttribute("user", user);
request.getRequestDispatcher("/WEB-INF/views/admin_user_update.jsp").forward(request, response);
break;
case "admin_book_type_management":
if (request.getAttribute("types") == null) {
request.setAttribute("types", bookTypeService.selectAll());
}
request.getRequestDispatcher("/WEB-INF/views/admin_book_type_management.jsp").forward(request, response);
break;
case "admin_book_type_update":
id = Integer.parseInt(request.getParameter("id"));
BookType bookType = bookTypeService.selectOne(id);
request.setAttribute("type", bookType);
request.getRequestDispatcher("/WEB-INF/views/admin_book_type_update.jsp").forward(request, response);
case "admin_book_type_insert":
request.getRequestDispatcher("/WEB-INF/views/admin_add_book_type.jsp").forward(request, response);
break;
case "admin_book_management":
if (request.getAttribute("books") == null) {
request.setAttribute("books", bookService.selectAll());
}
request.getRequestDispatcher("/WEB-INF/views/admin_book_management.jsp").forward(request, response);
break;
case "admin_add_book":
request.getRequestDispatcher("/WEB-INF/views/admin_add_book.jsp").forward(request, response);
break;
case "admin_book_update":
id = Integer.parseInt(request.getParameter("id"));
Book book = bookService.selectOne(id);
request.setAttribute("book", book);
request.getRequestDispatcher("/WEB-INF/views/admin_book_update.jsp").forward(request, response);
break;
}
}
}
当然,除上述详细介绍的功能之外,其他功能也同样具有非常丰富的内容,这些功能之间互相配合,从而组成了整个较为完备的图书管理系统。虽然仅仅作为JavaWeb项目不可能像正式的Spring项目那样更具有复杂性和现实性,但是该项目对于Java初学者却还是能够起到很好的借鉴、参考和帮助作用的。项目中对于JavaWeb相关对象的熟练使用可以帮助初学者较快掌握JavaWeb这一技术,快速通过这一环节,Java技术路线以后还有很长,且其重点,并不在此JavaWeb环节,初学者无需在此耗费过多精力。