Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Android] Search all by text #301

Closed
bootstraponline opened this issue Mar 21, 2013 · 9 comments · Fixed by #308
Closed

[Android] Search all by text #301

bootstraponline opened this issue Mar 21, 2013 · 9 comments · Fixed by #308

Comments

@bootstraponline
Copy link
Member

> $driver.find_element :xpath, %(*[@text='Sign Out'])
post
session/a5ddd229-4c4a-4745-95d2-a8e7bcb28623/element
{"using":"xpath","value":"*[@text='Sign Out']"}
Selenium::WebDriver::Error::XPathLookupError: Could not parse xpath data from *[@text='Sign Out']

Android has [text contains](http://developer.android.com/tools/help/uiautomator/UiSelector.html#textContains(java.lang.String\)) so that should work.

@bootstraponline
Copy link
Member Author

diff --git a/uiautomator/bootstrap/src/io/appium/android/bootstrap/AndroidCommandHolder.java b/uiautomator/bootstrap/src/io/appium/android/bootstrap/
index 0027561..ad18605 100644
--- a/uiautomator/bootstrap/src/io/appium/android/bootstrap/AndroidCommandHolder.java
+++ b/uiautomator/bootstrap/src/io/appium/android/bootstrap/AndroidCommandHolder.java
@@ -220,14 +220,11 @@ class AndroidCommandHolder {
     private static UiSelector selectorForFind(String strategy, String selector, Boolean many) throws InvalidStrategyException, AndroidCommandExcepti
         UiSelector s = new UiSelector();
         if (strategy.equals("tag name")) {
+        } else if (strategy.equals("text")) {
+            s = s.textContains(selector);
         } else if (strategy.equals("name")) {
             s = s.description(selector);
         } else {
@@ -241,4 +238,4 @@ class AndroidCommandHolder {
         return s;
     }

-}
\ No newline at end of file
+}

This works. Some selenium bindings will not accept finding by text so it should probably be placed under xpath.

@bootstraponline
Copy link
Member Author

"//*[contains(@text, 'Sign Out')]" I think that's the proper XPath. This works in chrome

$x("//*[contains(@href,'favico')]")

Appium can't parse it though.

> $driver.find_element :xpath, %(//*[contains(@text, 'agree')])
post
session/a691485b-f94a-43a2-9ad2-3d113816b863/element
{"using":"xpath","value":"//*[contains(@text, 'agree')]"}
Selenium::WebDriver::Error::XPathLookupError: Could not parse xpath data from //*[contains(@text, 'agree')]

@bootstraponline
Copy link
Member Author

Is there a better place for this than XPath?

@jlipps
Copy link
Member

jlipps commented Mar 22, 2013

we could use selenium's "link text".

also yeah xpath doesn't support * yet, but i imagine that it could... adding it to the feature list!

@bootstraponline
Copy link
Member Author

we could use selenium's "link text".

Link text is defined as Find the link element with matching visible text. The type can be any element so I'm not sure that makes sense.

also yeah xpath doesn't support * yet, but i imagine that it could... adding it to the feature list!

What about a simple implementation like this? I think there's only one valid XPath to trigger this feature.

> rgx
"//*[contains(@text, 'agree')]"
> rgx.match("//\\*\\[contains\\(@text, '(.*)'\\)\\]")[1]
"agree"

@bootstraponline
Copy link
Member Author

The fix seems simple enough for xpath.js.

  var root = "^(/?/?(?:[a-zA-Z]+|\\*))";

@bootstraponline
Copy link
Member Author

Android messes it up.

$driver.find_element :xpath, %(//*[contains(@text, 'agree')])
info: [ANDROID] [info] Got data from client: {"cmd":"action","action":"find","params":{"strategy":"xpath","selector":"//*[contains(@text, 'agree')]","context":"","multiple":false,"path":[{"node":"*","search":"desc"}],"attr":"text","constraint":"agree","substr":true}}
info: [ANDROID] [info] Got command of type ACTION
info: [ANDROID] [info] Building xpath selector from attr text and constraint agree and substr true
info: [ANDROID] [info] s.className('android.widget.*').textContains('agree')

@bootstraponline
Copy link
Member Author

I submitted #308 with a proper fix.

@jlipps jlipps closed this as completed in ec21895 Mar 23, 2013
sebv pushed a commit to sebv/appium that referenced this issue May 15, 2014
sebv pushed a commit to sebv/appium that referenced this issue May 15, 2014
dpgraham pushed a commit to dpgraham/appium that referenced this issue Oct 1, 2018
Remove bash script for starting up real device
dpgraham pushed a commit to dpgraham/appium that referenced this issue Nov 7, 2018
Remove bash script for starting up real device
@lock
Copy link

lock bot commented May 4, 2019

This thread has been automatically locked since there has not been any recent activity after it was closed. Please open a new issue for related bugs.

@lock lock bot locked and limited conversation to collaborators May 4, 2019
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants