在dart中存根类的任何实例 [英] Stub any instance of a class in dart
问题描述
在红宝石上开发可以做类似的事情:
Developing with ruby on rails allowed to do things like :
File.any_instance.expects(:delete)
这是在方法调用中测试副作用的好方法.
This was a great way to test for side effects within a method call.
如何在飞镖上做等效的事情?
How to do the equivalent in dart?
例如,如果您使用的是飞镖:
For example if you have in dart :
class Storage {
// the function to test
void deleteFile(String path) {
var fileToDelete = new File(path);
if (await fileToDelete.exists()) {
await fileToDelete.delete();
}
}
}
...
test("#deleteFile delete the file exists", () {
storage = new Storage();
// something equivalent to "File.any_instance.expects(:delete).once"
storage.deleteFile("/existing.txt")
});
test("#deleteFile does not try to delete the file when it does not exists", () {
storage = new Storage();
// something equivalent to "File.any_instance.expects(:delete).never"
storage.deleteFile("/not_existing.txt")
});
您将如何编写代码来检测是否已使用正确的参数调用了 File
的实例?
How would you write detect that an instance of File
has been called with the correct parameters?
存在一些可以使它可测试的模式,如此处所述: https://github.com/mockito/mockito/wiki/Mocking-Object-Creation
There is some patterns that exist that would make this testable as explained in here : https://github.com/mockito/mockito/wiki/Mocking-Object-Creation
但是,这两种模式都需要修改该类,以使其更具可测试性,方法是在自己的方法中隔离 File
对象创建,然后对该方法进行存根或使用工厂来推断该类.实例化 Storage
类时进行模拟.
However, these two patterns require to modify the class in order to make it more testable, by either isolating the File
object creation in his own method then stubbing this method or using a factory to infer the mock when instantiating the Storage
class.
我想找到一种方法来执行此操作,而不必修改类以使其像在ruby中一样更具可测试性.
I would like to find a way to do this without having to modify the class to make it more testable like in ruby.
这对于检查在方法执行期间是否生成了一些日志也非常有用.
This could be also very useful to check if some logs were produced during the method execution.
推荐答案
在Dart中,没有通用的方法来拦截静态方法调用(包括构造函数)或实例成员.
There is no general way to intercept static method calls (including constructors) or instance members on existing objects in Dart.
唯一知道何时调用某个方法的方法是,在对象引用传递给调用方之前,是否可以包装调用该方法的对象.因为Dart允许实现任何类接口,所以只要您可以在对象的创建者和用户之间找到对象,就可以包装任何已知的对象(如果您是创建者,则可以创建模拟而不是曾经有一个真实的对象).这种方法仍然不能用于静态方法.
The only way you can know when some method is called is if you can wrap the object that the method is called on, before the object reference is passed to the caller. Because Dart allows any class interface to be implemented, you can wrap any object that you know of, as long as you can get between the creator of the object and the user (and if you are the creator, you can create a mock instead of ever having a real object). That approach still cannot work for static methods.
也就是说,您需要一些抽象层,在其中可以替换代码而不是默认行为.
That is, you need some abstraction layer where you can substitute code instead of the default behavior.
当前问题的措辞方式无法解决.您不能更改由 File
构造函数创建的对象,也不能更改调用其 delete
方法时发生的情况.没有钩子允许这样做.您需要以某种方式重写 Storage
类,以引入允许您在类与 File
对象之间进行访问的抽象,也许可以使用 File createFile(字符串路径)
函数,而不是新文件
.
The way your current issue is phrased, it cannot be solved. You cannot change the object created by the File
constructor, and you cannot change what happens when its delete
method is called. There are no hooks to allow that.
You need to rewrite the Storage
class in some way to introduce the abstraction that allows you to get between the class and the File
object, maybe taking a File createFile(String path)
function that it uses instead of new File
.
这篇关于在dart中存根类的任何实例的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!