Firefox Selenium test freezes sometimes - firefox

I am using Selenium 2.46 and Firefox 31. Whenever my test gets to a point that an web-element does not exist (or an exception is thrown) my test freezes, but it does not happen when I use Chrome. Just to let you know I have already used different versions of selenium-java and Firefox. Please find the code below:
List<WebElement> divs = driverChrome.findElements(By.tagName("div"));
int i = 0;
while (true) {
boolean breakIt = true;
System.out
.println("Waiting for map to load completely, thanks for your patience.");
for (WebElement weDiv : divs) {
try {
if (weDiv.getText().equals("Loading")) {
Thread.sleep(2000);
breakIt = false;
break;
}
} catch (Exception e) {
}
}
if (breakIt) {
break;
}
driverChrome.manage().timeouts()
.implicitlyWait(5, TimeUnit.SECONDS);
divs = driverChrome.findElements(By.tagName("div"));
}
I am using this code to wait till a map is completely loaded

The most probable reason for your test to freeze is the while(true) loop. If the text "Loading" does not show up, there still can be an (invisible) element with that text.
Anyway, I would never use a wait mechanism without timeout. And I would always try to use methods provided by the framework.
WebDriver offers explicit and implicit wait mechanisms. This one-liner could replace your whole listing (waits for up to 60s, polling every two seconds):
new WebDriverWait(driver, 60000L, 2000L).until(ExpectedConditions.invisibilityOfElementWithText(By.tagName("div"), "Loading"));
Hope it helps. If not, check out other methods of ExpectedConditions or implement your own ExpectedCondition.

Related

Running a non-blocking, high-performance activity in nativescript/javascript

This question is about running a non-blocking, high-performance activity in nativescript that is needed for the simple task of reading and saving raw audio from the microphone by directly accessing the hardware through the native Android API. I believe I have brought the nativescript framework to the edge of its capabilities, and I need experts' help.
I'm building a WAV audio recorder in Nativescript Android. Native implementation is described here (relevant code below).
In short, this can be done by reading audio steam from an android.media.AudioRecord buffer, and then writing the buffer to a file in a separate thread, as described:
Native Android implementation
startRecording() is triggered by a button press, and starts a new Thread that runs writeAudioDataToFile():
private void startRecording() {
// ... init Recorder
recorder.startRecording();
isRecording = true;
recordingThread = new Thread(new Runnable() {
#Override
public void run() {
writeAudioDataToFile();
}
}, "AudioRecorder Thread");
recordingThread.start();
}
Recording is stopped by setting isRecording to false (stopRecording() is triggered by a button press):
private void stopRecording() {
isRecording = false;
recorder.stop();
recorder.release();
recordingThread = null;
}
Reading and saving buffer is stopped if isRecording = false:
private void writeAudioDataToFile() {
// ... init file and buffer
ByteArrayOutputStream recData = new ByteArrayOutputStream();
DataOutputStream dos = new DataOutputStream(recData);
int read = 0;
while(isRecording) {
read = recorder.read(data, 0, bufferSize);
for(int i = 0; i < bufferReadResult; i++) {
dos.writeShort(buffer[i]);
}
}
}
My Nativescript javascript implementation:
I wrote a nativescript typescript code that does the same as the native Android code above. The problem #1 I faced was that I can't run while(isRecording) because the javascript thread would be busy running inside the while loop, and would never be able to catch button clicks to run stopRecording().
I tried to solve problem #1 by using setInterval for asynchronous execution, like this:
startRecording() is triggered by a button press, and sets a time interval of 10ms that executes writeAudioDataToFile():
startRecording() {
this.audioRecord.startRecording();
this.audioBufferSavingTimer = setInterval(() => this.writeAudioDataToFile(), 10);
}
writeAudioDataToFile() callbacks are queued up every 10ms:
writeAudioDataToFile() {
let bufferReadResult = this.audioRecord.read(
this.buffer,
0,
this.minBufferSize / 4
);
for (let i = 0; i < bufferReadResult; i++) {
dos.writeShort(buffer[i]);
}
}
Recording is stopped by clearing the time interval (stopRecording() is triggered by button press):
stopRecording() {
clearInterval(this.audioBufferSavingTimer);
this.audioRecord.stop();
this.audioRecord.release();
}
Problem #2: While this works well, in many cases it makes the UI freeze for 1-10 seconds (for example after clicking a button to stop recording).
I tried to change the time interval that executes writeAudioDataToFile() from 10ms to 0ms and up to 1000ms (while having a very big buffer), but then the UI freezes were longer and, and I experienced loss in the saved data (buffered data that was not saved to the file).
I tried to offload this operation to a separate Thread by using a nativescript worker thread as described here, where startRecording() and stopRecording() are called by messages sent to the thread like this:
global.onmessage = function(msg) {
if (msg.data === 'startRecording') {
startRecording();
} else if (msg.data === 'stopRecording') {
stopRecording();
}
}
This solved the UI problem, but created problem #3: The recorder stop was not executed on time (i.e. recording stops 10 to 50 seconds after the 'stopRecording' msg.data is received by the worker thread). I tried to use different time intervals in the setInterval inside the worker thread (0ms to 1000ms) but that didn't solve the problem and even made stopRecording() be executed with greater delays.
Does anyone have an idea of how to perform such a non-blocking high-performance recording activity in nativescript/javascript?
Is there a better approach to solve problem #1 (javascript asynchronous execution) that I described above?
Thanks
I would keep the complete Java implementation in actual Java, you can do this by creating a java file in your plugin folder:
platforms/android/java, so maybe something like:
platforms/android/java/org/nativescript/AudioRecord.java
In there you can do everything threaded, so you won't be troubled by the UI being blocked. You can call the Java methods directly from NativeScript for starting and stopping the recording. When you build your project, the Java file will automatically be compiled and included.
You can generate typings from your Java class by grabbing classes.jar from the generated .aar file of your plugin ({plugin_name}.aar) and generate type declarations for it: https://docs.nativescript.org/core-concepts/android-runtime/metadata/generating-typescript-declarations
This way you have all the method/class/type information available in your editor.

Selenium waitForCondition

I am doing Selenium testing for the first time. On the homepage, I call some AJAX, and i want Selenium to wait for the element to load finish. I not sure it works, but i just type selenium and the waitForCondition are able to choose.
I not matter what I choose it always return "false". I do not now if the waitForCondition even work?
How can I test if it works?
And what am I doing wrong in this codes?
selenium.waitForCondition("//input[#name='Report'", "3000");
selenium.waitForCondition("//*[#id='MyTable']", "3000");
selenium.waitForCondition("css=.someClass2", "3000");
If I implement by own class - it return "true"
private boolean isElementPresent(By by) {
try {
driver.findElement(by);
return true;
} catch (NoSuchElementException e) {
return false;
}
}
isElementPresent(By.xpath("//*[#id='MyTable']")) - return "true"
waitForCondition is for Javascript calls only, not for waiting for elements to load.
What you have in isElementPresent is fine. I would combine it with explicit waits to be a bit more accurate about when an element is actually loaded and present on the screen:
http://seleniumhq.org/docs/04_webdriver_advanced.html
C#
You can do it like this:
First of all you can set timeout value for the condition.
Then you can use the condition.
var Wait = new WebDriverWait(GlobalDriver, TimeSpan.FromMinutes(1));
Wait.Until(ExpectedConditions.PresenceOfAllElementsLocatedBy(By.XPath("xPath"))));
OR
Wait.Until(driver => driver.FindElement(By.XPath("xPath")));
Thats all.
You can do it like this :
selenium.waitForCondition("selenium.isElementPresent(\"//input[#name='Report']\")", "30000");
This will wait for the element to be loaded till 30 seconds.
Hope this works for you
new WebDriverWait(driver, 30).until(new ExpectedCondition<Boolean>() {
public Boolean apply(WebDriver driver) {
JavascriptExecutor js = (JavascriptExecutor) driver;
return (Boolean) js.executeScript("return jQuery.active == 0");
}
});
This will check if the jQuery library has any active AJAX requests for 30 seconds.
Aaran referred you to the correct documentation for Selenium WebDriver waits.
You can see that they also write about ExpectedConditions class. This contains several helpful implementation of ExpectedCondition classes, such at the "is element present one", which is ExpectedConditions.presenceOfElementLocated .
Here is an example of using it:
WebDriver driver = new ChromeDriver();
driver.get("http://www.degraeve.com/reference/simple-ajax-example.php");
driver.findElement(By.name("word")).sendKeys("bird is the word");;
driver.findElement(By.cssSelector("input[type='button']")).click();
WebDriverWait driverWait = new WebDriverWait(driver, 10);
WebElement dynamicElement = driverWait.until(ExpectedConditions.presenceOfElementLocated(By.cssSelector("#result p")));
System.out.println(dynamicElement.getText());
If you find it too verbose, why won't you just refactor it and extract a function which will accept the element locator and the webdriver, and returns you the element?
DriverWait.until() accepting an ExpectedCondition instance is like a way of passing a predicate function, just doing it through a class, or in the documentation example an anonymous nested class, since under Java you can't send a function.
The ExpectedCondition "function" you pass also returns a value, which can be useful in case you're waiting for a condition on some element (or some other value from the WebDriver), so returning it will save you an extra call.
Try this once:
await().atMost(10, SECONDS).until(() -> driver.findElements(By.id("elementId")).size() >1);

Selenium test 'Unable to locate element' in IE

I have created an automated test that logs a user in to a site and performs certain operations. The test first runs in Firefox, Chrome and then IE. It runs perfectly in Firefox, closes the browser and then performs the test in Chrome and again closes the browser. When the exact same test opens the URL in IE it says it is unable to locate the element 'UserName' for the login process.
I have a wait function which I tried to extend in case it was a problem with the page rendering but this didn't work. When using the dev tools and searching for the element it finds it no problem so I am confused as to how it fails in the test.
Does anyone know what could cause this in IE?
The HTML for the text field looks like this...
The Selenium code that works in FF and Chrome but not IE is:
private Results _Test_Login(IWebDriver driver)
{
Results rt;
driver.Navigate().GoToUrl("MyURL");
driver.FindElement(By.Id("UserName")).Click();
TextboxOperation type = new TextboxOperation("UserName", driver, "Success", EnumSearchType.ById);
OperationExecutor.PerformOperations(type);
rt = new Results(driver.Url, driver.PageSource, "Existing Users");
return rt;
}
[TestMethod]
public void Test_Login()
{
List<IWebDriver> drivers = new List<IWebDriver>() { firefoxDriver, chromeDriver, ieDriver };
foreach (IWebDriver driver in drivers)
{
Results results = _Test_Login(driver);
if (results.Exception != null)
{
throw results.Exception;
}
Assert.IsFalse(results.ErrorState);
}
}
Sometimes you need to put a pause just before trying to locate an element because the page or frame is not yet ready. Or, if you don't want to have a pause, you can use a time-limited while loop wrapping a try-catch that handles error conditions and retries the find if it fails.)

Watin not recognising confirmation dialog OK button

I recently started a new testing job and my predecessor ran an automation suite using watin, which I've had no previous experience with so I'm sorry if I'm not able to give you the relevant information
When I run the suite it (against IE 8.0.7601.17514) seems to get stuck when ever there is a confirmation dialog and the next step is to press ok
//Enter invalid data
var confirmDialog = new ConfirmDialogHandler();
IE.DialogWatcher.Add(confirmDialog);
using (new UseDialogOnce(IE.DialogWatcher, confirmDialog))
{
//Click to reset data entry
IE.Page<DataEntryPage>().ResetVoucherButton.ClickNoWait();
confirmDialog.WaitUntilExists(40000);
confirmDialog.OKButton.Click();
WaitForPostBackToComplete.WaitForAsyncPostBackToComplete(IE);
}
It just hangs there and waits for the time out period to pass.
I thought the problem was with my IEStaticInstanceHelper.cs file but it seems to be correct
using System.Threading;
using WatiN.Core;
namespace WatiN
{
public class IEStaticInstanceHelper
{
private IE _ie;
private int _ieThread;
private string _ieHwnd;
public IE IE
{
get
{
var currentThreadId = GetCurrentThreadId();
if (currentThreadId != _ieThread)
{
_ie = IE.AttachTo<IE>(Find.By("hwnd", _ieHwnd));
_ieThread = currentThreadId;
}
return _ie;
}
set
{
_ie = value;
_ieHwnd = _ie.hWnd.ToString();
_ieThread = GetCurrentThreadId();
}
}
private int GetCurrentThreadId()
{
return Thread.CurrentThread.GetHashCode();
}
}
}
I've recently rebuilt my computer (well my sysadmin did) and this wasn't an issue before it was rebuilt, but I can't think what may have changed
Any help would be greatly appreciated
Edit
I didn't actually have to change the code, I just had to update my Watin Version as it couldn't handle what ever differences there were between earlier IE 8 dialog boxes and newer ones.
I had a similar problem with IE 9.
I used the following to simulate the shortcut keys on the dialogue
using (browser)
{
SendKeys.SendWait("+(%S)");
}
Send Keys = http://msdn.microsoft.com/en-us/library/system.windows.forms.sendkeys.aspx
Does this help?

FileReference: Loading a Windows-locked file

I'm using Flex in Flash Player 10 on Windows, using FileReference to load a file into memory, as below.
My issue is that when a file is locked by Windows, my FileReference is not giving me any feedback that the file is inaccessible--it simply never dispatches any events after my calling load().
Does anyone have insight into how to tell that Flash Player is unable to open the file?
var fileReference:FileReference = new FileReference();
private function onClick():void {
fileReference = new FileReference();
fileReference.addEventListener(Event.SELECT, onSelect);
fileReference.addEventListener(Event.COMPLETE, onComplete);
fileReference.addEventListener(Event.CANCEL, onOther);
fileReference.addEventListener(IOErrorEvent.IO_ERROR, onOther);
fileReference.addEventListener(ProgressEvent.PROGRESS, onOther);
fileReference.addEventListener(SecurityErrorEvent.SECURITY_ERROR, onOther);
// I've tried adding all of the other declared events
// for FileReference here as well
fileReference.browse();
}
private function onSelect(event:Event):void {
trace(fileReference.name);
try {
fileReference.load();
} catch (e:Error) {
trace(e);
}
}
private function onComplete(event:Event):void {
trace(fileReference.data.length);
}
private function onOther(event:Event):void {
trace("other:" + event.toString());
}
A possible (dirty) workaround might be to wait for -let say- 10 seconds, and suppose that the file isn't available if no event has triggered then.
Using a setTimeout (and clearing it with clearTimeout in your COMPLETE and *_ERROR events handlers) might do the trick.
I'll be glad if someone could come up with a nicer solution, though.
EDIT: Of course you might want to listen to HTTP_STATUS event (waiting for a 202 answer - if I understood this documentation correctly) rather than waiting for COMPLETE or *_ERROR.

Resources