背景:
我正在用JavaScript编写UI测试,使用Appium,用于iOS应用程序。它们具有类似的结构,例如this example。
我想要实现的目标:
初始屏幕包含元素列表(UITableView in iOS)的测试。从这个列表中,我想在某个级别(不知道有多少)深入导航,直到满足条件。这应该发生在该列表中的前3个元素(让我们称之为L0)。
实施例:
L0(第1要素) - > L1 - > L2 - > L3-> L4 - > L5 - >条件满足 - >导航回L0
L0(第2要素) - > L1 - > L2 - >条件满足 - >导航回L0
L0(第3元素) - > L1 - > L2 - > L3->条件满足 - >导航回L0
显示代码:
//the test
it('Browse list', function() {
return driver
.navigateToL0()
.navigateToPageDetail(1, 3);
});
//the function with the issue
navigateToPageDetail: function(driver, startIndex, endIndex) {
var listItemName;
var navigationBarItemName;
var hasListItemName = false;
var navigationLevelCount = 0;
var currentRootListElementIndex = startIndex;
var currentListElementIndex = endIndex;
var chain = driver;
do {
do {
chain = chain
.hasElementInListAtIndex(currentListElementIndex)
.then(function(assertion) {
hasListItemName = assertion;
if (assertion == true) {
return driver
.getExpectedElementName(currentListElementIndex, function (name) {
listItemName = name;
})
.clickElementInListAtIndex(currentListElementIndex)
.getActualElementName(function (name) {
navigationBarItemName = name;
listItemName.should.contain(navigationBarItemName);
navigationLevelCount ++;
});
}
if (currentListElementIndex != 1) {
currentListElementIndex = 1;
}
});
} while (hasListItemName && (listItemName == navigationBarItemName));
for (var j = 0; j <= navigationLevelCount; j++) {
chain = chain.goBack();
}
currentRootListElementIndex++;
currentListElementIndex = currentRootListElementIndex;
} while (currentRootListElementIndex <= endIndex);
return chain;
}
有什么问题?
内部do while
只运行一次,因为while
中的条件始终为false
所以currentListElementIndex = 4
然后它从L0导航3次到L1并返回。 (L0中的第4个元素)
我了解这是closures inside loops的问题,但我不明白如何修复内部do while
问题。
您尝试了什么?
我尝试使用Avoiding the Reference Problem。 所以我的代码变成了:
navigateToPageDetail: function(driver, startIndex, endIndex) {
var listItemName;
var navigationBarItemName;
var hasListItemName = false;
var navigationLevelCount = 0;
var currentRootListElementIndex = startIndex;
var currentListElementIndex = endIndex;
var chain = driver;
do {
(function(currentListElementIndex_v2) { //added line
do {
chain = chain
.hasElementInListAtIndex(currentListElementIndex_v2)
.then(function(assertion) {
hasListItemName = assertion;
if (assertion == true) {
return driver
.getExpectedElementName(currentListElementIndex_v2, function (name) {
listItemName = name;
})
.clickElementInListAtIndex(currentListElementIndex_v2)
.getActualElementName(function (name) {
navigationBarItemName = name;
listItemName.should.contain(navigationBarItemName);
navigationLevelCount ++;
});
}
if (currentListElementIndex_v2 != 1) {
currentListElementIndex_v2 = 1;
}
});
} while (hasListItemName && (listItemName == navigationBarItemName));
})(currentListElementIndex); //added line
for (var j = 0; j <= navigationLevelCount; j++) {
chain = chain.goBack();
}
currentRootListElementIndex++;
currentListElementIndex = currentRootListElementIndex;
} while (currentRootListElementIndex <= endIndex);
return chain;
}
这使我更接近预期的行为,因为currentListElementIndex
现在得到正确的值(1,2,3)
尽管如此,内部do while
只运行一次,因为while
中的条件始终为false。
有什么问题?
如何修复我的代码,以便我的内部do while
循环按预期运行?
如果问题不明确,请告诉我,我会改进不清楚的部分。