我们一直在使用SauceLabs进行夜间Jenkins CI测试。我们在Windows 8下的Firefox 24中运行测试没有任何问题。现在我们想要扩展测试并在更多平台和浏览器上运行它们。我们的目标是在Windows和OSX以及IE11,10和9下的最新Firefox和Chrome浏览器中运行测试。
使用node.js客户端为webdriver / selenium2编写测试https://github.com/admc/wd
我现在遇到的问题是让我们的dragAndDrop方法在IE11和IE10中工作。它适用于最新的Firefox和Chrome以及IE9。
代码:
dragAndDrop: function (elem, x, y) {
var i = 0,
parent = elem.elementByXPath('..'),
offsetX,
offsetY,
pos,
offsetPos,
size;
offsetPos = this.getLocationInView(elem);
pos = this.getLocationInView(parent);
size = this.getSize(elem);
offsetX = offsetPos.x - pos.x + ~~(size.width / 2);
offsetY = offsetPos.y - pos.y + ~~(size.height / 2);
this.moveTo(parent, offsetX, offsetY);
this.buttonDown(0);
if(typeof x !== 'undefined' && x) {
for(; i <= x; i++) {
this.moveTo(parent, offsetX + i, offsetY);
}
}
if(typeof y !== 'undefined' && y) {
i = 0;
for(; i < y; i++) {
this.moveTo(parent, offsetX, offsetY + i);
}
}
this.buttonUp(0);
}
网站上的拖放脚本适用于IE11和IE10,不是我们对它的测试。它既是图像裁剪工具,也是使用拖放功能的输入滑块。我们觉得在IE浏览器中脚本最容易破坏,所以让测试工作会很好。
当我在测试运行时控制SauceLabs中的浏览器时,点击页面主体有时实际上会帮助dragAndDrop方法起作用。而这几乎是我现在唯一的线索。我尝试使用Seleniums click()
方法模拟它,甚至用JavaScript执行它。
this.execute('var event=document.createEvent("MouseEvent");
event.initEvent("click",true,true,window,0,50,120);
document.body.dispatchEvent(event);');
但没有任何运气。我不知道Selenium中是否存在错误或问题是什么。我在谷歌上花的时间让我变得更聪明。任何帮助将不胜感激。
到目前为止,我已尝试按照建议使用document.body.focus()
将焦点设置到身体上。我尝试使用不同的目标进行模拟JavaScript鼠标点击和本机WebDriver点击。试图复制在SauceLabs中控制VM时发生的事情。没有什么工作,我甚至不确定如果它有效,它会解决问题。
我还应该澄清,这不是页面上的第一个动作。在初始导航之后,填充两个输入字段,然后测试等待AJAX调用完成。然后,当找到合适的元素时,就会运行此方法。
答案 0 :(得分:1)
以下是pstenstrm解决方案的改进版本,该解决方案考虑了从元素向X和Y方向移动。
/*
pageX
pageY
distanceX
distanceY
id
className
###############
The variables above were defined in the closure scope of function
running the execute function.
*/
var mousedown = document.createEvent("MouseEvent"),
mouseup = document.createEvent("MouseEvent"),
elem = document.getElementById(id),
result = [],
elems = elem.getElementsByTagName("*"),
k = 0,
j = 0,
i, interval;
for(i in elems){
if((" " + elems[i].className + " ").indexOf(" " + className + " ") > -1){
result.push(elems[i]);
}
}
mousedown.initMouseEvent("mousedown", true, true, window, 0, 0, 0, pageX, pageY, 0, 0, 0, 0, 0, null);
result[0].dispatchEvent(mousedown);
interval = setInterval(function(){
if(k !== distanceX){k++;}
if(j !== distanceY){j++;}
iter(k,j);
if(k === distanceX + 1 && j === distanceY + 1){
clearInterval(interval);
mouseup.initMouseEvent("mouseup", true, true, window, 0, pageX + k, pageY + j, pageX + k, pageY + j, 0, 0, 0, 0, 0, null);
result[0].dispatchEvent(mouseup);
}
}, 100);
function iter(_x,_y){
var mousemove = document.createEvent("MouseEvent");
mousemove.initMouseEvent("mousemove", true, true, window, 0, 0, 0, pageX + _x, pageY + _y, 0, 0, 0, 0, 0, null);
result[0].dispatchEvent(mousemove);
}
新的dragAndDrop看起来像:
dragAndDrop: function (elem, x, y, id, className) {
var i = 0,
offsetX,
offsetY,
pos, offsetPos,
size;
this.sleep(2000);
offsetPos = this.getLocationInView(elem);
size = this.getSize(elem);
pageX = offsetPos.x + ~~(size.width / 2);
pageY = offsetPos.y + ~~(size.height / 2);
// No linebreaks
this.execute('var mousedown=document.createEvent("MouseEvent"),mouseup=document.createEvent("MouseEvent"),elem=document.getElementById("' + id + '"),result=[],elems=elem.getElementsByTagName("*"),k=0,j=0,i,interval;for(i in elems){if((" "+elems[i].className+" ").indexOf(" ' + className + ' ")>-1){result.push(elems[i]);}}mousedown.initMouseEvent("mousedown",true,true,window,0,0,0,' + pageX + ',' + pageY +',0,0,0,0,0,null);result[0].dispatchEvent(mousedown);interval=setInterval(function(){if(k!==' + x + '){k++;};if(j!==' + y +'){j++;};iter(k,j);if(k===' + x + '+1&&j===' + y + '+1){clearInterval(interval);mouseup.initMouseEvent("mouseup",true,true,window,0,' + pageX + '+k,' + pageY +'+j,' + pageX + '+k,' + pageY +'+j,0,0,0,0,0,null);result[0].dispatchEvent(mouseup);}},100);function iter(_x,_y){var mousemove=document.createEvent("MouseEvent");mousemove.initMouseEvent("mousemove",true,true,window,0,0,0,' + pageX + '+_x,' + pageY + '+_y,0,0,0,0,0,null);result[0].dispatchEvent(mousemove);}');
// Give the script time to execute and take a nap
this.sleep(x*100+3000);
}
答案 1 :(得分:0)
我发现解决方案的问题是在JavaScript中执行该功能。它不是一个完美的解决方案,但它适用于我们。
该脚本不适用于IE9,并且在Chrome / Firefox中引起了一些断言错误。这是奇怪的,但完全除了这一点;它在IE10和IE11中完美运行。最糟糕的情况我必须在IE10 / 11和IE9 / Firefox / Chrome中使用此解决方案。
我的拖放方法现在看起来像这样:
dragAndDrop: function (elem, x, y, id, className) {
var i = 0,
offsetX,
offsetY,
pos, offsetPos,
size;
this.sleep(2000);
offsetPos = this.getLocationInView(elem);
size = this.getSize(elem);
pageX = offsetPos.x + ~~(size.width / 2);
pageY = offsetPos.y + ~~(size.height / 2);
// No linebreaks
this.execute('var mousedown=document.createEvent("MouseEvent"),mouseup=document.createEvent("MouseEvent"),elem=document.getElementById("' + id + '"),result=[],elems=elem.getElementsByTagName("*"),k=0,i,interval;for(i in elems){if((" "+elems[i].className+" ").indexOf(" ' + className + ' ")>-1){result.push(elems[i]);}}mousedown.initMouseEvent("mousedown",true,true,window,0,0,0,' + pageX + ',' + pageY +',0,0,0,0,0,null);result[0].dispatchEvent(mousedown);interval=setInterval(function(){k++;iter(k);if(k===' + x + '+1){clearInterval(interval);mouseup.initMouseEvent("mouseup",true,true,window,0,' + pageX + '+k,' + pageY +',' + pageX + '+k,' + pageY +',0,0,0,0,0,null);result[0].dispatchEvent(mouseup);}},100);function iter(y){var mousemove=document.createEvent("MouseEvent");mousemove.initMouseEvent("mousemove",true,true,window,0,0,0,' + pageX + '+y,' + pageY +',0,0,0,0,0,null);result[0].dispatchEvent(mousemove);}');
// Give the script time to execute and take a nap
this.sleep(x*100+3000);
}
执行的JS中不能有换行符。清理它看起来像这样:
var mousedown = document.createEvent("MouseEvent"),
mouseup = document.createEvent("MouseEvent"),
elem = document.getElementById(id),
result = [],
elems = elem.getElementsByTagName("*"),
k = 0,
i, interval;
for(i in elems){
if((" " + elems[i].className + " ").indexOf(" " + className + " ") > -1){
result.push(elems[i]);
}
}
mousedown.initMouseEvent("mousedown", true, true, window, 0, 0, 0, clientX, clientY, 0, 0, 0, 0, 0, null);
result[0].dispatchEvent(mousedown);
interval = setInterval(function(){
k++;
iter(k);
if(k === distance + 1){
clearInterval(interval);
mouseup.initMouseEvent("mouseup", true, true, window, 0, screenX + k, screenY, clientX + k, clientY, 0, 0, 0, 0, 0, null);
result[0].dispatchEvent(mouseup);
}
}, 100);
function iter(y){
var mousemove = document.createEvent("MouseEvent");
mousemove.initMouseEvent("mousemove", true, true, window, 0, 0, 0, clientX + y, clientY, 0, 0, 0, 0, 0, null);
result[0].dispatchEvent(mousemove);
}
initMouseEvent()
的参数意味着您可以查看https://developer.mozilla.org/en-US/docs/Web/API/event.initMouseEvent
对于mouseup
,我必须设置screenX/Y
,并且我假设客户端始终是屏幕的完整大小。代码包含很多关于它运行环境的假设,但是为你的环境修改它不应该太难。
@JimEvans的评论最终促成了我的答案。