I am working with the following html table,

<tbody role="rowgroup">
<tr data-uid="d4d2114f-2aaf-4498-977b-ae5b8c16618c" role="row" class="Standard k-state-selected" aria-selected="true">
<td role="gridcell" id="sublist-ComplianceTaskUserLinksSublist-sublist-grid-wrapper_active_cell" class="k-state-focused" aria-describedby="7f2be8c4-c05c-4959-8b6e-26f26ffd343c sublist-ComplianceTaskUserLinksSublist-sublist-grid-wrapper_active_cell">USER5</td>
<td role="gridcell">USER5 </td></tr>
</tbody>

There is only one row however this will not always be the case so i have wrote a method which identifies a rows data-uid based on a cell value which is,

IWebElement tablebody = LinkedUserGroupComplianceTaskUserLinkTable.FindElement(By.TagName("tbody"));
wait.Until(ExpectedConditions.VisibilityOfAllElementsLocatedBy(By.TagName("tr")));
List<IWebElement> rows = new List<IWebElement>(tablebody.FindElements(By.TagName("tr")));
IWebElement row = rows.Where(item => item.Text.Contains(loginname)).FirstOrDefault();
string rowid = row.GetAttribute("data-uid");

However when i run a test containing this method i get exception,

WebDriverTimeoutException

against wait.Until(ExpectedConditions.VisibilityOfAllElementsLocatedBy(By.TagName("tr")));

I have used the above method elsewhere with success.

I have added a thread sleep to the method instead of the line throwing the exception which when ran works - code below,

IWebElement tablebody = LinkedUserGroupComplianceTaskUserLinkTable.FindElement(By.TagName("tbody"));
Thread.Sleep(3000);
List<IWebElement> rows = new List<IWebElement>(tablebody.FindElements(By.TagName("tr")));
IWebElement row = rows.Where(item => item.Text.Contains(loginname)).FirstOrDefault();
string rowid = row.GetAttribute("data-uid");

I'm looking for some help in how to refactor the method so i don't have to use the Thread.Sleep() or any suggestions as to why my original method is throwing the exception?

up vote 1 down vote accepted

Got it working by waiting for all cells to be visible using the below,

wait.Until(ExpectedConditions.VisibilityOfAllElementsLocatedBy(By.CssSelector("td role = gridcell")));

According to API documentation of VisibilityOfAllElementsLocatedBy(By):

An expectation for checking that all elements present on the web page that match the locator are visible. Visibility means that the elements are not only displayed but also have a height and width that is greater than 0.

I think you should try PresenceOfAllElementsLocatedBy(By) which checks for all elements present (but not necessarily visible) on the web page that match the locator.

  • Tried that still no joy - I have now got it working, will add the answer. – Luke Apr 29 at 10:06

I see you've already found an answer to your question. I was wondering if there were other tables on the page that were invisible. Using just the tag name to find an element or elements is very often not selective enough to get what you're using.

I was going to suggest By.XPath instead of by tag name. You could use something like:

IWebElement tablebody = LinkedUserGroupComplianceTaskUserLinkTable.FindElement(By.TagName("tbody"));
wait.Until(ExpectedConditions.VisibilityOfAllElementsLocatedBy(By.XPath("//tbody[@role='rowgroup']//td")));
// I'd prefer to put some way of uniquely identifying the table here
// but you only showed us the <tbody> element.
IWebElement row = LinkedUserGroupComplianceTaskUserLinkTable.FindElement(By.XPath("//tbody[@role='rolegroup']/tr[@role='role' and contains(text(),'" + loginname + "']"));

Your Answer

 

By clicking "Post Your Answer", you acknowledge that you have read our updated terms of service, privacy policy and cookie policy, and that your continued use of the website is subject to these policies.

Not the answer you're looking for? Browse other questions tagged or ask your own question.