I'm facing an issue in one of our automated script wherein I need to read the text of an element whose accessibility is hidden, since selenium can't read text of hidden elements. I checked other posts here as well and they suggest to execute javascript and read innerHTML using the element's ID. In our case the challenge is I can't use ID of the web element as its dynamic and changes each the time the page is loaded in web browser so I'm bound to rely on Xpath's, please find below the code of the element -
<div id="milestone_gwt-uid-2132" class="accessibilityhidden">Current Step: Referral Details</div>
Now id i.e. "milestone_gwt-uid-2132" is not static and changes whenever the page is loaded and I want to read the text - "Current Step: Referral Details". Is there any effective way to do that using Selenium Java?
Thanks
The method getText returns the visible text. Use executeScript to get the hidden text:
WebElement elem = driver.findElement(By.xpath("//div[contains(text(), 'Current Step:')]"));
String hiddenText = (String)((JavascriptExecutor)driver).executeScript(
"return arguments[0].textContent;", elem);
Note that assessing some hidden text in a test is probably a bad idea since it doesn't reflect what the user can see.
You can use dynamic id in your XPath in following way:
//div[contains(#id, "milestone_gwt-uid-")]
You can get innerHTML with following code
WebElement element = driver.findElement(By.xpath('//div[contains(#id, "milestone_gwt-uid-")]'));
String contents = (String)((JavascriptExecutor)driver).executeScript("return arguments[0].innerHTML;", element);
Thanks! Works with MS Word Online!!
calling the method:
String textFromEditor = getValue(driver.findElement(By.id(editorFieldId)));
the body of method:
protected String getValue(WebElement element) {
try
{
String value = (String)((JavascriptExecutor) driver).executeScript("return arguments[0].textContent;", element);
return value;
}
catch (Exception e)
{
return "can't get text";
}
}
You can assert the element by concatenating two Texts since the DOM will always contain a unique element.
Related
In selenium is there any way to find out the type of tag
In my automation page some fields may change.say first filed value is greater the second filed become input text if first is IN then drop down like that.
so is there any java script executor method to find tag name from the identified element
I have triedfollowing 2 methods
1)
WebElement ele=driver.findElement(By.id("identifierId"));
String tag =(String) ((JavascriptExecutor) driver).executeScript(" return ele.tagName ");
System.out.println(tag);
2)
String xpath="input[id='identifierId']";
String mainURL =(String) ((JavascriptExecutor) driver).executeScript(" return (document.querySelector(\"xpath \").tagName) ");
Is there any solution for this?
This code is in Java and it'll give you the tag name.
driver.findElement(By.id("username")).getTagName()
I have a
Button class = "searchbar__SearchButton-sc-1546roh-3 searchbar__CancelButton-sc-1546roh-4 glEceZ"
and trying to return in the browser element using
return browser.element('button[class^="searchbar__CancelButton-"]');
But I see an error that element can't be found.
can someone help me how can I use the element.
According to the CSS selector spec, ^ means
E[foo^="bar"] an E element whose foo attribute value begins exactly with the string bar
In your case, the class string doesn't start with "searchbar__CancelButton-". You need to change the ^ to * to indicate contains.
button[class*="searchbar__CancelButton-"]
Given that I need to set an element's selected index with javascript in capybara by the input name...
var element = document.querySelector("select[name='user[user_locations_attributes][0][location_attributes][state]']").selectedIndex = '50';
What is the proper way to interpret this as a string so it can be executed in Capybara with execute_script(function_name_string)? Because I keep getting syntax errors, unsure how to nest the " and ' quotations.
Easiest solution to your question is to use a heredoc
page.execute_script <<~JS
var element = document.querySelector("select[name='user[user_locations_attributes][0][location_attributes][state]']").selectedIndex = '50';
JS
Although if you have need for the element for anything else it's probably nicer to find the element in ruby and then just call execute_script on the element
el = find("select[name='user[user_locations_attributes][0][location_attributes][state]']")
el.execute_script('this.selectedIndex = 50;')
As a related question - is there a reason you're doing this via JS rather than just clicking on the correct option? If you're just scraping a page there's no issue, but if you're actually testing something this basically makes your test invalid since you could potentially be doing things a user couldn't
Since you commented that you are testing, you really shouldn't be doing this via JS, but should instead be using select or select_option. select takes the options string (which you should have - otherwise why have a select element in the first place)
select('the text of option', from: 'user[user_locations_attributes][0][location_attributes][state]')
select_option is called on the option element directly, which can be found in a number of ways, such as
find("select[name='user[user_locations_attributes][0][location_attributes][state]'] option:nth-child(50)").select_option
I'm scraping all element attributes via javascript using the following code:
((JavascriptExecutor) driver).executeScript("var items = {}; for (index = 0; index < arguments[0].attributes.length; ++index) { items[arguments[0].attributes[index].name] = arguments[0].attributes[index].value}; return items;", element);
Although this mostly returns only the attributes that identify the element in question I'm finding certain attributes are returned by this code that do not actually correspond to the desired element.
Case in point:
If you navigate to http://google.com and identify the search box via (.//input[contains (#role,'combobox')]) (or any one of many other XPath) and then execute said JS code it returns the attribute (.//input[contains (#class,'gsfi lst-d-f')]) that does not actually correspond with the search box. In fact, this attribute is not even present on page when using FireBug.
I did notice though that a similar text is hidden in the style tag on page however even there I did not find an exact match of this text. In either case it still does not correspond to the element in question.
Why does JS return this text and is there a way around it?
Thanks
I need to get links from the javascript. I using jsoup, but it didn't work.
screen
I need to get this link from the source of page. Can anyone help me how to do it?
String url = "http://www.cda.pl/video/149016ec/Rybki-z-ferajny-2004-1080p-Dubbing-pl";
Document doc = Jsoup.connect(url).get();
Elements scriptElements = doc.getElementsByTag("script");
for (Element element :scriptElements ){
for (DataNode node : element.dataNodes()) {
System.out.println(node.getWholeData());
}
System.out.println("-------------------");
}
I marked on screen what urls i want to get.
You can use this code:
String url = "http://www.cda.pl/video/149016ec/Rybki-z-ferajny-2004-1080p-Dubbing-pl";
Document doc = Jsoup.connect(url).get();
//we pick the script node
Element script = doc.select("#player > script").get(0);
String text = script.html();
//then we parse the script for the desired uri
final String prefix = "l='";
int p1 = text.indexOf(prefix) + prefix.length();
int p2 = text.indexOf("'", p1);
String uri = text.substring(p1, p2);
System.out.println(uri);
It will give the desired output:
http://vgra001.cda.pl/lqcc6f8b3c8f76d1b58c1234813fcf67c7.mp4?st=SjoQ8DDcnH7pW8_XNNkA3w&e=1416438406
Please note that this is only a example, you will need to do error checking.
Now the explanation:
You almost had it done, you had the location of the code with the uri, then it was easy to find the important script node: You can see a <div class="wrapqualitybtn"> near the script tag, then you can find the div that contains both your script tag and that div tag (the <div id="player" ... >, the script's tag parent node)
Once you have the script node you only need to do String parsing. Parsing javascript code could be risky because a little change in the code can break your parser, but I think in this case looking for l=' is a solid bet.
A couple of advices:
When a page uses jQuery you can use jQuery in browser console too! If you put $('#player > script')[0] In the browser you will see your script tag.
You can search through the DOM of a page in Developer tools of your browser (F12) and then right click a node and click in Copy CSS Path (in chrome, something similar in firefox) And you will obtain a selector useable in JSoup.
For a more resiliant script parsing you could use regular expressions instead of plain indexOf search.
I hope it will help, excuse me for the verbosity.