DAO 可以用于多个表吗?
Can DAO be used for multiple tables ?
我正在用 javaSE 开发小应用程序,只是为了提高我的技能。所以我有业务服务(更进一步的 BS),其中一些方法像 registerUser(User user)、addAmount(Long accountId)。 BS使用dao。假设 BS 是从 WS 或其他界面元素调用的。我有以下 DAO:
public interface UserDao {
User getUserByUsername(String username);
void saveUser(User user);
}
public interface AccountDao {
void saveAccount(Account account);
Account getAccountByUserId(Long userId);
}
我的 BS 看起来像
public class FastAccountServiceImpl implements FastAccountService{
private UserDao userDao;
private AccountDao accountDao;
public void registerUser(User user, Account account) throws Exception {
if (user.getUsername() == null || user.getUsername().isEmpty()) {
throw new Exception("all params are mandatory");
}
if (userDao.getUserByUsername(user.getUsername()) != null) {
throw new Exception("This user exists");
}
userDao.saveUser(user);
accountDao.saveAccount(account);
}
public void withdrawAmount(Double amount, Long userId) throws Exception {
if (amount == null || userId == null) {
throw new Exception("amount and userId are mandatory");
}
Account account = accountDao.getAccountByUserId(userId);
if (account.getAmount() == null || account.getAmount().compareTo(amount) < 1) {
throw new Exception("Insufficient amount in account");
}......
}}
所以我的第一个问题是我应该在哪里检查参数是否为 null 等?在学士学位?
第二个问题是为什么我们要为每个 table 设置单独的 dao?我可以为所有 table 只创建一个 dao 吗?所以在 BS 中只有一个 dao。该 dao 表示如下:
public interface MagicDao {
User getUserByUsername(String username);
void saveUser(User user);
void saveAccount(Account account);
Account getAccountByUserId(Long userId);
}
是的,在业务服务中检查 null 比在 Dao 中检查它们要好,因为这是一个分层架构,并且在 BS 中检查发生得更早。
至于为什么 "one Dao per table" - 好吧,Dao 的习惯是随着时间的推移变得更加复杂,所以如果你现在对 "Account" table 进行 2 次操作,将来很可能会有 10 或 20 个操作,因此有凝聚力的 1 对 1 方法更易于管理,也更容易 testable.
所以我肯定会避免MagicDao
。跨 tables 操作的工作是服务的角色(或其他一些模式,如 Facade
)——而不是 Dao,至少按照通用惯例。
此外,现代依赖注入框架使得在服务中声明和使用您需要的所有 Daos 变得简单。在业务服务中有 5 个或更多 Daos 没有问题(每个 table 一个)——我在我使用的代码中经常看到这种情况。
顺便说一下,你可以在你抛出 Exception
的地方使用 IllegalArgumentException
- 它更明确,它也是一个 RuntimeException
(所以你不需要声明它与 throws
)
我正在用 javaSE 开发小应用程序,只是为了提高我的技能。所以我有业务服务(更进一步的 BS),其中一些方法像 registerUser(User user)、addAmount(Long accountId)。 BS使用dao。假设 BS 是从 WS 或其他界面元素调用的。我有以下 DAO:
public interface UserDao {
User getUserByUsername(String username);
void saveUser(User user);
}
public interface AccountDao {
void saveAccount(Account account);
Account getAccountByUserId(Long userId);
}
我的 BS 看起来像
public class FastAccountServiceImpl implements FastAccountService{
private UserDao userDao;
private AccountDao accountDao;
public void registerUser(User user, Account account) throws Exception {
if (user.getUsername() == null || user.getUsername().isEmpty()) {
throw new Exception("all params are mandatory");
}
if (userDao.getUserByUsername(user.getUsername()) != null) {
throw new Exception("This user exists");
}
userDao.saveUser(user);
accountDao.saveAccount(account);
}
public void withdrawAmount(Double amount, Long userId) throws Exception {
if (amount == null || userId == null) {
throw new Exception("amount and userId are mandatory");
}
Account account = accountDao.getAccountByUserId(userId);
if (account.getAmount() == null || account.getAmount().compareTo(amount) < 1) {
throw new Exception("Insufficient amount in account");
}......
}}
所以我的第一个问题是我应该在哪里检查参数是否为 null 等?在学士学位? 第二个问题是为什么我们要为每个 table 设置单独的 dao?我可以为所有 table 只创建一个 dao 吗?所以在 BS 中只有一个 dao。该 dao 表示如下:
public interface MagicDao {
User getUserByUsername(String username);
void saveUser(User user);
void saveAccount(Account account);
Account getAccountByUserId(Long userId);
}
是的,在业务服务中检查 null 比在 Dao 中检查它们要好,因为这是一个分层架构,并且在 BS 中检查发生得更早。
至于为什么 "one Dao per table" - 好吧,Dao 的习惯是随着时间的推移变得更加复杂,所以如果你现在对 "Account" table 进行 2 次操作,将来很可能会有 10 或 20 个操作,因此有凝聚力的 1 对 1 方法更易于管理,也更容易 testable.
所以我肯定会避免MagicDao
。跨 tables 操作的工作是服务的角色(或其他一些模式,如 Facade
)——而不是 Dao,至少按照通用惯例。
此外,现代依赖注入框架使得在服务中声明和使用您需要的所有 Daos 变得简单。在业务服务中有 5 个或更多 Daos 没有问题(每个 table 一个)——我在我使用的代码中经常看到这种情况。
顺便说一下,你可以在你抛出 Exception
的地方使用 IllegalArgumentException
- 它更明确,它也是一个 RuntimeException
(所以你不需要声明它与 throws
)