How to read ol and li elements dynamically without using xpath - selenium

I'm new to selenium and Below is my HTML and i want to display sons of Dhritrashtra and grandsons of pandu (without using xpath). I've tried methods like getText and getLinkText but it's not working for me. Please help.Thanks.
Kuru
Shantanu
Vichitravirya
Dhritrashtra
DuryodhanaDushasanaDussalanJalagandhaSamaSahaVindhaAnuvindhaDurmukhaChitrasenaDurdarshaDurmarshaDussahaDurmadaVikarnaDushkarnaDurdharaVivinsatiDurmarshanaDurvishahaDurvimochanaDushpradharshaDurjayaJaitraBhurivalaRaviJayatsenaSujataSrutavanSrutantaJayatChitraUpachitraCharuchitraChitrakshaSarasanaChitrayudhaChitravarmanSuvarmaSudarsanaDhanurgrahaVivitsuSubaahuNandaUpanandaKrathaVatavegaNishaginKavashinPaasiVikataSomaSuvarchasasDhanurdharaAyobaahuMahabaahuChithraamgaChithrakundalaBheemarathaBheemavegaBheemabelaUgraayudhaKundhaadharaVrindaarakaDridhavarmaDridhakshathraDridhasandhaJaraasandhaSathyasandhaSadaasuvaakUgrasravasUgrasenaSenaanyAparaajithaKundhasaaiDridhahasthaSuhasthaSuvarchaAadithyakethuUgrasaaiKavachyKradhanaKundhyBheemavikraAlolupaAbhayaDhridhakarmaavuDhridharathaasrayaAnaadhrushyaKundhabhedyViraavyChithrakundalaPradhamaAmapramaadhyDeerkharomaSuveeryavaanDheerkhabaahuKaanchanadhwajaKundhaasyVirajas
Pandu
Yudhishtir
Prativindhya
Bhim
Sutasoma
Ghatotkch
Arjun
Srutakirti
Babhruvahan
Nakul
Satanika
Sahadev
Shrutkarma

Here is the solution for your query:
It's not mandatory to use xpath always. As per the Selenium Documentation & standards, consider the following attributes in sequence: id, name, css, linktext, xpath. If still unable to detect the element try for css/xpath with multiple attributes like class, src, etc.
Once you can identify the element then only you will be able to retrieve the properties of the element like getText() & getLinkText().
Most important, you have provided the copy of the text from the website. It's impossible to identify an an element from the website text to help you out. You need to provide some relevant part of the HTML DOM inorder to enable us to help you. You can look into the PageSource of any webpage to know the properties (id/name/css/xpath) of the elements. For that, while you are on a webpage, you can right-click and select "View Page Source". For Mozilla Firefox you can download & install extensions ​like Firepath & Firebug to know the properties of an element.
Finally you have to write some code either in Java/Python/C# to open a browser through Selenium of your choice, open a website and perform certain actions with different elements present on the webpage.
Let me know if this answers your question.

I don't know the exact syntax your html has but You can use cssSelector as below per my assumptions of your html elements for both your queries:
1) ul ol ol ol li:nth-child(n) - n= element index
2) ul ol ol ol:nth-child(2) li:nth-child(n) li:nth-child(1) - n= element index

Related

Selenium C# - I'm unable to find an element on this page using any of the locators

This was just a random script I made to complete a quiz but I can't seem to access the final element. I want to select the element, click the element and then send some text to the element.
I have tried to access the input box by class name, CssSelector and by XPath.
The website is https://www.16personalities.com/free-personality-test
Here are the XPaths I have tried:
//*[contains(#class, 'email-wrapper')]
//div[contains(#placeholder, 'your#email.com')]
//div[#class="row request-info-wrapper"]
//*[#id='request - email']"
Any help is greatly appreciated as I'm new to the framework and would very much like to know what I'm not understanding about locators! Thank you!
EDIT:
I can't seem to target this element or any of its children:
You have selected wrong tag DIV.Try this following Xpath. All should work.
"//input[#id='request-email']"
Or
"//input[#name='email']"
Or
"//input[#placeholder='your#email.com']"
Your field has a (presently) unique ID of "request-email".
Thus you can simply use, as a CSS selector,
('#request-email')
Then, in you can simply tell Selenium to hit ENTER to save your data. Let me know if you need help doing that.

How to write a XPath for the text one4

I want to use XPath to locate a link behind a text.
I want to use XPath to locate a link behind a text. For example, locate "one4" by "what10". You can only use the text message "what10", but you can't use it in any other way, because the information on this page will change. I want to get is the "one4" link node.
<body>
<p>
so
<br>what1 one
<br>what2two
<br>what11one4
<br>what3three
<br>what4one1
<br>what5two2
<br>what6three3
<br>what7one3
<br>what8two3
<br>what9three3
<br>what10one4
<br>just return
<br></p>
</body>
For some special reasons, what I want to pass is that the text of what10 is positioned to one4.
Please help me.
You can use below line
WebElement loginLink = driver.findElement(By.linkText("one4"));
Selenium doesn't supports xpath-2.0 but uses xpath-1.0
The element which you are trying to refer i.e. which contains the text what10 is a Text Node and Selenium can't use it as a reference. So finding the node with text as one4 with reference to the text what10 won't be possible. As an alternative if the desired node is always the last but one node you can use the following solution:
xpath:
driver.findElement(By.xpath("//body/p//a[position()=last()-1]"));
Update
As per #MosheSlavin counter question here is the snapshot to demonstrate that the XPath works perfecto:

How to locate ALL html tags in Selenium with Python

My code:
import stuff...
driver = webdriver.Firefox(executable_path='C:\\...\\geckodriver.exe')
driver.get('https://webpage.com/')
elems = driver.find_elements_by_CLASS_ID_TEXT_XPATH_WHATEVER_ELSE_BADLY_DOCUMENTED_STUFF
How do I get a list of ALL CSS Selectors, such as Class, ID, p, span, input, button and all other elements from the webpage.com?
If you know a link to a brief and clear info resource with plentiful of examples explaining find_elements_by or Locating Elements in advanced detail, please share here.
edit:
ok, a bit more specific question then, how could I get the list of ALL Class Selectors from a webpage into elems?
elems = driver.find_elements_by_class_name('????')
You could use XPath to search the DOM, there's a good tutorial on using XPath here. You may also find this resource useful which covers using XPath queries with Selenium.
You can use XPath queries with selenium like so:
elements = driver.find_elements(By.XPATH, '//button')
This code would return all buttons on the page.
elements = driver.find_elements(By.XPATH, '[class]')
This would return all the elements that contain a class attribute
I hope this helps.

Unable to recognize Element with relative xpath or other locator

I am facing an issue where I am unable to locate Element on webpage with any type of locator expect Absolute xpath. Here are details:
URL : https://semantic-ui.com/modules/dropdown.html#selection
Required Element Screen shot:
Manually created Xpath Screen shot( Please note that I am able to recognize Element in web application with manually created xpath but Same xpath is not working in selenium code)
But Same xpath is not working in selenium script.
PLEASE NOTE THAT I AM ABLE TO IDENTIFY SAME OBJECT WITH Absolute xpath
Please help to me to understand reason for this.
Here is code:
public static WebDriver driver;
public static void main(String[] args) {
driver= new FirefoxDriver();
driver.manage().window().maximize();
driver.manage().timeouts().implicitlyWait(10, TimeUnit.SECONDS);
driver.get("https://semantic-ui.com/modules/dropdown.html");
//Selection
driver.findElement(By.xpath("//div[#class='ui selection dropdown upward']")).click();
driver.findElement(By.xpath("//div[#class='menu transition visible']/div[text()='Female']")).click();
System.out.println("Done");
This may be issue with your first x-path. You may try the following code. It may work.
driver.findElement(By.xpath("//div[#class='ui selection dropdown']").click();
driver.findElement(By.xpath("//div[#class='menu transition visible']/div[text()='Male']").click();
You are missing a preceding wildcard in you driver.FindElement XPath.
Instead of driver.findElement(By.xpath("//div..."));, do driver.findElement(By.xpath("//*div..."));.
Currently, what your code is doing is telling the XPath locator to find a first level div (not easily possible, as the first item is almost always the document body), but the wildcard of "*" tells it that it can look for the div at any level.
As an aside, please edit your answer up top with actual code instead of pictures so others with the same problem can find their solution easier.
Longshot:
You are using Chrome to look at the source, but Selenium is using Firefox.
There is a chance that the source is rendered differently between the two browsers. Specifically, your xpath is relying on an exact match of class. I do know that FireFox is notorious for modifying source output.
I haven't done any testing but I would not be surprised if the class is in a different order and it's failing on an exact match.
There are two solutions if that is the case:
Don't do a single exact match (xpath = "") but instead do a mix of contains joined with && (contains ui && contains selection && dropdown)
Don't rely on the output from the console tab. Instead "View Page Source" and view what is actually being sent instead of what is being interpreted by the browser
Find the dropdown container element firstly, then use it to find self descendant, like option etc.
driver.get("https://semantic-ui.com/modules/dropdown.html");
// find dropdown container element
WebElement dropdownWrapper = driver.findElement(
By.xpath("//div[#class='html']/div[input[#name='gender']]"));
// expand drop down options by click on the container element
dropdownWrapper.click();
// or click the down arrow
dropdownWrapper.findElement(By.css('i')).click();
// select option
dropdownWrapper.findElement(By.xpath(".//div[text()='Female']")).click();
To locate the element with text as Gender and select the option Female you can use the following Locator Strategy :
Code Block :
System.setProperty("webdriver.chrome.driver", "C:\\path\\to\\geckodriver.exe");
WebDriver driver = new FirefoxDriver();
driver.get("https://semantic-ui.com/modules/dropdown.html#selection");
driver.findElement(By.xpath("//div[#class='another dropdown example']//div[#class='ui dropdown selection']")).click();
driver.findElement(By.xpath("//div[#class='another dropdown example']//div[#class='ui dropdown selection active visible']//div[#class='menu transition visible']//div[#class='item' and contains(.,'Female')]")).click();
System.out.println("Gender Female selected.");
Console Output :
Gender Female selected.
This might be helpful to clearify how selectors are working in general:
.(dot): Dot at starting represents the current node. It tells us that the processing will start from the current node.
. .(double dot): It will select parent of current node. For example, //table/. . will return div element because div is the parent of table element.
‘*’: is used to select all the element nodes descending from the current node. For example:
/table/*: It will select all child elements of a table element.
//*: It will select all elements in the document.
//*[#id = ‘username’]: It will select any element in document which has an attribute named “id” with the specified value “username”.
#: It represents an attribute which selects id, name, className, etc. For example:
#id: It will select all elements that are defined with the id attribute in the document. No matter where it is defined in the document.
//img/#alt: It will select all the img elements that are defined with the #alt attribute.
//td[#*]: It will select all td elements with any attribute.
Here is a link to the article:
https://www.scientecheasy.com/2020/07/selenium-xpath-example.html/

selenium webdriver code to click on 'Album' in facebook

I am not able to click on 'Albums' in Facebook.
The HTML is Albums how to locate the element 'Albums' in selenium web driver.
I tried with using driver.findelement(By.xpath(span[#class="_3sz"]) showing error as element not found
And, the html looks the following:
<span class="_3sz">Albums</span>
If I am understanding your problem correctly then that xpath you mentioned returns more than one elements. Use a text based search which is more easier and specific.
driver.findelement(By.xpath("//*[.='Albums']").click();
And, here . is used to directly point to the parent element. Additional wait might be needed to wait for the element to interact. Also, I am assuming you are trying to click the element.
EDIT
Driver = new ChromeDriver();
WebDriverWait wait = new WebDriverWait(Driver, TimeSpan.FromSeconds(10));
Driver.Navigate().GoToUrl("http://www.facebook.com");
Driver.Manage().Window.Maximize();
Driver.FindElement(By.CssSelector("#email")).SendKeys("your email");
Driver.FindElement(By.CssSelector("#pass")).SendKeys("your pass");
Driver.FindElement(By.CssSelector("[type='submit'][value='Log In']")).Click();
Driver.FindElement(By.CssSelector(".fbxWelcomeBoxName")).Click();
Driver.FindElement(By.XPath("//*[.='Photos']")).Click();
wait.Until(ExpectedConditions.ElementIsVisible(By.XPath("//*[.='Albums']")));
Driver.FindElement(By.XPath("//*[.='Albums']")).Click();
By albumname = By.XPath("//strong[.='2014']"); //this should be your album name. In my case it's 2014
wait.Until(ExpectedConditions.ElementExists(albumname));
Driver.FindElement(albumname).Click();
wait.Until(ExpectedConditions.ElementExists(By.CssSelector(".fbPhotoAlbumHeader.fbPhotoAlbumOptionsPresent [type='file']")));
Driver.FindElement(By.CssSelector(".fbPhotoAlbumHeader.fbPhotoAlbumOptionsPresent [type='file']")).SendKeys(#"D:\Users\Saifur\Desktop\FacebookPicture\150232_585410621540701_1836495431_a.jpg");
wait.Until(ExpectedConditions.ElementExists(By.CssSelector(".pvm.phl.footerBox.uiBoxWhite")));
Driver.SwitchTo().ActiveElement();
wait.Until(ExpectedConditions.ElementExists(By.CssSelector("[name='postPhotosButton']")));
Driver.FindElement(By.CssSelector("[name='postPhotosButton']")).Click();
Notice mine is C#
It always best practice to follow this sequence while selecting elements.
1) ID
2) CSS
3) XPath (This will have some issues with different browsers specially IE)
In this case, considering this is no other span class with same name. It would have work like this "span._3sz". Simple and powerful.