下面从概念 → 设计原则 → 常见结构 → 示例代码 → 现代演进几个层面,系统讲一下 Java DAO(Data Access Object) 的设计方法。
DAO(Data Access Object) 是一种设计模式,用于:
将业务逻辑与数据访问逻辑解耦
屏蔽底层数据库(JDBC / MyBatis / JPA)的差异
核心思想:
Service → DAO → 数据库
XxxDao 接口XxxDaoImpl 实现SQLExceptioncom.example.demo
├── entity
│ └── User.java
├── dao
│ ├── UserDao.java (接口)
│ └── UserDaoImpl.java (实现)
├── service
│ └── UserService.java
└── exception
└── DaoException.java
public class User {
private Integer id;
private String username;
private String password;
// getter / setter
}
public interface UserDao {
User findById(Integer id);
List<User> findAll();
void insert(User user);
void update(User user);
void delete(Integer id);
}
public class UserDaoImpl implements UserDao {
private DataSource dataSource;
public UserDaoImpl(DataSource dataSource) {
this.dataSource = dataSource;
}
@Override
public User findById(Integer id) {
String sql = "SELECT id, username, password FROM user WHERE id = ?";
try (Connection conn = dataSource.getConnection();
PreparedStatement ps = conn.prepareStatement(sql)) {
ps.setInt(1, id);
ResultSet rs = ps.executeQuery();
if (rs.next()) {
User user = new User();
user.setId(rs.getInt("id"));
user.setUsername(rs.getString("username"));
user.setPassword(rs.getString("password"));
return user;
}
} catch (SQLException e) {
throw new DaoException("查询用户失败", e);
}
return null;
}
// 其他方法类似...
}
public class DaoException extends RuntimeException {
public DaoException(String message, Throwable cause) {
super(message, cause);
}
}
public class UserService {
private UserDao userDao;
public UserService(UserDao userDao) {
this.userDao = userDao;
}
public User login(String username, String password) {
User user = userDao.findByUsername(username);
if (user == null || !user.getPassword().equals(password)) {
throw new BusinessException("用户名或密码错误");
}
return user;
}
}
✅ 业务层完全不关心数据库实现
@Mapper
public interface UserDao {
User selectById(@Param("id") Integer id);
void insert(User user);
}
public interface UserRepository extends JpaRepository<User, Integer> {
}
| 对比项 | DAO | Repository |
|---|---|---|
| 关注点 | 表 / SQL | 聚合 / 领域 |
| 使用场景 | 传统项目 | DDD |
| 技术 | JDBC / MyBatis | JPA |
❌ 在 DAO 里写业务逻辑
❌ Service 直接写 SQL
❌ DAO 返回 ResultSet
❌ 每个方法 new 一个 DAO
❌ 不使用接口
DAO 的本质是:用接口隔离数据访问,用实现隐藏数据库细节。
如果你愿意,我可以:
你现在是传统 Java 项目还是 Spring Boot?
免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。