java - 在 DAO 模式中添加服务有什么好处?

标签 java dao

我正在设计我的 JSF 网络应用程序。我不想在我的 Beans 类中包含业务逻辑代码。所以我决定使用 DAO 模式。现在 Beans 数据(修复数据)存储在 xml 文件中。现在我想为数据库扩展它并使用 Hibernate。

但我对我应该在我的服务类中放什么(如果有的话)感到困惑。

如果我有这个 DAO

public interface IRepairDao {

public Repairs fetchRepairs() throws RepairDaoException;
public Manufacturers fetchManufacturers() throws RepairDaoException;
public List<Model> fetchManufacturerModels(Manufacturer manufacturer) throws RepairDaoException;
public void saveRepairs(Repairs repairs) throws RepairDaoException;
}

例如这个 DAO 实现

public class RepairXmlDao implements IRepairDao {

private Serializer xmlSer;
private final String repairsXmlPath = "E:\\WORK\\Mariusz\\repairs.xml";
private final String setupXmlPath = "E:\\WORK\\Mariusz\\setup.xml";

@Override
public Repairs fetchRepairs() throws RepairDaoException {
    try {
        xmlSer = new Persister();
        InputStream fis = new FileInputStream(repairsXmlPath);
        BufferedReader in = new BufferedReader(
                new InputStreamReader(fis, Charset.forName("UTF-8")));
        String str = "", s;
        while((s = in.readLine()) != null)
            str += s;
        Repairs repairs = xmlSer.read(Repairs.class, str);
        return repairs;
    } catch(Exception e) {
        throw new RepairDaoXmlExcpetion("Thrown when fetching repairs from xml", e);
    }
}

@Override
public Manufacturers fetchManufacturers() throws RepairDaoException {
    try {
    xmlSer = new Persister();
    InputStream fis = new FileInputStream(setupXmlPath);
    BufferedReader in = new BufferedReader(
            new InputStreamReader(fis, Charset.forName("UTF-8")));
    String str = "", s;
    while((s = in.readLine()) != null)
        str += s;
    Manufacturers manufacturers = xmlSer.read(Manufacturers.class, str);
    //models = manufacturers.getManufacturers().get(0).getModels();
    return manufacturers;
    } catch(Exception e) {
        throw new RepairDaoXmlExcpetion("Thrown when fetching manufacturers from xml", e);
    }
}

@Override
public List<Model> fetchManufacturerModels(Manufacturer manufacturer) throws RepairDaoException {
    List<Model> models = new ArrayList<>();
    Manufacturers manufacturers = fetchManufacturers();
    for(Manufacturer m : manufacturers.getManufacturers()) {
        if(m.getName().equals(manufacturer.getName())) {
            models = m.getModels();
            break;
        }
    }
    return models;
}

@Override
public void saveRepairs(Repairs repairs) throws RepairDaoException {
    try {
        xmlSer = new Persister();
        File result = new File(repairsXmlPath);
        xmlSer.write(repairs, result);
    } catch(Exception e) {
        throw new RepairDaoXmlExcpetion("Thrown when saving repairs to xml", e);
    }
}

}

向其中添加此服务对我有何真正好处?

public class RepairService {

private IRepairDao repairDao;

public Repairs fetchRepairs() throws RepairDaoException {
    return repairDao.fetchRepairs();
}

public Manufacturers fetchManufacturers() throws RepairDaoException {
    return repairDao.fetchManufacturers();
}

public List<Model> fetchManufacturerModels(Manufacturer manufacturer) 
        throws RepairDaoException {
    return repairDao.fetchManufacturerModels(manufacturer);
}

public void saveRepairs(Repairs repairs) throws RepairDaoException {
    repairDao.saveRepairs(repairs);
}
}

我看不到对我有任何真正的好处。尽管我确实看到了缺点,例如,如果我需要修改我的 DAO,我也将不得不修改我的服务。或者也许我的服务代码是错误的,它缺少一些重要的部分?感谢您提供任何提示或建议。

编辑

您是否建议创建服务层次结构,类似于我的 DAO 设计?

public abstract class ARepairService {

protected IRepairDao repairDao;

public ARepairService(IRepairDao repairDao) {
    this.repairDao = repairDao;
}

public abstract Repairs fetchRepairs() throws RepairDaoException;

public abstract Manufacturers fetchManufacturers() throws RepairDaoException;

public abstract List<Model> fetchManufacturerModels(Manufacturer manufacturer) 
        throws RepairDaoException;

public abstract void saveRepairs(Repairs repairs) throws RepairDaoException;
}

以这个实现为例

public class RepairServiceXml extends ARepairService {

public RepairServiceXml(IRepairDao repairDao) {
    super(repairDao);
}

@Override
public Repairs fetchRepairs() throws RepairDaoException {
    return repairDao.fetchRepairs();
}

@Override
public Manufacturers fetchManufacturers() throws RepairDaoException {
    return repairDao.fetchManufacturers();
}

@Override
public List<Model> fetchManufacturerModels(Manufacturer manufacturer) 
        throws RepairDaoException {
    return repairDao.fetchManufacturerModels(manufacturer);
}

@Override
public void saveRepairs(Repairs repairs) throws RepairDaoException {
    repairDao.saveRepairs(repairs);
}
}

最佳答案

服务通常是指您将 DAO 捆绑在一起以形成一些业务逻辑。假设您有这样的事情:

public interface CarService {
  public void repairCar(Car car);
}

在实现中,您必须从 ManufacturerDao 中检索维修零件,更新汽车状态并最终向车主收费。例如

// skipped non-relevant parts(e.g. DAO injection) for brevity
public class CarServiceImpl implements CarService {

public ManufacturerDao manufacturerDao;
public BillingDao billingDao;
public CarDao carDao;

public void repairCar(Car car) {
    // get the car part
    Model model = car.getMissingPart();
    CarPart carPart = manufacturerDao.getNewCarPart(model);
    // install it and save the car
    car.installCarPart(carPart);
    car.setStatus(Status.REPAIRED);
    carDao.updateCar(car);
    // bill the owner
    billingDao.bill(car.getOwner());
}

整个 repairCar 必须是一个事务。想象一下,如果你正在修车,而当你想给客户开账单时,你会得到一个异常(exception)!如果整件事情不在交易中,您将不得不向供应商支付固定汽车零件的费用,但是……您无法向客户开具账单。没有事务,业务逻辑和数据库状态都被破坏了。

这可能就是为什么您看不到在 DAO 层之上添加服务层的值(value)的原因。您的业​​务逻辑非常简单,您的服务层只需将调用委托(delegate)给 DAO 层即可。对于您的用例,您可以在没有服务层的情况下生活,直到您需要它。然而在现实世界中,业务逻辑不会那么微不足道,服务层是必不可少的。

关于java - 在 DAO 模式中添加服务有什么好处?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60419432/

相关文章:

java - 如何将 .jar 文件转换为 Unix 可执行文件? (苹果)

java - 如何更改对象实例并在同一方法中返回值?

java - 如何在 hibernate 中使用连接表

java - jsf检查用户是否登录

java - 在计算器中识别一元减号,java

java - 匹配子字符串后替换字符串的所有后续字符

android - 如何从 DAO 查询返回单个 int 值?

java - 通用 DAO 如何为所有不同的 DAO 实现返回相同的类型?

c# - Linq to SQL 中的 DAO 工厂

java - 重写传递静态常量的方法是否被认为是不好的做法?