I need to know how can I do assertion in Selenium WebDriver. My situation is I have one edit, but on screen, but that edit button is present on some certain criteria.
So I want to check that if that button is present. It should be clicked on and it should open another child window and should perform certain actions. If that edit button element is not present on the screen, it should check the next condition which is the log off button in my keyword framework.
I have tried try and catch block and it is working fine.
Here is the code:
public void click_edit_childwindow2(String objectName) {
// Store the current window handle
String winHandleBefore = driver.getWindowHandle();
// Perform the click operation that opens new window
try{
WebElement elemnt = driver.findElement(By.xpath("//*[#id='main']/div[1]/table/tbody/tr[2]/td[6]/button"));
elemnt.click();
driver.findElement(By.xpath("//*[#id='main']/div[1]/table/tbody/tr[2]/td[6]/button")).click();
// Switch to new window opened
for(String winHandle : driver.getWindowHandles()){
driver.switchTo().window(winHandle);
}
// Perform the actions on new window
driver.findElement(By.xpath("//*[#id='myModal']/div/div/div[2]/form/div/div[10]/div/button[1]")).click();
// Close the new window, if that window no more required
//driver.close();
// Switch back to original browser (first window)
driver.switchTo().window(winHandleBefore);
// Continue with original browser (first window)
}
catch(Exception e){
driver.findElement((By.xpath("//*[#id='logoutForm']/ul/li[2]/a"))).click();
}
}
But I want to do it with assert. Though try and catch is not stopping the code, but after testing execution it is showing that the test case as failed. How can I do it with assert?
I am using keyword framework in which one is class is for keyword and another is for reading an Excel file.
A typical Selenium setup will include a test framework that is attached to your project.
There are several test frameworks to use, but here are the most popular for Java:
jUnit
TestNG
...
When you have a test framework attached to your project, you could then use asserts like:
Assert.assertTrue(driver.getWindowHandles().size().equals(2));
If the assertion fails, it will fail the test script. This is just one small example. I'd certainly do some research on how to use your test framework of choice. Selenium out-of-the-box is designed to be agnostic to what you use. Get creative.
Try the below code:
Boolean isPresent = driver.findElements(By.yourLocator).size() > 0
if(isPresent == true)
{
// Code
}
At first you need to check whether that button is displayed in the webpage. You can do that by this -
WebElement web = driver.findElement(By.xpath("//*[#id='myModal']/div/div/div[2]/form/div/div[10]/div/button[1]"));
boolean bool = web.isDisplayed();
Assert.assertEquals(true, bool); // Here it will match that if that button
// is present or not. If present it will
// continue execution from the next line
// or if it is not present the execution
// stops there and your test case fails.
You could avoid try-catch by:
List <WebElement> editButton = driver.findElements(By.xpath("//*[#id='main']/div[1]/table/tbody/tr[2]/td[6]/button"));
if(editButton.size() > 0)
{
editButton.get(0).click();
for(String winHandle : driver.getWindowHandles()){
driver.switchTo().window(winHandle);
}
// Perform the actions on new window
driver.findElement(By.xpath("//*[#id='myModal']/div/div/div[2]/form/div/div[10]/div/button[1]")).click();
// Close the new window, if that window no more required
//driver.close();
//Switch back to original browser (first window)
driver.switchTo().window(winHandleBefore);
}
else
{
driver.findElement((By.xpath("//*[#id='logoutForm']/ul/li[2]/a"))).click();
}
Related
I am using Selenium for Scrapping purpose for Job Website scrapping. I am ctrl+clicking on jobs to go to second page and scrape details, I somehow wish to keep track of where I clicked to which tab opened up (using a map).
But as soon as I ctrl+click an element, new tab opens and focus changes to that.
How do I get handle of the current focused tab in Selenium
I tried
webDriver.getWindowHandle()
But it returns me the handle for main tab that I ctrl+clicked an element from.
My Full Code
private void openAndMapJobTabs(WebElement jobList) {
List<WebElement> jobRowsSelector = jobList.findElements(By.tagName("article"));
for (WebElement jobRow : jobRowsSelector) {
try {
ctrlClickElement(jobRow);
Thread.sleep(4000);
//the next line is expected by me to give handle of current focused tab
System.out.println(webDriver.getWindowHandle()); // but this gives me handle of main tab
webElementToTabMapper.put(jobRow, webDriver.getWindowHandle());
webDriver.switchTo().window(websiteTabHandle);
} catch (Exception e) {
logger.info("Could Not Click Open Job Tab: "+e.getMessage());
}
}
}
UPDATE
Actually for me, I need to map elements to the tab they open, so order of tabs are important for me, so I purposely need the handle of current focused tab so I can map it with the element which opened that. But by iterating through all handels, I might mess up the order if any one of the webElement fails to open a new tab or if click is disabled on that.
Any help world be highly appreciated.
Also if there are faster and better tools for scrapping, please recommend.
You have to get the handles of those two tabs or windows, then you have to iterate and switch to the newly opened tab. Try the below code:
// This line will get the handles of the all the tabs or windows and store in a var with type 'Set'
Set<String> windowHandles = driver.getWindowHandles();
// Iterating through the Set - i.e., window handles and switch to the other tab
for (String handle : windowHandles) {
// System.out.println(handle);
driver.switchTo().window(handle);
System.out.println("Title: " + driver.getTitle());
}
If you have more than two tabs or windows, then put the above code the in a method, pass the window title which you want to switch as a parameter, and compare the title with each window title, once you switch to the expected window, break.
Goal: alert pop up. whether it's shown or not, I want it to continue. if it shows, have to select the checkbox, and hit continue. if not, ignore.
Blocker: if alert shows, it will handle the action and dialog will be closed. but when it's not, selenium hangs there without handling condition when it's not shown.
background: I use UFT before, maybe my logic could be wrong.
the pop up is application alert(not systems), so assumed "switch to(),accept()/dismiss() won't work. and I will add handle alert right after login and within the login method below.
Selenium framework background. : we use selenium maven framework, serenity BDD. object is set at the beginning of the page. and serenity.properties handle the time out default and so on.
Pop up objects (if it appears):
#FindBy(xpath = "//input[#id='notification-ack']")
private WebElement PcoNoticeChbx; //this is a check box, needs to be checked
#FindBy(xpath = "//button[contains(.,'Continue')]")
private WebElement PcoNoticeContinueBtn;//button to close the alert
*Log in method *
public void loginIntoExtApplication(String baseURL, String loginURL, String uId, String pwd, String extAppEnv)throws Exception {
gotoExtLoginPage(baseURL, loginURL);
enterLoginCredential(uId, pwd);
openAt("https://" + extAppEnv + ".programportaltest.hrsa.gov/sdms-
extranet/index.xhtml");
My Approaches:
//1.
if (PcoNoticeChbx!=null) {
PcoNoticeChbx.click();
PcoNoticeContinueBtn.click();
} else {
System.out.println("Dialog didn't display, no need any action");
}
//2. hanged here after login actions.
if(!getDriver().findElements(By.xpath("//*[#id='submit']")).isEmpty()){
PcoNoticeChbx.click();
PcoNoticeContinueBtn.click();
}
else {
System.out.println("Dialog didn't display, no need any action");
}
//3. added to watch doesn't work, it shows pending, below code failed too. I ran my Maven in Junit in debug mode. it used to work fine. but watch elements always show (pending)..
boolean isPresent = getDriver().findElements(By.id("noticebox")).size() >0
System.out.println("the diaolog exist= " + isPresent);
//4. even tried the try-catch method.
try{
PcoNoticeChbx.click();
PcoNoticeContinueBtn.click();
}catch (Exception e){
// Printing logs for my report
Log.error("Report Category button element is not found.");
// After doing my work, now i want to stop my test case
throw(e);
}
return;
}
//5. tried list webelemets:
List temp = webdriver.findElements(org.openqa.selenium.By.id("noticebox"));
if (temp.Count > 0 && temp[0].Displayed) {
// script to execute if element is found
} else {
// continue the test
}
//6. and below
if (!WebDriver.findElements(By.xpath("//*[#id='submit']")).isEmpty()==true);
{
//handle the dialog
}
else{
//continue
}
// 7.tried with a boolean value, but it also hangs on here first steps
boolean Nbox = PcoNoticeChbx.isDisplayed(); {
if (Nbox==false)
{
System.out.println("Dialog didn't display, no need any action");
}
else if (Nbox==true) {
PcoNoticeChbx.click() ;
PcoNoticeContinueBtn.click();
}
If this is like the popups that I've dealt with they work like this:
Customer comes to site and the site checks for the existence of a cookie. If that cookie exists, the popup is never launched (ideal state). If that cookie does NOT exist (typical state), after a specified period of time a popup appears.
Customer dismisses the popup and a cookie is created with an expiration time
Once that expiration time passes, the cookie expires and the popup will fire again
You need to do some investigation and find the cookie that is created once the popup is dismissed. Clear your cache, browse to the site, and note all the cookies that exist. Wait for the popup and dismiss it. Now find the cookie that was just created and examine it. This is the cookie you need to create. There are a lot of tutorials on creating cookies. It's pretty straightforward.
Once you learn how to create the cookie, you add it to your script as described below:
Navigate to some page on the domain that you know doesn't exist, e.g. www.domain.com/some404page. We do this because it won't trigger the popup countdown and we need to be on the domain to create the cookie.
Create the cookie
Do your normal test
No more popups.
Solution found for my case.
this maybe very easy. but takes some times for me to research. hopefully it will help you.
after use of many methods, for this javascripts confirmation alert. i have used below method. all of help of .CurrentlyVisible() method. because this one, and i guess only this one will give you result even when the element does not exist or null..
if (element(NoticeContinueBtn).**isCurrentlyVisible**()==true) {
PcoNoticeChbx.click();
PcoNoticeContinueBtn.click();
//else just continue
}
I am trying to automate a scenario where when I click on a link another tab opens with details.
Question 1 : Do I have to specifically set my focus to the 2nd tab or selenium automatically finds the element in the 2nd tab?
I am using the below code to set the focus to the 2nd tab :
String currentWindow = driver.getWindowHandle();
driver.switchTo().window(currentWindow);
Problem : I am getting an error that selenium is unable to find the specified element.
Could you guys suggest me what am I doing wrong, and the best way to switch to 2nd tab.
Actually, you are setting the focus on the first tab, not the second one. You need to do something like this
String currentWindow = driver.getWindowHandle();
// open the new tab here
for (String handle : driver.getWindowHandles()) {
if (!handle.equals(currentWindow)) {
driver.switchTo().window(handle);
}
}
And the answer to your question is yes, you have to tell the driver to set its focus on the new tab.
You can get all the window handles as handlers=driver. GetWindowHandles() which will return all the handler string. Then using index switch to the appropriate handle using driver.switchto().window(handlers[1])
I'm writing an automated test case for a web page. Here's my scenario.
I have to click and type on various web elements in an html form. But, sometimes while typing on a text field, an ajax loading image appears , fogging all elements i want to interact with. So, I'm using web-driver wait before clicking on the actual elements like below,
WebdriverWait innerwait=new WebDriverWait(driver,30);
innerwait.until(ExpectedConditions.elementToBeClickable(By.xpath(fieldID)));
driver.findelement(By.xpath(fieldID)).click();
But the wait function returns the element even if it is fogged by another image and is not clickable. But the click() throws an exception as
Element is not clickable at point (586.5, 278).
Other element would receive the click: <div>Loading image</div>
Do I have to check every time if the loading image appeared before interacting with any elements?.(I can't predict when the loading image will appear and fog all elements.)
Is there any efficient way to handle this?
Currently I'm using the following function to wait till the loading image disappears,
public void wait_for_ajax_loading() throws Exception
{
try{
Thread.sleep(2000);
if(selenium.isElementPresent("id=loadingPanel"))
while(selenium.isElementPresent("id=loadingPanel")&&selenium.isVisible("id=loadingPanel"))//wait till the loading screen disappears
{
Thread.sleep(2000);
System.out.println("Loading....");
}}
catch(Exception e){
Logger.logPrint("Exception in wait_for_ajax_loading() "+e);
Logger.failedReport(report, e);
driver.quit();
System.exit(0);
}
}
But I don't know exactly when to call the above function, calling it at a wrong time will fail. Is there any efficient way to check if an element is actually clickable? or the loading image is present?
Thanks..
Given the circumstances that you describe, you are forced to verify one of two conditions:
Is the element that you want to click clickable?
Is the reason that blocks the clicks still present?
Normally, if the WebDriver is able to find the element and it is visible, then it is clickable too. Knowing the posible reasons that might block it, I would rather choose to verify those reasons. Besides, it would be more expressive in the test code: you clearly see what you are waiting for, what you are checking before clicking the element, instead of checking the "clickability" with no visible reason for it. I think it gives one (who reads the test) a better understanding of what is (or could be) actually going on.
Try using this method to check that the loading image is not present:
// suppose this is your WebDriver instance
WebDriver yourDriver = new RemoteWebDriver(your_hub_url, your_desired_capabilities);
......
// elementId would be 'loadingPanel'
boolean isElementNotDisplayed(final String elementId, final int timeoutInSeconds) {
try {
ExpectedCondition condition = new ExpectedCondition<Boolean>() {
#Override
public Boolean apply(final WebDriver webDriver) {
WebElement element = webDriver.findElement(By.id(elementId));
return !element.isDisplayed();
}
};
Wait w = new WebDriverWait(yourDriver, timeoutInSeconds);
w.until(condition);
} catch (Exception ex) {
// if it gets here it is because the element is still displayed after timeoutInSeconds
// insert code most suitable for you
}
return true;
}
Perhaps you will have to adjust it a bit to your code (e.g. finding the element once when the page loads and only checking if it is displayed).
If you are not sure when exactly the loading image comes up (though I suppose you do), you should call this method before every click on elements that would become "unclickable" due to the loading image. If the loading image is present, the method will return true as soon as it disappears; if it doesn't disappear within 'timeoutInSeconds' amount of time, the method will do what you choose (e.g. throw an exception with specific message).
You could wrap it together like:
void clickSkippingLoadingPanel(final WebElement elementToClick) {
if (isElementNotDisplayed('loadingPanel', 10)) {
elementToClick.click();
}
}
Hope it helps.
I am trying to automate test scripts in selenium. Scenario of the activity to be automated:
It should open automatically a page URL first.
Click on the left navigation.
The page then gets populated with a drop-down, it should select a fixed value from the drop down(say = company)
Click a create button at the bottom of the page.
In my case the code is working until the population of drop down but after that the code fails to click the create button as the next action. The error message which I got in the command console is as follows:
Element name = create not found on session c48334c30....96ed
Here is my code:
public class testing {
Selenium selenium = null;
#Test
public void submit() throws Exception {
selenium = new DefaultSelenium("localhost", 4545, "*firefox", "URL");
selenium.start();
selenium.open("URL");
selenium.windowFocus();
selenium.windowMaximize();
selenium.click("link=Work with company names");
selenium.waitForPageToLoad("30000");
selenium.select("//select[#name='company_id']", "label=company");
selenium.waitForPageToLoad("3000");
selenium.click("name = create");
}
}
Please provide me your suggestions to solve this, since I am not able to understand why it is failing to click the button named "create". I also tried to use selenium.click("xpath=//button[matches(#id,'.*create')]"); instead of selenium.click("name = create") but it didnt work as well.
Please let me know what can be the issue for this error and how can I resolve it? Thanks.
1) it would be good if you provide html code of your page.
2) before clicking any element (which is loaded after some action) I recommend using WaitForElementPresent (from Selenium IDE), i.e. be sure that element really exists. Selenium works rather fast and it may try clicking the element before the element actually loaded.
You may use something like this:
public bool waitForElementPresent(string Xpath) {
bool present = false;
for (int second = 0; ; second++) {
if (second >= 5) {
break;
}
if (IsElementPresent(Xpath)) {
present = true;
break;
}
Thread.Sleep(1000);
}
return present;
}
try with this
selenium.click("//*[contains(#name,'create')]");
As you are using: selenium.waitForPageToLoad("3000");
Selenium is waiting for page to load. You want to add a pause, though thread.sleep isn't the best practise it can still work for you.