32 KiB
32 KiB
资产管理系统 — 整体代码设计思路
一、分层设计思路
1.1 四层职责划分
| 层次 | 包路径 | 职责 | 核心原则 |
|---|---|---|---|
| 表示层 | view/ |
用户交互、数据展示、事件响应 | 只做展示与交互,不包含业务逻辑 |
| 业务逻辑层 | service/ |
业务规则校验、流程控制、事务协调 | 不含SQL,不包含UI逻辑 |
| 数据访问层 | dao/ |
数据库CRUD操作、SQL封装 | 只做数据存取,不含业务判断 |
| 实体层 | entity/ |
数据载体,与表结构对应 | 纯POJO,无业务逻辑 |
1.2 层间调用规则
view ──调用──▶ service ──调用──▶ dao ──操作──▶ MySQL
│ │ │
│ ├── util ├── util/DBUtil
│ ├── entity ├── entity
│ └── exception └── exception
│
├── util/ValidatorUtil(表单即时校验)
└── entity(界面数据绑定)
严格规则:
- view 只能调用 service,禁止直接调用 dao
- service 只调用 dao 和 util,禁止包含 Swing 组件引用
- dao 只操作数据库,禁止包含业务判断逻辑
- entity 被所有层共享,禁止依赖其他任何层
1.3 数据流转示例(资产录入)
用户填写表单 → AssetDialog收集输入 → 构造Asset对象
→ ValidatorUtil校验字段 → AssetService.addAsset(asset)
→ 校验资产编号唯一性 → AssetDAO.insert(asset)
→ DBUtil获取连接 → PreparedStatement执行SQL → 释放资源
→ 返回操作结果
→ 界面刷新表格 + 提示成功/失败
二、核心类设计
2.1 实体类(entity)
设计原则: 一个实体对应一张表,属性名=字段名(驼峰转换),提供全参构造+getter/setter+toString。
User.java
// 字段:id, username, password, realName, role, status, createTime, updateTime
// 角色:role取值 "admin" / "user"
// 状态:status取值 1(启用) / 0(禁用)
// 构造:注册用构造(不含id/time)、查询用全参构造
Asset.java
// 字段:id, assetCode, assetName, categoryId, status, value, purchaseDate, location, description, createTime, updateTime
// 状态:status取值 "available" / "borrowed" / "disposed"
// 关联:categoryId关联Category,界面展示时需关联查询分类名称
Category.java
// 字段:id, categoryCode, categoryName, description, createTime, updateTime
// 用途:资产分类,如"办公设备"、"电子设备"、"家具"等
Borrow.java
// 字段:id, assetId, userId, borrowDate, expectedReturnDate, actualReturnDate, reason, status, approverId, approveTime, approveRemark, createTime, updateTime
// 状态流转:pending → approved / rejected,approved → returned / overdue
Disposal.java
// 字段:id, assetId, userId, reason, status, approverId, approveTime, approveRemark, disposalDate, createTime, updateTime
// 状态流转:pending → approved / rejected
2.2 DAO类(dao)
BaseDAO.java — 通用CRUD模板
// 设计思路:抽取所有DAO共用的增删改查操作为模板方法
//
// 核心方法:
// int update(String sql, Object... params) — 通用增删改
// <T> T queryOne(String sql, RowMapper<T> mapper, Object... params) — 查询单条
// <T> List<T> queryList(String sql, RowMapper<T> mapper, Object... params) — 查询列表
// long count(String sql, Object... params) — 统计数量
//
// RowMapper接口:将ResultSet行映射为实体对象(函数式接口)
// @FunctionalInterface
// interface RowMapper<T> { T mapRow(ResultSet rs) throws SQLException; }
//
// 资源管理:所有方法内部保证Connection/PreparedStatement/ResultSet正确关闭
// 事务支持:提供getConnection()供Service层手动管理事务
UserDAO.java
// 继承BaseDAO,实现用户特有查询
//
// 核心方法:
// User findByUsername(String username) — 按用户名查询(登录验证)
// User findById(int id) — 按ID查询(关联查询用)
// int insert(User user) — 新增用户
// int updatePassword(int id, String newPassword) — 修改密码
// int updateRole(int id, String role) — 修改角色
// int updateStatus(int id, int status) — 修改状态
// List<User> findAll() — 查询所有用户
// long countByUsername(String username) — 用户名唯一性校验
AssetDAO.java
// 继承BaseDAO,实现资产特有查询
//
// 核心方法:
// int insert(Asset asset) — 新增资产
// int update(Asset asset) — 修改资产
// int deleteById(int id) — 删除资产
// Asset findById(int id) — 按ID查询
// Asset findByAssetCode(String assetCode) — 按编号查询(唯一性校验)
// List<Asset> findAll() — 查询所有
// List<Asset> findByCondition(String name, Integer categoryId, String status, String location)
// — 多条件组合查询
// int updateStatus(int id, String status) — 更新资产状态
// long countByCategoryId(int categoryId) — 统计分类下资产数量(删除前检查)
CategoryDAO.java
// 继承BaseDAO,实现分类特有查询
//
// 核心方法:
// int insert(Category category) — 新增分类
// int update(Category category) — 修改分类
// int deleteById(int id) — 删除分类
// Category findById(int id) — 按ID查询
// List<Category> findAll() — 查询所有
// long countByCategoryCode(String code) — 编号唯一性校验
BorrowDAO.java
// 继承BaseDAO,实现借用特有查询
//
// 核心方法:
// int insert(Borrow borrow) — 新增借用记录
// int updateStatus(int id, String status, Integer approverId, String remark)
// — 更新借用状态(审批)
// int updateReturn(int id, LocalDateTime returnDate) — 登记归还
// Borrow findById(int id) — 按ID查询
// List<Borrow> findByUserId(int userId) — 按借用人查询
// List<Borrow> findByAssetId(int assetId) — 按资产查询
// List<Borrow> findByStatus(String status) — 按状态查询
// List<Borrow> findAll() — 查询所有
// List<Borrow> findOverdue() — 查询逾期未还
DisposalDAO.java
// 继承BaseDAO,实现报废特有查询
//
// 核心方法:
// int insert(Disposal disposal) — 新增报废记录
// int updateStatus(int id, String status, Integer approverId, String remark)
// — 更新报废状态(审批)
// Disposal findById(int id) — 按ID查询
// List<Disposal> findByUserId(int userId) — 按申请人查询
// List<Disposal> findByAssetId(int assetId) — 按资产查询
// List<Disposal> findByStatus(String status) — 按状态查询
// List<Disposal> findAll() — 查询所有
2.3 Service类(service)
UserService.java
// 用户业务逻辑
//
// 核心方法:
// User login(String username, String password)
// → 校验用户名非空、密码非空
// → MD5加密密码后与数据库比对
// → 检查账户状态(是否禁用)
// → 失败抛出BusinessException
//
// void register(String username, String password, String realName)
// → 校验用户名长度(3-20)、密码长度(6-20)、真实姓名非空
// → 校验用户名唯一性
// → MD5加密密码
// → 调用DAO插入,默认角色user、状态1
//
// void changePassword(int userId, String oldPwd, String newPwd)
// → 验证旧密码正确性
// → 校验新密码格式
// → MD5加密新密码后更新
//
// List<User> getAllUsers()
// → 调用DAO查询所有用户
//
// void updateUserRole(int userId, String role)
// → 校验角色值合法性(admin/user)
// → 调用DAO更新角色
//
// void updateUserStatus(int userId, int status)
// → 校验状态值合法性(0/1)
// → 调用DAO更新状态
AssetService.java
// 资产业务逻辑
//
// 核心方法:
// void addAsset(Asset asset)
// → 校验必填项(编号、名称、分类、价值、购入日期)
// → 校验资产编号唯一性
// → 校验价值为正数
// → 校验购入日期不晚于今天
// → 调用DAO插入
//
// void updateAsset(Asset asset)
// → 校验必填项
// → 调用DAO更新
//
// void deleteAsset(int assetId)
// → 检查资产状态,已被借用的不可删除
// → 调用DAO删除
//
// Asset getAssetById(int id)
// → 调用DAO查询
//
// List<Asset> getAllAssets()
// → 调用DAO查询所有
//
// List<Asset> searchAssets(String name, Integer categoryId, String status, String location)
// → 调用DAO多条件组合查询
// → 任意条件可为空(null表示不筛选)
//
// void updateAssetStatus(int assetId, String status)
// → 校验状态值合法性
// → 调用DAO更新状态
CategoryService.java
// 分类业务逻辑
//
// 核心方法:
// void addCategory(Category category)
// → 校验分类名称非空、编号非空
// → 校验分类编号唯一性
// → 调用DAO插入
//
// void updateCategory(Category category)
// → 校验必填项
// → 调用DAO更新
//
// void deleteCategory(int categoryId)
// → 检查该分类下是否有资产(引用完整性)
// → 有资产则抛出BusinessException,禁止删除
// → 无资产则调用DAO删除
//
// List<Category> getAllCategories()
// → 调用DAO查询所有
//
// Category getCategoryById(int id)
// → 调用DAO查询
BorrowService.java
// 借用业务逻辑(核心业务,状态流转复杂)
//
// 核心方法:
// void applyBorrow(int assetId, int userId, String reason, LocalDate expectedReturnDate)
// → 校验资产状态必须为"available"
// → 校验预计归还日期晚于今天
// → 校验借用原因非空
// → 创建Borrow记录(状态pending)
// → 更新资产状态为"borrowed"(预占,审批通过后确认)
// → 注意:此处需事务保证借用记录与资产状态一致
//
// void approveBorrow(int borrowId, int approverId, boolean approved, String remark)
// → 校验借用状态必须为"pending"
// → 校验操作人为管理员
// → 若同意:状态改为approved,资产状态保持borrowed
// → 若拒绝:状态改为rejected,资产状态恢复为available
// → 记录审批人、审批时间、审批备注
// → 需事务保证
//
// void returnAsset(int borrowId)
// → 校验借用状态必须为"approved"
// → 更新借用记录:状态改returned,记录实际归还日期
// → 更新资产状态为available
// → 需事务保证
//
// List<Borrow> getMyBorrows(int userId)
// → 查询当前用户的借用记录
//
// List<Borrow> getPendingBorrows()
// → 查询待审批借用记录
//
// List<Borrow> getAllBorrows()
// → 查询所有借用记录
//
// void checkOverdue()
// → 批量检查逾期:approved状态+预计归还日期<今天 → 更新为overdue
DisposalService.java
// 报废业务逻辑
//
// 核心方法:
// void applyDisposal(int assetId, int userId, String reason)
// → 校验资产状态必须为"available"
// → 校验报废原因非空
// → 创建Disposal记录(状态pending)
// → 需事务保证
//
// void approveDisposal(int disposalId, int approverId, boolean approved, String remark)
// → 校验报废状态必须为"pending"
// → 校验操作人为管理员
// → 若同意:状态改approved,资产状态改为disposed,记录报废日期
// → 若拒绝:状态改rejected,资产状态保持available
// → 需事务保证
//
// List<Disposal> getMyDisposals(int userId)
// → 查询当前用户的报废申请
//
// List<Disposal> getPendingDisposals()
// → 查询待审批报废记录
//
// List<Disposal> getAllDisposals()
// → 查询所有报废记录
StatService.java
// 统计业务逻辑
//
// 核心方法:
// Map<String, Integer> getCategoryStat()
// → 按分类统计资产数量,返回{分类名: 数量}
// → 用于饼图展示
//
// Map<String, Integer> getStatusStat()
// → 按状态统计资产数量,返回{状态名: 数量}
// → 用于柱状图展示
//
// List<Map<String, Object>> getBorrowFrequency(int topN)
// → 统计借用次数TOP N的资产
// → 返回[{资产名, 借用次数}, ...]
//
// Map<String, Double> getValueStat()
// → 按分类统计资产价值汇总
// → 返回{分类名: 总价值}
//
// int getTotalAssetCount()
// → 资产总数
//
// double getTotalAssetValue()
// → 资产总价值
//
// int getBorrowingCount()
// → 当前借出数量
//
// int getOverdueCount()
// → 逾期未还数量
2.4 界面类(view)
LoginFrame.java
// 登录窗口 — 程序启动入口界面
// 布局:居中显示,用户名/密码输入框 + 登录按钮 + 注册链接
// 事件:
// 登录按钮 → 调用UserService.login()
// 成功 → 隐藏LoginFrame,显示MainFrame(传入User对象)
// 失败 → 弹出错误提示
// 注册链接 → 打开RegisterDialog
// 窗口:setSize(400, 300),居中,关闭时退出程序
RegisterDialog.java
// 注册对话框 — JDialog模态窗口
// 表单:用户名、密码、确认密码、真实姓名 + 注册/取消按钮
// 校验:
// 用户名3-20位 → 即时校验
// 密码6-20位 → 即时校验
// 两次密码一致 → 提交时校验
// 真实姓名非空 → 提交时校验
// 提交 → 调用UserService.register()
MainFrame.java
// 主窗口 — 功能导航容器
// 布局:BorderLayout
// 北部:顶部信息栏(欢迎语 + 当前用户 + 角色 + 修改密码按钮 + 退出按钮)
// 西部:左侧导航菜单(JList或JButton组)
// 菜单项:资产管理、分类管理、借用管理、报废管理、数据统计
// 管理员额外可见:用户管理
// 中部:右侧内容区(CardLayout切换各功能面板)
// 切换逻辑:
// 点击左侧菜单项 → CardLayout.show(对应Panel)
// 切换面板时自动刷新数据
panel/AssetPanel.java
// 资产管理面板
// 布局:
// 顶部:搜索栏(名称输入 + 分类下拉 + 状态下拉 + 位置输入 + 搜索按钮 + 重置按钮)
// 中部:JTable资产列表(编号/名称/分类/状态/价值/购入日期/位置)
// 底部:操作按钮(新增/编辑/删除/详情)
// 右下:分页控件(可选)
// 事件:
// 搜索 → 调用AssetService.searchAssets() → 刷新表格
// 新增 → 打开AssetDialog(mode=ADD)
// 编辑 → 选中行 → 打开AssetDialog(mode=EDIT, asset)
// 删除 → 选中行 → 确认对话框 → AssetService.deleteAsset()
// 详情 → 选中行 → 打开AssetDialog(mode=VIEW, asset)
panel/CategoryPanel.java
// 分类管理面板
// 布局:
// 中部:JTable分类列表(编号/名称/描述/资产数量/创建时间)
// 底部:操作按钮(新增/编辑/删除)
// 事件:
// 新增 → 打开CategoryDialog(mode=ADD)
// 编辑 → 选中行 → 打开CategoryDialog(mode=EDIT, category)
// 删除 → 选中行 → 确认对话框 → CategoryService.deleteCategory()
// → 捕获BusinessException提示"该分类下有资产,禁止删除"
panel/BorrowPanel.java
// 借用管理面板
// 布局:
// 顶部:Tab切换(我的借用 / 待审批 / 全部记录)—— 根据角色显示不同Tab
// 中部:JTable借用列表
// 底部:操作按钮(借用申请 / 审批 / 归还)
// 事件:
// 借用申请 → 打开BorrowDialog
// 审批 → 选中待审批行 → 打开ApproveDialog(type=borrow)
// 归还 → 选中已审批行 → 确认归还 → BorrowService.returnAsset()
panel/DisposalPanel.java
// 报废管理面板
// 布局:
// 顶部:Tab切换(我的申请 / 待审批 / 全部记录)
// 中部:JTable报废列表
// 底部:操作按钮(报废申请 / 审批)
// 事件:
// 报废申请 → 打开DisposalDialog
// 审批 → 选中待审批行 → 打开ApproveDialog(type=disposal)
panel/StatPanel.java
// 数据统计面板
// 布局:
// 顶部:Tab切换(分类统计 / 状态统计 / 借用排行 / 价值汇总)
// 中部:JFreeChart图表区域
// 底部:汇总数据标签(资产总数/总价值/借出数/逾期数)
// 图表:
// 分类统计 → PieDataset + ChartFactory.createPieChart()
// 状态统计 → DefaultCategoryDataset + ChartFactory.createBarChart()
// 借用排行 → DefaultCategoryDataset + 横向柱状图
// 价值汇总 → DefaultCategoryDataset + 柱状图
panel/UserPanel.java
// 用户管理面板(仅管理员可见)
// 布局:
// 中部:JTable用户列表(用户名/姓名/角色/状态/创建时间)
// 底部:操作按钮(修改角色 / 启用禁用)
// 事件:
// 修改角色 → 下拉选择admin/user → UserService.updateUserRole()
// 启用禁用 → 确认对话框 → UserService.updateUserStatus()
2.5 工具类(util)
DBUtil.java
// 数据库连接管理工具
// 设计思路:读取db.properties配置,提供连接获取与释放
//
// 核心方法:
// static Connection getConnection() — 获取数据库连接
// static void close(Connection conn) — 关闭连接
// static void close(ResultSet rs, PreparedStatement pstmt, Connection conn)
// — 释放查询资源(重载)
//
// 实现要点:
// 1. 类加载时读取db.properties,只读一次
// 2. getConnection()每次创建新连接(课程项目无需连接池)
// 3. close方法判断null后再关闭,避免NPE
// 4. 所有DAO方法通过DBUtil获取连接,finally块中释放
MD5Util.java
// MD5加密工具
//
// 核心方法:
// static String encrypt(String input) — 返回32位小写MD5摘要
//
// 实现:java.security.MessageDigest("MD5") + Hex转换
ValidatorUtil.java
// 通用表单校验工具
//
// 核心方法:
// static boolean isEmpty(String str) — 判空(null或trim后为空)
// static boolean isPositive(BigDecimal value) — 判断为正数
// static boolean isLengthInRange(String str, int min, int max) — 长度范围校验
// static boolean isDateAfter(LocalDate date, LocalDate after) — 日期先后校验
// static boolean isAlphanumeric(String str) — 字母数字校验(用户名)
// static boolean isNumeric(String str) — 纯数字校验
//
// 使用场景:
// Service层校验 + View层即时校验
DateUtil.java
// 日期工具类
//
// 核心方法:
// static String format(LocalDate date) — LocalDate → "yyyy-MM-dd"
// static String format(LocalDateTime dateTime) — LocalDateTime → "yyyy-MM-dd HH:mm:ss"
// static LocalDate parseDate(String str) — "yyyy-MM-dd" → LocalDate
// static LocalDateTime parseDateTime(String str) — "yyyy-MM-dd HH:mm:ss" → LocalDateTime
2.6 异常类(exception)
BusinessException.java
// 业务异常,继承RuntimeException
// 字段:errorCode(错误码)、message(错误描述)
// 用途:Service层抛出,View层捕获并展示给用户
// 示例:throw new BusinessException("资产编号已存在")
DBException.java
// 数据库异常,继承RuntimeException
// 字段:message(错误描述)、cause(原始SQLException)
// 用途:DAO层抛出,Service层捕获后包装为BusinessException或直接向上传播
三、业务逻辑设计
3.1 登录注册流程
登录流程:
用户输入 → ValidatorUtil判空 → UserService.login()
→ UserDAO.findByUsername() → 用户不存在?→ 抛异常"用户名或密码错误"
→ MD5Util.encrypt(输入密码) → 与数据库密码比对 → 不匹配?→ 抛异常"用户名或密码错误"
→ status==0?→ 抛异常"账户已被禁用"
→ 返回User对象 → LoginFrame隐藏 → MainFrame显示
注册流程:
用户输入 → ValidatorUtil校验格式 → 确认密码一致性
→ UserService.register() → 用户名唯一性校验 → MD5加密密码 → UserDAO.insert()
3.2 资产CRUD流程
录入:表单填写 → ValidatorUtil校验 → AssetService.addAsset()
→ 编号唯一性校验 → 价值正数校验 → 日期合理性校验 → AssetDAO.insert()
修改:选中行 → 回填表单 → 修改字段 → AssetService.updateAsset()
→ 校验必填项 → AssetDAO.update()
删除:选中行 → 确认对话框 → AssetService.deleteAsset()
→ 检查资产状态(borrowed不可删) → AssetDAO.deleteById()
查询:输入条件 → AssetService.searchAssets()
→ 任意条件为null则不筛选 → AssetDAO.findByCondition() → 返回结果列表
3.3 借用归还流程
借用申请:
选择可用资产 → 填写原因+预计归还日期 → BorrowService.applyBorrow()
→ 校验资产状态为available → 创建Borrow(pending)
→ 更新资产状态为borrowed → 事务提交
审批(管理员):
选中待审批记录 → 同意/拒绝 → BorrowService.approveBorrow()
→ 同意:Borrow.status → approved,资产保持borrowed
→ 拒绝:Borrow.status → rejected,资产恢复available
→ 事务提交
归还:
选中已审批记录 → 确认归还 → BorrowService.returnAsset()
→ Borrow.status → returned,记录实际归还日期
→ 资产状态恢复available → 事务提交
逾期检查:
BorrowService.checkOverdue() → approved + expectedReturnDate < 今天 → overdue
3.4 报废流程
报废申请:
选择可用资产 → 填写报废原因 → DisposalService.applyDisposal()
→ 校验资产状态为available → 创建Disposal(pending)
审批(管理员):
选中待审批记录 → 同意/拒绝 → DisposalService.approveDisposal()
→ 同意:Disposal.status → approved,资产状态 → disposed
→ 拒绝:Disposal.status → rejected,资产状态保持available
3.5 统计查询流程
分类统计:StatService.getCategoryStat()
→ SELECT c.category_name, COUNT(a.id) FROM t_asset a JOIN t_category c → PieDataset → 饼图
状态统计:StatService.getStatusStat()
→ SELECT status, COUNT(*) FROM t_asset GROUP BY status → DefaultCategoryDataset → 柱状图
借用排行:StatService.getBorrowFrequency(10)
→ SELECT a.asset_name, COUNT(b.id) FROM t_borrow b JOIN t_asset a GROUP BY a.id → TOP 10
价值汇总:StatService.getValueStat()
→ SELECT c.category_name, SUM(a.value) FROM t_asset a JOIN t_category c → 柱状图
3.6 表单校验设计
校验层级:
1. 即时校验(View层)— 输入时实时反馈
- JTextField.addKeyListener / FocusListener
- 用户名长度、密码长度、数值格式等
2. 提交校验(Service层)— 提交时完整性校验
- 必填项非空
- 唯一性(用户名、资产编号)
- 业务规则(资产状态、日期合理性)
3. 数据库校验(DAO层)— 数据库约束兜底
- UNIQUE约束
- NOT NULL约束
- 外键约束
校验反馈:
- 即时校验:字段旁红色提示文字
- 提交校验:JOptionPane.showMessageDialog警告
- 数据库校验:捕获SQLException转为友好提示
3.7 数据可视化设计
JFreeChart集成:
1. Maven依赖:org.jfreechart/jfreechart
2. 图表创建:ChartFactory + 数据集(PieDataset/CategoryDataset)
3. 图表展示:ChartPanel封装 → 添加到StatPanel
4. 样式定制:标题、颜色、字体、图例
四种图表:
- 饼图(PieChart):分类数量占比,颜色区分各类别
- 柱状图(BarChart):状态数量对比,横向展示
- 排行图:借用频率TOP 10,降序横向柱状图
- 价值图:各分类资产价值汇总,柱状图
四、数据库交互设计
4.1 JDBC连接管理
// DBUtil核心逻辑
// 1. 静态初始化块加载db.properties
static {
Properties props = new Properties();
try (InputStream is = DBUtil.class.getClassLoader().getResourceAsStream("db.properties")) {
props.load(is);
url = props.getProperty("db.url");
username = props.getProperty("db.username");
password = props.getProperty("db.password");
Class.forName(props.getProperty("db.driver"));
} catch (Exception e) {
throw new RuntimeException("数据库配置加载失败", e);
}
}
// 2. 获取连接
public static Connection getConnection() throws SQLException {
return DriverManager.getConnection(url, username, password);
}
// 3. 释放资源 — 判断null后关闭,顺序:ResultSet → PreparedStatement → Connection
4.2 PreparedStatement防注入
// 所有SQL操作均使用PreparedStatement,禁止字符串拼接SQL
// 示例:
String sql = "SELECT * FROM t_user WHERE username = ? AND password = ?";
try (PreparedStatement pstmt = conn.prepareStatement(sql)) {
pstmt.setString(1, username); // 参数化,防SQL注入
pstmt.setString(2, password);
ResultSet rs = pstmt.executeQuery();
// ...
}
4.3 事务管理
// 需要事务的操作:借用申请、借用审批、借用归还、报废审批
// 这些操作涉及多表更新,需保证原子性
//
// 事务管理模式:手动事务控制
// Connection conn = null;
// try {
// conn = DBUtil.getConnection();
// conn.setAutoCommit(false); // 开启事务
//
// // 执行多条SQL...
//
// conn.commit(); // 提交事务
// } catch (Exception e) {
// if (conn != null) conn.rollback(); // 回滚事务
// throw new BusinessException("操作失败:" + e.getMessage());
// } finally {
// if (conn != null) conn.setAutoCommit(true);
// DBUtil.close(conn);
// }
4.4 BaseDAO通用操作封装
// 通用更新(INSERT/UPDATE/DELETE)
public int update(String sql, Object... params) {
Connection conn = null;
PreparedStatement pstmt = null;
try {
conn = DBUtil.getConnection();
pstmt = conn.prepareStatement(sql);
for (int i = 0; i < params.length; i++) {
pstmt.setObject(i + 1, params[i]);
}
return pstmt.executeUpdate();
} catch (SQLException e) {
throw new DBException("数据库操作失败", e);
} finally {
DBUtil.close(null, pstmt, conn);
}
}
// 通用查询列表
public <T> List<T> queryList(String sql, RowMapper<T> mapper, Object... params) {
// 类似结构,ResultSet遍历 + mapper映射
}
五、规范要求
5.1 Java命名规范
| 类型 | 规范 | 示例 |
|---|---|---|
| 类名 | 大驼峰 | AssetService, BorrowDAO |
| 方法名 | 小驼峰 | findByUsername, addAsset |
| 变量名 | 小驼峰 | assetList, currentUser |
| 常量名 | 全大写下划线 | MAX_RETRY_COUNT |
| 包名 | 全小写 | com.asset.service |
| 数据库表名 | t_前缀+小写下划线 | t_asset, t_borrow |
| 数据库字段名 | 小写下划线 | asset_code, create_time |
5.2 注释规范
/**
* 资产业务逻辑类
* 提供资产的增删改查、状态管理、数据校验等业务功能
*
* @author 作者名
* @version 1.0
*/
public class AssetService {
/**
* 新增资产
* 校验资产编号唯一性、必填项、价值正数后调用DAO插入
*
* @param asset 资产实体对象
* @throws BusinessException 编号重复、校验不通过时抛出
*/
public void addAsset(Asset asset) {
// 校验资产编号唯一性
// ...
}
}
5.3 异常处理思路
异常分层处理策略:
DAO层:捕获SQLException → 包装为DBException向上抛出
Service层:捕获DBException → 转为BusinessException(对用户友好)
Service层:业务规则不满足 → 直接抛BusinessException
View层:捕获BusinessException → JOptionPane展示错误信息
View层:捕获未预期异常 → 记录日志 + 通用错误提示
禁止:
- 禁止空catch块吞掉异常
- 禁止catch Exception后不做处理
- 禁止在DAO/Service层直接弹出UI对话框
5.4 AI代码校验优化要求
| 校验维度 | 检查要点 |
|---|---|
| 逻辑正确性 | 业务流程是否完整、边界条件是否处理 |
| SQL安全性 | 是否使用PreparedStatement、参数是否正确绑定 |
| 资源泄漏 | Connection/Statement/ResultSet是否正确关闭 |
| 命名规范 | 是否符合Java命名规范 |
| 异常处理 | 是否合理捕获/抛出、异常信息是否明确 |
| 代码冗余 | 是否有重复代码可提取到BaseDAO或工具类 |
| 业务完整性 | 状态流转是否正确、事务是否保证 |
六、课程评分匹配设计
6.1 功能完整性(满分保障)
| 课程要求 | 本系统实现 |
|---|---|
| 用户登录注册 | ✅ 登录+注册+修改密码+角色权限 |
| 资产数据增删改查 | ✅ 完整CRUD + 多条件组合查询 |
| 数据可视化展示 | ✅ 4种JFreeChart图表 |
| 表单数据校验 | ✅ 三层校验(即时+提交+数据库) |
| 资产管理基础业务 | ✅ 借用/归还/报废全流程 |
| 功能量级2-3倍 | ✅ 5张表、8个模块、审批流程、统计功能 |
6.2 代码质量
| 维度 | 保障措施 |
|---|---|
| 分层清晰 | 严格四层架构,层间调用规则明确 |
| 命名规范 | 遵循Java命名规范+阿里巴巴开发手册 |
| 注释完整 | 类注释+方法注释+关键逻辑行内注释 |
| 异常处理 | 自定义异常+分层处理+友好提示 |
| SQL安全 | PreparedStatement+参数化查询 |
| 资源管理 | finally块关闭+DBUtil统一释放 |
6.3 文档配套
| 文档 | 内容 |
|---|---|
| 架构设计文档 | 技术架构+功能模块+数据库设计+AI规范+感悟 |
| 目录结构文档 | 项目结构+目录功能注释 |
| 代码设计思路文档 | 本文档,完整设计思路 |
| SQL脚本 | 建库建表+初始数据 |
| 代码内注释 | 类/方法/逻辑三层注释 |
6.4 创新拓展
| 拓展点 | 说明 |
|---|---|
| 审批流程 | 借用/报废均需管理员审批,非简单状态切换 |
| 逾期自动检测 | 系统自动检测逾期借用记录 |
| 多维度统计 | 分类/状态/借用/价值四维度可视化 |
| 角色权限 | 管理员/普通用户功能差异化 |
| 组合查询 | 资产支持多条件组合筛选 |
| 数据关联完整性 | 删除分类检查资产引用、删除资产检查借用状态 |