Better way to get a parent element using Selenium - selenium

There is this button that when I try to click on, he kinda moves a little and opens a sub-menu. The solution is easy, just click on the div a few levels above him (still the button). But he is always changing class names.
I mannage to do it using this aberation //div[#style]/span[#aria-label]/../../../../../...
I also tried to use //div[#style]/span[#aria-label]/parent::div[#role="option"], but it did not work, and I don't know why.
Does anyone have any suggestions to make it more decent? I am sure that the "../" was not mean to be used on so many levels...
Also, I was trying to use CSS selectors for my entire project, but after spending some hours looking at StackOverflow answers, the solution seems to be use XPATH. If there is a way to do this operation with CSS Selectors, I would be very interested.

You can shorten and make your XPath expression more readable with :
//div[#style]/span[#aria-label]/ancestor::*[5]
where ancestor::*[5] replaces /../../../../../...

Related

Vuejs 2 v-on:click.prevent()

I would like to know what these options people are using more.
1) Using v-on on normal (div, span, etc) element
<div v-on:click="myFunction" class="cursor-pointer">Click me<div>
Here, it requires to have the a class to set up the pointer cursor to indicate that is can be clicked, and also, to increase the UX.
1) Using v-on on link element
Click me
Here, doesn't need to have any classe to set up the pointer cursor. However, it requires the prevent mode to stop the link action.
So, What is the best practice, advantages and drawbacks of these two approaches?
Ultimately, it doesn't really matter. Generally speaking though, you should be writing your HTML dom in Vue.js the same way you would write it without Vue.js. If something should be a link because it's leading to another view in your application, then <a> makes sense. If you wouldn't normally use an anchor link if it was just a static HTML page, then you're probably better to be writing it with a div, span, or whatever your developer instincts decide in that case.
Always try to write your code as if someone else is going to be looking at it, in which case they are going to have some expectation of what an <a> is supposed to be doing.

Identify objects in selenium

In my application, it has several tabs, say 'AAA','ABC','ADF'; I need to automate the click on tab 'ABC'.
Those tabs have ids and they are 'tab1','tab2','tab3'. I can done this easily by using ids. but i don't want to use this because those tabs will change time to time. so I need to use the name in the tab, because it is unique.
Below is my tag:
<a id="tab2" class="current" onclick="expandcontent('sc2', this);" href="#"> ABC </a>
If this is the case, you will probably need to fall back to XPath and perform text-based searches, for instance:
//a[text()='ABC']
Though, I'd advise you work with your development team to have consistent ID's. Text based matching is fine, but when you start to use older browsers you'll notice it really really slows down the tests.
However, you can also use the .LinkText and .PartialLinkText selectors in your language API's - there should be an implementation of those selectors in each API (C#, Ruby, Python etc). The catch here is this will be for a (anchor) elements only. However, providing that is the only type of elements this needs to be done by, you can get away with using this instead of XPath.
As Arran mentioned, you are likely best off searching for the tab names using XPath but, you can also use FindBy as well. An example of this would be:
#FindBy(css=<the CSS value for the tab>) private WebElement pageTab2;
#FindBy(id="tab2") private WebElement pageTab2;
I can only agree with what Arran also mentioned about your developers using more relevant naming conventions as well. The easier they make your job, the more you can do to make their lives easier too.
Simplest answer will be Use..."link=ABC" or link=" ABC " (it there are leading and trailing spaces).
The simplest approach would be to use X paths to find your tabs.
When you are starting out there are two helpful tools to help you find X paths. Download Mozilla Firefox and get these two add-ons:
Web Driver Element Locator-After downloading you can right click a web element and select X path.
Selenium IDE-This is a recorder and will give you the X paths or CSS of each web element you interact with.
I would recommend starting with these tools to help you out since you are just starting out.
As for your question:
I would recommend using what #Arran said...
//a[text()='ABC']
'a'-will search the entire page for whatever text you have in single quotes ''
If you Right Click the element or Tab and select Inspect. You will then be looking through the back-end of the page for classes or div that help you identify each different element.
xpath=//a[contains(#class,"current") and contains(#text,"ABC")]

Finding clickon Element using Selenium. (JAVA)

I spend hours already trying to find the way to find the Element using Selenium WebDriver. I assume I need to use driver.findElement(By.xpath("")), but I am not quite sure how.
I somehow need to find and click on "clickon" element. The problem is that part of that element is changing (see screenshot) I need to pick up from the file and putted into the xpath.
I would appreciate any help.
We have been rigorously searching for automated functional testing solutions recently, and we began with Selenium. The entire reason we decided to search for other solutions was that our application also has dynamic IDs with no other obvious XPath mechanism to identify them. Selenium is unable to identify these elements on the page without some additional knowledge, just as you would be unable to identify these elements on the page if you didn't already know what they are.
If you are controlling the DOM creation, consider adding a unique ID or class to this element.
We recently came across eggPlant from testPlant, and it is an interesting approach to functional testing. It's essentially image based. Other viable solutions are Ranorex or HP's QTP or SmartBear's TestComplete.
You can use xpath. If the div class is constant, you can use something like:
driver.findElement(By.xpath("list-row field-item")).click();
To view the xpath, you can install firefox plugin called 'xpath checker' found here and right click on the dom element and click 'View Xpath' option to get the xpath of the element and then you can use that xpath in your code.
Or you can even use regex in the xpath which is suitable for the similar problems. Xpath with regex is really powerful.
It seems that you want to click the div that has the on click attribute that contains certain text that doesn't change, ignoring the part that does. In that case, use an xpath like this:
//div[contains(#onclick, '/challenge/index/rfp_id/')]
This will select the first div with an onclick attribute with a value containing /challenge/index/rfp_id.

How to handle dynamic id from xpath

I am trying to explore IDE with this site http://www.barnesandnoble.com/, by just recording and play back.
1.In the search box just enter any text to search,
2.Ten click on All Products, select Books.
When i record its xpath is as below
/html/body[#id='CDS']/div[#id='navContainer']/div[#id='bnnav2011']/div[#id='yui_3_3_0_1_1355746621091_93']/div[#id='bn-global-header']/div[#id='yui_3_3_0_1_1355746621091_92']/div[#id='yui_3_3_0_1_1355746621091_91']/form[#id='qs']/div[#id='yui_3_3_0_1_1355746621091_90']/div[#id='yui_3_3_0_1_1355746621091_89']/ul[#id='yui_3_3_0_1_1355746621091_88']/li[#id='yui_3_3_0_1_1355746621091_99']
But when we play ti again it gives error,[error] locator not found:
Wehn i search for its xpath , its chnaged and is as below
/html/body[#id='CDS']/div[#id='navContainer']/div[#id='bnnav2011']/div[#id='yui_3_3_0_1_1355748592221_91']/div[#id='bn-global-header']/div[#id='yui_3_3_0_1_1355748592221_97']/div[#id='yui_3_3_0_1_1355748592221_96']/form[#id='qs']/div[#id='yui_3_3_0_1_1355748592221_95']/div[#id='yui_3_3_0_1_1355748592221_94']/ul[#id='yui_3_3_0_1_1355748592221_93']/li[#id='yui_3_3_0_1_1355748592221_98']
Observe that, its ID's are changing.
Can any one tell me how to handle this ?
The IDE is not very smart at generating XPath queries, in fact, there isn't an automated tool out there that will calculate a reliable XPath query. Why? The reason is because to generate the XPath query, it will walk down the tree from the top (at the html element), down to the element you are interacting with.
Whilst this is fine for a lot of things, if you have elements that have dynamic values (dynamic text/ID/name/classes or even if it changes position), it's never going to work.
You'll need to look at a different way to get it, so you'll have to override what the IDE is giving you.
Looking at the source, they give whatever is selected a class value of ui-selectmenu-selected. So when the page loads, the 'All Products' list item (li) will have that class, when you change the item the new item will have that class.
So you could use this XPath:
//li[#class='ui-selectmenu-selected']
Or, this CSS selector:
li.ui-selectmenu-selected
Or, use this XPath to get the 'All Products' item specifically. It will start one level up, using the actual menu, then go down and find the item:
//ul[#class='ui-selectmenu']/li[text()='All Products' and not(#class='ui-selectmenu-hidden')]
You can try using xpath: Position. It seems that the IDs are changing all the time.
As an answer to your question you should move away from id's and try using xpath or css selectors where you can select the nth child of the parent.
Since you are new to selenium I would like to point to my notes here at.-
http://selenium-testing-notes.blogspot.in/
it will help you through a lot of other pitfalls I fell in.
The best way I found to help with selectors is to work with firebug with firepath installed. This setup can help you verifying your xpath and css selectors.
I saw your question based on that answer is first you need to add on fire-path in Firefox .Using firepath you can find the xpath locator. it is very simple to you
Example:
driver.find_element_by_xpath("see![image which i have attached in this question][1] the xpath path locator details").click()
Hi Arran i am able to click the All Products button using the xpath you have given ( xpath= //ul[#class='ui-selectmenu']/li[text()='All Products' and not(#class='ui-selectmenu-hidden')]
and also get the list available. But then not able to click the Books item from the Menu.

How to convert this xpath to css?

How to change this below Xpath to css? Please help.
//button[text()='Continue' and #class='buttonLargeAlt' and #type='submit']
Unfortunately, you can't.
The problem is that CSS selectors can't find by text. Therefore, you can't translate text()='Continue' XPath to a working CSS selector. This is one of the two main reasons for XPaths to be actually used till today for HTML elements selecting.
There was a :contains() pseudo class for this in CSS3, but it's long gone. Sizzle, the JS engine for CSS selecting in Selenium, has kept it, though. So if your browser doesn't support native CSS selecting (or you disable it), you can use it like this:
button.buttonLargeAlt:contains('Continue')[type='submit']
I normally use this cssify, This is pretty cool