Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/440.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript Jasmine可以在对象上创建新属性并在以后删除它们吗?_Javascript_Unit Testing_Jasmine - Fatal编程技术网

Javascript Jasmine可以在对象上创建新属性并在以后删除它们吗?

Javascript Jasmine可以在对象上创建新属性并在以后删除它们吗?,javascript,unit-testing,jasmine,Javascript,Unit Testing,Jasmine,我必须监视某个规范的全局对象上当前不存在的属性。此规范中的全局对象属性由测试的功能在规范之外访问。为了更好的测试隔离,我希望mocked属性在规范结束时被删除。因为我不想跟踪这一点,我希望它在规范结束后被自动删除,就像jasmine删除用spyOn创建的间谍一样。我试图使用spyOnProperty,这只会给我一个属性不存在的错误。代码如下: 描述('test',函数(){ const value=“value” 常量测试={}; 它('应该在对象上创建自动删除的属性',函数(){ spyOnP

我必须监视某个规范的全局对象上当前不存在的属性。此规范中的全局对象属性由测试的功能在规范之外访问。为了更好的测试隔离,我希望mocked属性在规范结束时被删除。因为我不想跟踪这一点,我希望它在规范结束后被自动删除,就像jasmine删除用spyOn创建的间谍一样。我试图使用
spyOnProperty
,这只会给我一个
属性不存在的错误。代码如下:

描述('test',函数(){
const value=“value”
常量测试={};
它('应该在对象上创建自动删除的属性',函数(){
spyOnProperty(测试,“键”、“获取”)和.returnValue(值);
/*在我的代码中,这是一个复杂的调用,从外部访问全局变量:*/
expect(test.key).toBe(value)
});
});
我知道我可以做到以下几点,但这很容易出错(属性必须手动删除)而且冗长:

描述('test',函数(){
const value=“value”
常量测试={};
它('手动创建和删除对象上的属性',函数(){
Object.defineProperty(测试“键”{
获取:()=>值,
可配置:true
});
spyOnProperty(test,“key”,“get”).和.callThrough();
/*在我的代码中,这是一个复杂的调用,从外部访问全局变量:*/
expect(test.key)、toBe(value);
删除test.key;
});
})
这是我的小提琴


jasmine提供了更好的方法吗?

如果测试隔离是您的目标,您应该将对象作为一个整体进行隔离。您发现了正确的问题,但现在询问此任意库是否可以提供解决方案

由于我不知道你的全部情况,我只能列出你可以遵循的两个最可能的选择

选项1-测试隔离对象 而不是使用const test={};在描述块中,您可以将其拉入it块。如果您有更多的it块,并且反复使用测试,则可以在此it块中创建另一个测试对象,并且只将您的属性添加到此对象

描述('test',函数(){
const value=“value”
常量测试={};
它('手动创建和删除对象上的属性',函数(){
//替换为您的构造逻辑
const anotherTest={};
//用实际的方法调用替换值
另一个test.key=值;
expect(另一个test.key)、toBe(value);
});
})
因为没有其他人使用该对象,所以您的测试对象被隔离,其他测试不受影响

选项2-每次之前 不要直接在描述中创建对象,而是在创建对象的描述中添加beforeach

描述('test',函数(){
const value=“value”
常数试验;
beforeach(函数(){
//在每个it()-块之前创建的新对象,覆盖以前的测试对象
测试={};
}
它('手动创建和删除对象上的属性',函数(){
test.key=值;
expect(test.key)、toBe(value);
});
})

间谍不需要管理对象的生命周期。顾名思义,间谍应该看东西,而不是与之互动。当你想让间谍“改变某些东西”的时候,你违反了合同。

回答得很好。我强烈倾向于第一种选择。测试应该是可读的、独立的、彻底的和明确的(RITE-way).Explicit意味着您需要了解测试的所有内容都在该测试的范围内定义。每次测试前后都违反了该原则,使得依赖它们的测试更难完全理解。您不能这样概括。每次测试前都会增加复杂性,但当您有20个测试时()-块,在每个块中复制粘贴相同的代码不仅是不可读的,而且是维护的噩梦。所有这些原则的目标都是减少维护工作量。复制粘贴通常会增加维护工作量。很抱歉没有像我可能应该的那样显式。全局对象完全超出我的范围,从int开始使用ernal logic,它是从规范中调用的。这可能看起来不太漂亮,但我无法访问这部分代码。我的示例中的期望只是一个占位符。我也不完全同意您的结论:jasmine中的间谍确实与逻辑交互,因为它可以配置为返回您选择的值。这重要的是,允许对代码区域进行有针对性的测试(例如,您希望在“else”-逻辑中测试代码,因此返回false)。这就是我试图在这里实现的。你需要小心这里的措辞。在测试中,你有间谍、存根和模拟。Jasmine将它们放在一起可能会对你造成伤害,但处理它们的方式有很大的不同。JS中很少需要模拟和存根。因为你可以在任何给定的时间创建和重写任何对象输入法,它们在这里没有用。但是这远远超出了你的问题。所以请解释一下,你遗漏了什么。