为接口或每个实现编写单元测试?

时间:2017-08-25 03:34:12

标签: java unit-testing mockito

我有一个Java接口和几个实现。现在我想用Mockito编写单元测试用例。

我的问题是,我应该为每个实现编写模拟测试用例还是仅为接口模拟测试用例?这种情况下的最佳做法是什么?我希望我的问题有道理。如果我错过了什么,请纠正我。

课程详情:

interface MessageQueue {
    add()
    poll()
    size()
}

class InMemoryMessageQueue implements MessageQueue {
    add() {
        //implementation
    }
    poll() {
        //implementation
    }
    size() {
        //implementation
    }
}

class FileSystemMessageQueue implements MessageQueue {
    add() {
        //implementation
    }
    poll() {
        //implementation
    }
    size() {
        //implementation
    }
}

目前我只使用Mockito为MessageQueue界面提供单元测试用例。

3 个答案:

答案 0 :(得分:3)

听起来你在这里混淆了一些细节,因为"模拟测试案例"没有进一步的细节,没有多大意义......

首先,如果您有,请说三个接口的实现,最佳做法是测试所有这三个。

只要您的实施没有依赖关系,就不会涉及任何嘲弄,因为......

第二,mocking用于测试依赖项。例如:

您的实现#2必须从数据库加载数据。为此,它使用类的实例,让它称之为DatabaseAccessor。通过调用此DatabaseAccessor对象的方法,它从数据库中获取数据。

现在,如果你想进行单元测试实现#2,你不想真正需要一个数据库,因为你遇到了很多问题。例如,如果数据库已关闭或处于错误状态,则即使实际#2(实际上是您要测试的实现)完全正常,您的测试也会失败。

那就是模拟进来的地方。你不是使用实际的DatabaseAccessor对象,而是模拟一个。换句话说,您创建一个看起来像DatabaseAccessor的对象,但实际上并没有访问Ddtabase。可以配置这种模拟的行为,这样,例如,如果调用一个方法,模拟会返回一些有用的测试数据(同样,在没有实际调用数据库的情况下,你只需告诉它"如果方法X被称为,做这个")。

这样,您可以专注于仅测试您的设备 - 实现#2 - 而不必担心它的所有依赖关系。这些是嘲笑的,你知道,他们会按照自己的意愿行事。

是的,使用Mockito,您可以模拟实现和接口,但最佳做法是使用接口。如有其他问题,我建议您提供有关课程的更多详细信息。

答案 1 :(得分:2)

让我们转向更加面向对象的讨论。 假设我们编写了一个Car接口,它有一个方法就像putFuel一样,

interface Car {
    void putFuel(FuelStation fs);
}

现在我想出了三个版本的汽车 -PetrolCar实现了Car -DieselCar实现了Car -CNGCar实现Car

现在putFuel()方法对于每个实现都会有很大不同,例如加油站,柴油站和CNG站,以及它们与模拟相关的依赖项。

因此,我应该为所有实现编写测试用例,因为每个实现都是不同的。 还要考虑到将来所有实现都可能具有接口可能没有的其他不同方法,因此为每个实现编写单独的单元测试用例是完全有意义的。

答案 2 :(得分:1)

单元测试是为测试类的功能而编写的。接口只有空方法。你应该为每个班级编写测试。