How to select option from dynamic dropdown - selenium

I got a problem with choosing an option from a dynamic dropdown.
I've already tried several options:
- by choosing from the select list (in the 'target' i tried (label, index, value))
- by choosing from the div id="id_language_chzn (in the 'target' i tried (label, index, value))
Nothing supposed to work !
Code is here: http://pastebin.com/v3Q7NDGs
Regards if could help me on this,
Szymon

Use a little delay after the page load, very likely the JS did not initialize completely.
http://release.seleniumhq.org/selenium-core/1.0/reference.html#pause
Also for this Chosen problem, click on the dynamically created element itself, do not use the html form element.

I would do it like this:
driver.manage().timeouts().implicitlyWait(10, TimeUnit.SECONDS);
By ddLocator = By.xpath(".//select[1]");
By items = By.xpath(".//option");
ByChained comboBox1 = new ByChained( ".//select[1]", ".//option" );
List<WebElement> allOptions = driver.getElements( comboBox1 );
for ( WebElement we : allOptions ) {
// do something here
}

Ok, it occurred that selenium IDE had some problems with taking out the selected option. I have used webdriver and it helped.
Here is the code:
driver.findElement(By.cssSelector("a.class > span")).click();
driver.findElement(By.id("id_name[1]")).click();

Related

selenium element.click() not working (doesn't click)

String selector = ".rmcAlertDialog .buttons :first-child";
RemoteWebElement selection = (RemoteWebElement) driver.findElement(By.cssSelector(selector));
WebDriverWait wait = new WebDriverWait(driver, 60);
WebElement element = wait.until(ExpectedConditions.elementToBeClickable(selection));
if (element == selection) selection.click();
But the element in question (a button) is not responding to the click.
If I click the button manually it works so its not the web page at fault, but the automation.
I have verified the button is there by comparing it's text content.
updated for clarification
This code works (or worked) for most buttons. The code is from a script interpreter which is parsing:-
select ".rmcAlertDialog .buttons :first-child" click
This code was working prior to more recent versions of chrome/selenium/chromedriver.
The code now doesn't work for some buttons.
selection.click() IS being called (verified in a debugger), as element will always equal selection, it just is not working.
.buttons is the class name of the container div for the button(s)
The selector is not directing to the element with button class. You have a space between .button and :first-child in the selector. Remove the space. The given selector is searching for a child element of the tag with button class. But I'm assuming you are trying to click on the first element with button class not the child node of the button class element.
Use this:
String selector = ".rmcAlertDialog .buttons:first-child";
I think the main reason it's failing is because your if statement will never be true. I've never done any comparisons like this but you can simplify your code significantly and still get the desired effect.
A few suggestions:
Don't define locators as Strings, define them as Bys. The By class is defined for just such a task and makes using and passing them around MUCH easier.
String selector = ".rmcAlertDialog .buttons:first-child";
would turn into
By locator = By.cssSelector(".rmcAlertDialog .buttons:first-child");
Note the correction that S Ahmed pointed out in his answer.
You don't need to find the element to wait for it to be clickable. There is an overload that takes a By locator, use that instead.
RemoteWebElement selection = (RemoteWebElement) driver.findElement(By.cssSelector(selector));
WebDriverWait wait = new WebDriverWait(driver, 60);
WebElement element = wait.until(ExpectedConditions.elementToBeClickable(selection));
becomes
WebElement element = new WebDriverWait(driver, 60).until(ExpectedConditions.elementToBeClickable(locator));
Skip the RemoteWebElement and WebElement comparison. I don't think this will work and there's no need for it anyway. Your locator will locate the same element consistently.
So your final code should look something like
By locator = By.cssSelector(".rmcAlertDialog .buttons:first-child");
new WebDriverWait(driver, 60).until(ExpectedConditions.elementToBeClickable(locator)).click();

<Select> Tag is not working for selecting value in dropdown

I am facing an issue where dropdown has tag. but still I am unable to select value in dropdown and it is throwing exception. I am able to get dropdown values but unable to select
Here is complete details
URL : https://semantic-ui.com/modules/dropdown.html
Testcase: Select multiple values in Skill dropdown.( Find attachment for exact field on web page.
WebDriver driver = new FirefoxDriver();
driver.get("https://semantic-ui.com/modules/dropdown.html");
driver.manage().timeouts().implicitlyWait(10L, TimeUnit.SECONDS);
WebElement Dropdown = driver.findElement(By.name("skills"));
Select sel = new Select(driver.findElement(By.name("skills")));
List<WebElement> Options = sel.getOptions();
System.out.println(Options.size());
for(int i=0;i<Options.size()-1;i++) {
driver.findElement(By.xpath("//*[#id=\"example\"]/div[4]/div[1]/div[2]/div[4]/div[1]/div[8]/div")).click();
System.out.println(Options.get(i).getAttribute("value"));
if(Options.get(i).getAttribute("value").equalsIgnoreCase("angular")||Options.get(i).getAttribute("value").equalsIgnoreCase("Graphic Design")||Options.get(i).getAttribute("value").equalsIgnoreCase("HTML")) {
Thread.sleep(6000);
sel.selectByIndex(i);
}
}
}
Exception:
Exception in thread "main" org.openqa.selenium.ElementNotInteractableException:
Please help to suggest for this.
Your drop down is a simulated drop down by css, not a HTML native drop down: Select. So you can not operate it as native drop down.
After look into the HTML code of your dropdown, there is an embed native drop down, but it's always invisible no matter you expand options or not. Selenium can't operate on invisible element(But you can read value/attribute from it), that's why the exception you met.
Actually all options come from the div class="menu", so you should click the option from div class="menu" as below screenshot show:
Code to resolve your problem:
// click arrow down to expand options
driver.findElement(By.cssSelector("select[name='skills'] + i")).click();
// choose option: Angular
driver.findElement(By.xpath("//div[contains(#class, 'multiple')][select[#name='skills']]//div[.='Angular']"));

How to select the checkbox in the list of checkboxes ONE-BY-ONE in selenium?

I need to select all the checkboxes from here one-by-one after every 3 second. I tried couple of xpaths with list,none of them have worked
Tried xpaths:
//div/div[#class='filters-list sdCheckbox ']
Using input and type. But none of them worked. Can you please help me out?
Reference website: https://www.snapdeal.com/products/storage-devices?sort=plrty
->Capacity at the left hand corner
By.xpath("//a[#class='filter-name']") this one listed out all the filters of page.
The xPath "//div[#data-name='Capacity_s']/div[#class='filters-list sdCheckbox ']/input" will fetch you the list of all input elements that you need to check.
There is a container DIV that holds all the filters of a certain type, e.g. Brand, Capacity, etc. The one for Brand is shown below.
<div class="filter-inner " data-name="Brand">
Under that container, all the LABEL tags are what you need to click to check the boxes. So, we can craft a CSS selector using the grouping as a filter to reach only the checkboxes we want.
"div[data-name='Brand'] label"
Since this is something I assume you will reuse, I would write this as a function.
public static void CheckFilters(String filterGroup)
{
WebDriverWait wait = new WebDriverWait(driver, 10);
List<WebElement> filters = driver.findElements(By.cssSelector("div[data-name='" + filterGroup + "'] label"));
// System.out.println(filters.size()); // for debugging
for (int i = 0; i < filters.size(); i++)
{
filters.get(i).click();
// wait for the two overlays to disappear
wait.until(ExpectedConditions.invisibilityOfElementLocated(By.cssSelector("div.searcharea-overlay")));
wait.until(ExpectedConditions.presenceOfElementLocated(By.cssSelector("div.filterLoader.hidden")));
// reload the element list after the refresh so you don't get StaleElementExceptions
filters = driver.findElements(By.cssSelector("div[data-name='" + filterGroup + "'] label"));
}
}
and you would call it like
driver.get("https://www.snapdeal.com/products/storage-devices?sort=plrty");
CheckFilters("Brand");

How to edit element in table with selenium?

I'm trying to edit value of element that placed it the table on
this page.
I'm using this code:
driver.manage().timeouts().implicitlyWait(10, TimeUnit.SECONDS);
driver.get("http://samples.gwtproject.org/samples/Showcase/Showcase.html#!CwCellTable");
WebElement firstName = driver.findElement(By.xpath("//*[#id=\"gwt-debug-contentPanel\"]/div[2]/div/div[2]/div/div[3]/div/div/div/table/tbody/tr[1]/td/table/tbody[1]/tr[1]/td[2]/div"));
firstName.click();
firstName.clear();
firstName.sendKeys("test");
It says:
"Element must be user-editable in order to clear it."
How i can edit this element?
Also i have troubles with "Category" field on this page. I'm trying to select each of them successively. Doing this with:
WebElement category = driver.findElement(By.xpath("//*[#id=\"gwt-debug-contentPanel\"]/div[2]/div/div[2]/div/div[3]/div/div/div/table/tbody/tr[1]/td/table/tbody[1]/tr[1]/td[4]/div/select"));
category.sendKeys("Businesses");
category.sendKeys("Friends");
category.sendKeys("Coworkers");
category.sendKeys("Businesses");
category.sendKeys("Family");
I tried to make category.sendKeys(""); once and it works well.
But throws this: "stale element reference: element is not attached to the page document" when i get a lot. How i can change this elements one by one?
This is kinda a strange one. The DOM keeps changing which makes it harder to see what's going on so that you can do the right thing to make it work. You have to click one element which changes the DOM and inserts an INPUT which is what you need to .sendKeys() to. I have tested the code below and it works.
I like to create functions for things like this so that they are reusable. This function changes the first name. rowIndex is the row of the table you want to change and firstName is the desired first name. You have to wait for the table to finish loading because it loads dynamically after the page is loaded.
public static void setFirstName(int rowIndex, String firstName)
{
WebElement firstNameElement = new WebDriverWait(driver, 10)
.until(ExpectedConditions.visibilityOfAllElementsLocatedBy(By.cssSelector("tr[__gwt_row='" + rowIndex + "'] > td > div")))
.get(1);
firstNameElement.click();
firstNameElement.findElement(By.tagName("input")).sendKeys(firstName + "\n");
}
To change the first name of the first row to "FirstName" you would call it like,
setFirstName(0, "FirstName");

Selenium Xpath Not Matching Items

I am trying to use Selenium's Xpath ability to be able to find an set of elements. I have used FirePath on FireFox to create and test the Xpath that I have come up with and that is working just fine but when I use the Xpath in my c# test with Selenium nothing is returned.
var MiElements = this._driver.FindElements(By.XPath("//div[#class='context-menu-item' and descendant::div[text()='Action Selected Jobs']]"));
and the Html looks like this:-
Can Anyone please point me right as everything that I have read the web says to me that this Xpath is correct.
Thanking you all in-advance.
Please post the actual HTML, so we can simply "drop it in" into a HTML file and try it ourselves but I noticed that there is a trailing space at the end of the class name:
<div title="Actions Selected Jobs." class="context-menu-item " .....
So force XPath to strip the trailing spaces first:
var MiElements = this._driver.FindElements(By.XPath("//div[normalize-space(#class)='context-menu-item' and descendant::div[text()='Action Selected Jobs']]"));
Perhaps you don't take into consideration the time that the elements need to load and you look for them when they aren't yet "searchable". UPDATE I skipped examples regarding this issue. See Slanec's comment.
Anyway, Selenium recommends to avoid searching by xpath whenever it is possible, because of being slower and more "fragile".
You could find your element like this:
//see the method code below
WebElement div = findDivByTitle("Action Selected Jobs");
//example of searching for one (first found) element
if (div != null) {
WebElement myElement = div.findElement(By.className("context-menu-item"));
}
......
//example of searching for all the elements
if (div != null) {
WebElement myElement = div.findElements(By.className("context-menu-item-inner"));
}
//try to wrap the code above in convenient method/s with expressive names
//and separate it from test code
......
WebElement findDivByTitle(final String divTitle) {
List<WebElement> foundDivs = this._driver.findElements(By.tagName("div"));
for (WebElement div : foundDivs) {
if (element.getAttribute("title").equals(divTitle)) {
return element;
}
}
return null;
}
This is approximate code (based on your explanation), you should adapt it better to your purposes. Again, remember to take the load time into account and to separate your utility code from the test code.
Hope it helps.