How do I replace an element? - java

I have the following HTML
<html>
<head>
<title>test</title>
</head>
<body>
<table>
<caption>table title and/or explanatory text</caption>
<thead>
<tr>
<th>header</th>
</tr>
</thead>
<tbody>
<tr>
<td id=\"test\" width=\"272\"></td>
</tr>
</tbody>
</table>
Test link
<img src=\"http://www.google.se/images/nav_logo95.png\" />"
</body>
</html>;
And I want to find the first link with jsoup and replace it with a text
Element elem = page.select("a[href=" + link.getUrl() + "]:contains(" + link.getName() + ")").first();
I can only replace the inner HTML with elem.html("foo") or print the outerHtml with elem.outerHtml()
Does anyone know how I can achieve this?

I found the answer!
TextNode text = new TextNode("foo", "");
elem.replaceWith(text);

Once you have found the element that you want to work with, you may apply the commands such as explained here: http://jsoup.org/cookbook/modifying-data/set-html
I could not get it right. I am trying this:
elemento.prepend("<a href='www.test.com'>");
elemento.html("Roberto C. Santos.");
elemento.append("</a>");
elemento.wrap("<a href='www.test.com'> </a>");
But I am getting this:
<td> <a style="" target="_self" title="" href="http://ivv.veveivv.vvzenes.com.br/mao/ara/ccacao" data-mce-href="resolveuid/5cc1c7c8c9efcacaaeedec22a9c69a54" class="internal-link">Roberto C. Santos.</a></td>
</tr>
I still don´t know the exact way to exchange the contents of an URL element.
I´d like to have, as the result:
<a href='www.test.com'> Roberto C. Santos.</a>"
How coul´d I erase the href that is inbetween?

Related

How to access a webtable element using xpath if the webtable element is inside a td tag

I am not able to access the webtable elements inside the table2 , please see the page source below :
<table id="table1">
<tr class="head">
<td class="left" colspan="2">
<!--PAGE LINKS-->
</td>
</tr>
<tr>
<td class="left_link">
<h1>
<a name="nav_home" href="index.html" id="home_link" class="home">HOME</a><br>
<a name="nav_adopt" href="adoption.html" id="adoption_link">ADOPTION</a><br>
<a name="nav_about" href="about.html" id="about_link">ABOUT</a><br>
<a name="nav_contact" href="contact.html" id="contact_link">CONTACT</a><br>
</h1>
</td>
<td class="content">
<h1>
CONTACT US
</h1>
<hr>
<p>
Use the form below to contact us if you have any questions, queries or even any requests.
We are always happy to hear from you all.
</p>
<h1 class="subhead">Contact Form</h1>
<form name="message_form">
<table id="table2" class="inner_table">
<tr>
<td>Enter Name</td>
<td><input type="text" name="name_field"></td>
</tr>
<tr>
<td></td>
<td>
<input type="radio" id="rinfo" name="rbutton" value="information">Information
<input type="radio" id="rdona" name="rbutton" value="Donation">Donation
<input type="radio" id="radop" name="rbutton" value="Donation">Adoption
</td>
</tr>
For example i am not able to access the name inside the table2.
I tried accessing using below but failed .
driver.findElements(By.xpath("//*[#class='table1']/tbody/tr[2]/td[2]/form/table[#class='inner_table']/tr[1]/td[1))
Try this below xpath
//table[#id='table2']/..//following::input[#name='name_field']
Explanation of xpath:- Use id attribute of <table> tag and move ahead with <input> tag using following keyword.
This above xpath will locate the Enter Name field text box.
Note:- Instead of using absolute xpath, Use relative xpath.
It is not recommended to use xpath on selenium, since elements might tend to change and you have to refactor your selector if you add another element.
To answer your question, you can use the id for table2 and select the desired element.
It should be a CSS selector as simple as input[name='name_field'] or if that isn't specific enough, use #table2 input[name='name_field'].
Try xpath like below:
to access input filed with name 'name_field' use below xpath
driver.findElement(By.xpath("//table[#id='table2' and #class= 'inner_table']//input[#type='text' and #name='name_field']")
Hope it will help.
In web tables, you can use xPath to reach parent of an element and then finding the preceding-sibling or the following-sibling of td tags
This tutorial will help you:
http://www.seleniumtests.com/2011/10/using-xpath-to-reach-parent-of-element.html

Scrape all matching contents using XPath function

How do I make sure that my selenium code scrapes all matching contents of my XPath?
Please help me with your ideas.
For example, these are my HTML Tags:
<tr class="1" role="r1">
<td class="c1">
<a href="www.google.com">
</a>
</td>
</tr>
<tr class="2" role="r2">
<td class="c2">
<a href="www.youtube.com">
</a>
</td>
</tr>
<tr class="3" role="c3">
<td class="c3">
<a href="www.facebook.com">
</a>
</td>
</tr>
I want my selenium code to fetch all links from href tag.
So, below is my XPath:
String links = driver.findElement(By.xpath("//tr[#role='cad']//td[#class='c1']//a")).getAttribute("href");
System.out.println(links);
but it fetches only the first href output, i.e. www.google.com.
The desired output is:
www.google.com
www.youtube.com
www.facebook.com
How can I achieve this?
Any array implementation would be better options?
Try Following code:
List<WebElement> elements= driver.findElements(By.xpath("//table/tbody/tr"));
int i =0 ;
while(i<elements.size()){
WebElement childElement = elements.get(i).findElement(By.cssSelector("a"));
System.out.println(childElement.getAttribute("href"));
i++;
}
Try below code.
List<WebElement> links = driver.findElements(By.xpath("//tr/td/a"));
for(int i=0;i<links.size();i++){
System.out.println(links.get(i).getAttribute("href"));
}

Print only html table using javascript

I have the following basic html table with a Java function to print only the table content However the Print button does nothing when clicked,I figure probably the java coding is the issue, however it is not working could I get a third pair of eyes to assist please
<html>
<body>
<table border="1" cellpadding="3" id="printTable">
<tbody><tr>
<th>First Name</th>
<th>Last Name</th>
<th>Points</th>
</tr>
<tr>
<td>Jill</td>
<td>Smith</td>
<td>50</td>
</tr>
<tr>
<td>Eve</td>
<td>Jackson</td>
<td>94</td>
</tr>
<tr>
<td>John</td>
<td>Doe</td>
<td>80</td>
</tr>
<tr>
<td>Adam</td>
<td>Johnson</td>
<td>67</td>
</tr>
</tbody></table>
<br />
<br />
<button>Print me</button>
<script>
function printData()
{
var divToPrint=document.getElementById("printTable");
newWin= window.open("");
newWin.document.write(divToPrint.outerHTML);
newWin.print();
newWin.close();
}
$('button').on('click',function(){
printData();
})
</script>
</body>
</html>
When working with javascript, it is often useful to look at your browser's console. After opening this page, mine has the error:
ReferenceError: $ is not defined
$ is a global variable inserted by jQuery. Try adding
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.2/jquery.min.js"></script>
to the code. This will include the jQuery library.
The call to the javascript function is not correct. When you're using the '$' symbol it means that you're using JQuery. You have 2 options:
1 - Include the jquery library to your page:
<script src="//ajax.googleapis.com/ajax/libs/jquery/1.4.3/jquery.min.js"></script>
2 - Call the javascript function directly on the button on the 'onclick' event. This is the best option in your case:
<button onclick="printData()">Print me</button>
Change this var divToPrint=document.getElementById("printTable");
to this var divToPrint=document.getElementById("<%=printTable.ClientID>");
and add jquery library <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.2/jquery.min.js"></script>

Finding dynamic text using selenium

I have a webpage that dynamically places a text in a span. It is something like:
<table id=table_1>
<td>
<span> $available/$total <span><label id=label_1>Servers available</label>
</td>
</table>
The only thing i know is that either "x/y Servers available" or "No Servers Available" would be displayed on the webpage. Please let me know how can I get this x and y.
<html>
<body>
<div class="refresh_div" >
<table id="Server_status_table" >
<!-- -----------For Server Status box header ---------------->
<tr>
<%
int num=Integer.parseInt(request.getAttribute("availWorkerCount").toString());
int tot=Integer.parseInt(request.getAttribute("totalWorkerCount").toString());
int avg = 0;
if(tot!=0 && num>0){
avg=num*100/tot;
}
pageContext.setAttribute("total", tot);
%>
<c:choose>
<c:when test="${ total eq 0 }">
<!-- -----------For showing how many servers are available now---------------->
<td>
<label id="Avaibility_l" style="font-size: 120%;">Availability</label>
</td>
<td>
<span>No server available</span>
</td>
</c:when>
<c:otherwise>
<!-- -----------For showing how many servers are available now---------------->
<td>
<label id="Avaibility_l" style="font-size: 120%;">Availability</label>
<br/> &nbsp
</td>
<td >
<!-- -----------For showing the availability bar---------------->
<div id="progress" class="progress">
<div id="bar" class="bar" style="width:<%=avg %>%;"></div>
</div>
<!-- -----------For showing the availability progress detail message---------------->
<span>
${availWorkerCount} / ${totalWorkerCount}<label id="Progress_message_l"> occupied</label>
</span>
</td>
</c:otherwise>
</c:choose>
</tr>
<tr>
<!-- -----------For showing the approximate Queue Wait time ---------------->
<td>
<label id="Queue_wait_time_l" style="font-size: 120%;">Queue waiting time</label>
</td>
<!-- -----------For showing the approximate wait time detail message---------------->
<td >
<label id="Wait_time _message_1stpart_l" >Approximately</label>
${queueWaitingTime}
</td>
</tr>
</table>
</div>
</body>
</html>
I need ${availWorkerCount} , ${totalWorkerCount} and ${queueWaitingTime}
I have an idea. Please follow the below steps might work for you, this answer is from the HTML prospective. I not sure what you mean by
I need ${availWorkerCount} , ${totalWorkerCount} and ${queueWaitingTime}
Full example code after the steps. Just to mention, I have not ran this code.
1.Search the Element label by text
label[contains(.,'Servers available')]
you can add id check with it also like
label[contains(#id,'label_1') and contains(.,'Servers available')]
2.get the label and then get the parallel element span. Span should have the value
CODE :
List<WebElement> elements = driver.findElements(By.xpath("label[contains(#id,'label_1') and contains(.,'Servers available')]");
for(// now loop over the elements)
{
WebElement elem = elements.get(0);
List<WebElement> spanelems = elem.findElements(By.xpath("../span"));
spanelems.get(0).getText() // this should give you the data under the span
}
With WebDriver you're picking text off from the page after it has finished loading. Thus getting this kind of "dynamic" text won't be a problem. Your example is only dynamic on the server side, in the client side the text from these variables would be static content and just as easy to grab from the page as any other text.
I suggest you put an id attribute to the <span> you're looking for, then it's super simple to get its contents with Selenium.
For example:
<span id="myStuff">foobar</span>
And fetch it with:
String contentsOfMySpan = driver.findElement(By.id("myStuff")).getText();
* EDIT *
Since you can't change original code, here's the hard way to do it:
By qwt = By.xpath("//label[#id = 'Wait_time _message_1stpart_l']/parent::td/text()[2]");
By wc = By.xpath("//label[#id = 'Progress_message_l']/parent::span/text()[1]");
String queueWaitingTime = driver.findElement(qwt).getText();
String[] workerCounts = driver.findElement(wc).getText().split(" / ");
String availWorkerCount = workerCounts[0];
String totalWorkerCount = workerCounts[1];

In tag <td></td> DOUBLE_WHITESPCE in query href

I have a very strange problem.
<table border ="1">
<tbody>
<c:forEach var="question" items="${questions}">
<tr>
<td>
${question.getQuestion()}
</td>
<td>
<c:forEach var="answer" items="${question.getAnswers()}">
<input type="checkbox" name ="user_answer" value="${answer.getAnswer()}">
${answer.getAnswer()}
<br />
</c:forEach>
</td>
<td>
<a href="/TutorWebApp/controller?command=edit_qestion&question=${question}">
Edit
</a>
</td>
</tr>
</c:forEach>
</tbody>
</table>
But If I use in I get next error
But if I don't use tag <a> in <td> it's OK. I don't have any ideas.
Thanks
I think this is just a bug/limitation of your editor. Try deploying your JSP and see if it works as expected or not.
That said, if your question contains characters that must be URL and/or HTML escaped, your HTML code will be invalid. You should use the c:url tag to avoid that:
<c:url var="editQuestionUrl" value="/TutorWebApp/controller">
<c:param name="command" value="edit_question"/>
<c:param name="question" value="${question}"/>
</c:url>
<%-- now the params are url-encoded --%>
Edit
<%-- now the query string is HTML-escaped --%>
You need to encode your question text (or whole URL) here by calling URLEncoder#encode()
You can look at this Q&A on how to encode a URL in JSTL.
Alternatively you can try calling JSTL's escapeXml function on your question text.
try replacing this line
<a href="/TutorWebApp/controller?command=edit_qestion&question=${question}">
with
<a href="/TutorWebApp/controller?command=edit_qestion&question='${question}'">

Categories