Skip to content

Commit a2b9440

Browse files
authored
Move search context methods from webdriver and webelement to search_context (#461)
* Move ios search context methods to search_context file * Move android search text methods * Move windows search context * Move mobile search context * Divided search_context into each class * Move custom and image methods * Move contents in search_context.py to __init__.py * Add rtype to each docstring for auto completion in IDE * Add comments
1 parent 4589bc4 commit a2b9440

File tree

9 files changed

+473
-467
lines changed

9 files changed

+473
-467
lines changed
Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
#!/usr/bin/env python
2+
3+
# Licensed under the Apache License, Version 2.0 (the "License");
4+
# you may not use this file except in compliance with the License.
5+
# You may obtain a copy of the License at
6+
#
7+
# http://www.apache.org/licenses/LICENSE-2.0
8+
#
9+
# Unless required by applicable law or agreed to in writing, software
10+
# distributed under the License is distributed on an "AS IS" BASIS,
11+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
# See the License for the specific language governing permissions and
13+
# limitations under the License.
14+
15+
# pylint: disable=abstract-method
16+
17+
from selenium import webdriver
18+
from selenium.webdriver.remote.webelement import \
19+
WebElement as SeleniumWebElement
20+
21+
from .android import AndroidSearchContext
22+
from .custom import CustomSearchContext
23+
from .ios import iOSSearchContext
24+
from .mobile import MobileSearchContext
25+
from .windows import WindowsSearchContext
26+
27+
28+
class AppiumSearchContext(webdriver.Remote,
29+
AndroidSearchContext,
30+
CustomSearchContext,
31+
iOSSearchContext,
32+
MobileSearchContext,
33+
WindowsSearchContext):
34+
"""Returns appium driver search conext"""
35+
36+
37+
class AppiumWebElementSearchContext(SeleniumWebElement,
38+
AndroidSearchContext,
39+
CustomSearchContext,
40+
iOSSearchContext,
41+
MobileSearchContext,
42+
WindowsSearchContext):
43+
"""Returns appium web element search context"""

appium/webdriver/extensions/search_context.py renamed to appium/webdriver/extensions/search_context/android.py

Lines changed: 70 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -16,21 +16,9 @@
1616

1717
import json
1818

19-
from selenium import webdriver
20-
from selenium.webdriver.remote.webelement import \
21-
WebElement as SeleniumWebElement
22-
2319
from appium.webdriver.common.mobileby import MobileBy
2420

25-
26-
class BaseSearchContext(object):
27-
"""Used by each search context. Dummy find_element/s are for preventing pylint error"""
28-
29-
def find_element(self, by=None, value=None):
30-
raise NotImplementedError
31-
32-
def find_elements(self, by=None, value=None):
33-
raise NotImplementedError
21+
from .base_search_context import BaseSearchContext
3422

3523

3624
class AndroidSearchContext(BaseSearchContext):
@@ -58,6 +46,9 @@ def find_element_by_android_data_matcher(self, name=None, args=None, className=N
5846
5947
Usage:
6048
driver.find_element_by_android_data_matcher(name='hasEntry', args=['title', 'Animation'])
49+
50+
# To enable auto completion in PyCharm(IDE)
51+
:rtype: `appium.webdriver.webelement.WebElement`
6152
"""
6253

6354
return self.find_element(
@@ -83,6 +74,8 @@ def find_elements_by_android_data_matcher(self, name=None, args=None, className=
8374
8475
Usage:
8576
driver.find_elements_by_android_data_matcher(name='hasEntry', args=['title', 'Animation'])
77+
78+
:rtype: `appium.webdriver.webelement.WebElement`
8679
"""
8780

8881
return self.find_elements(
@@ -99,12 +92,70 @@ def _build_data_matcher(self, name=None, args=None, className=None):
9992

10093
return json.dumps(result)
10194

95+
def find_element_by_android_uiautomator(self, uia_string):
96+
"""Finds element by uiautomator in Android.
97+
98+
Args:
99+
uia_string: The element name in the Android UIAutomator library
100+
101+
Usage:
102+
driver.find_element_by_android_uiautomator('.elements()[1].cells()[2]')
103+
104+
Returns:
105+
`appium.webdriver.webelement.WebElement`
106+
107+
:rtype: `appium.webdriver.webelement.WebElement`
108+
"""
109+
return self.find_element(by=MobileBy.ANDROID_UIAUTOMATOR, value=uia_string)
110+
111+
def find_elements_by_android_uiautomator(self, uia_string):
112+
"""Finds elements by uiautomator in Android.
113+
114+
Args:
115+
uia_string (str): The element name in the Android UIAutomator library
116+
117+
Usage:
118+
driver.find_elements_by_android_uiautomator('.elements()[1].cells()[2]')
119+
120+
Returns:
121+
:obj:`list` of :obj:`appium.webdriver.webelement.WebElement`
122+
123+
:rtype: list of `appium.webdriver.webelement.WebElement`
124+
"""
125+
return self.find_elements(by=MobileBy.ANDROID_UIAUTOMATOR, value=uia_string)
126+
127+
def find_element_by_android_viewtag(self, tag):
128+
"""Finds element by [View#tags](https://developer.android.com/reference/android/view/View#tags) in Android.
102129
103-
class AppiumSearchContext(webdriver.Remote,
104-
AndroidSearchContext):
105-
"""Returns appium driver search conext"""
130+
It works with [Espresso Driver](https://github.com/appium/appium-espresso-driver).
131+
132+
Args:
133+
tag (str): The tag name of the view to look for
106134
135+
Usage:
136+
driver.find_element_by_android_viewtag('a tag name')
137+
138+
Returns:
139+
`appium.webdriver.webelement.WebElement`
140+
141+
:rtype: `appium.webdriver.webelement.WebElement`
142+
"""
143+
return self.find_element(by=MobileBy.ANDROID_VIEWTAG, value=tag)
107144

108-
class AppiumWebElementSearchContext(SeleniumWebElement,
109-
AndroidSearchContext):
110-
"""Returns appium web element search context"""
145+
def find_elements_by_android_viewtag(self, tag):
146+
"""Finds element by [View#tags](https://developer.android.com/reference/android/view/View#tags) in Android.
147+
148+
It works with [Espresso Driver](https://github.com/appium/appium-espresso-driver).
149+
150+
Args:
151+
tag (str): The tag name of the view to look for
152+
153+
Usage:
154+
driver.find_elements_by_android_viewtag('a tag name')
155+
156+
Returns:
157+
:obj:`list` of :obj:`appium.webdriver.webelement.WebElement`
158+
159+
:rtype: list of `appium.webdriver.webelement.WebElement`
160+
"""
161+
return self.find_elements(by=MobileBy.ANDROID_VIEWTAG, value=tag)
Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
#!/usr/bin/env python
2+
3+
# Licensed under the Apache License, Version 2.0 (the "License");
4+
# you may not use this file except in compliance with the License.
5+
# You may obtain a copy of the License at
6+
#
7+
# http://www.apache.org/licenses/LICENSE-2.0
8+
#
9+
# Unless required by applicable law or agreed to in writing, software
10+
# distributed under the License is distributed on an "AS IS" BASIS,
11+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
# See the License for the specific language governing permissions and
13+
# limitations under the License.
14+
15+
# pylint: disable=abstract-method
16+
17+
18+
class BaseSearchContext(object):
19+
"""Used by each search context. Dummy find_element/s are for preventing pylint error"""
20+
21+
def find_element(self, by=None, value=None):
22+
raise NotImplementedError
23+
24+
def find_elements(self, by=None, value=None):
25+
raise NotImplementedError
Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,62 @@
1+
#!/usr/bin/env python
2+
3+
# Licensed under the Apache License, Version 2.0 (the "License");
4+
# you may not use this file except in compliance with the License.
5+
# You may obtain a copy of the License at
6+
#
7+
# http://www.apache.org/licenses/LICENSE-2.0
8+
#
9+
# Unless required by applicable law or agreed to in writing, software
10+
# distributed under the License is distributed on an "AS IS" BASIS,
11+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
# See the License for the specific language governing permissions and
13+
# limitations under the License.
14+
15+
# pylint: disable=abstract-method
16+
17+
from appium.webdriver.common.mobileby import MobileBy
18+
19+
from .base_search_context import BaseSearchContext
20+
21+
22+
class CustomSearchContext(BaseSearchContext):
23+
"""Define search context for custom plugin"""
24+
25+
def find_element_by_custom(self, selector):
26+
"""Finds an element in conjunction with a custom element finding plugin
27+
28+
Args:
29+
selector (str): a string of the form "module:selector", where "module" is
30+
the shortcut name given in the customFindModules capability, and
31+
"selector" is the string that will be passed to the custom element
32+
finding plugin itself
33+
34+
Usage:
35+
driver.find_element_by_custom("foo:bar")
36+
37+
Returns:
38+
`appium.webdriver.webelement.WebElement`
39+
40+
# To enable auto completion in PyCharm(IDE)
41+
:rtype: `appium.webdriver.webelement.WebElement`
42+
"""
43+
return self.find_element(by=MobileBy.CUSTOM, value=selector)
44+
45+
def find_elements_by_custom(self, selector):
46+
"""Finds elements in conjunction with a custom element finding plugin
47+
48+
Args:
49+
selector: a string of the form "module:selector", where "module" is
50+
the shortcut name given in the customFindModules capability, and
51+
"selector" is the string that will be passed to the custom element
52+
finding plugin itself
53+
54+
Usage:
55+
driver.find_elements_by_custom("foo:bar")
56+
57+
Returns:
58+
:obj:`list` of :obj:`appium.webdriver.webelement.WebElement`
59+
60+
:rtype: list of `appium.webdriver.webelement.WebElement`
61+
"""
62+
return self.find_elements(by=MobileBy.CUSTOM, value=selector)
Lines changed: 120 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,120 @@
1+
#!/usr/bin/env python
2+
3+
# Licensed under the Apache License, Version 2.0 (the "License");
4+
# you may not use this file except in compliance with the License.
5+
# You may obtain a copy of the License at
6+
#
7+
# http://www.apache.org/licenses/LICENSE-2.0
8+
#
9+
# Unless required by applicable law or agreed to in writing, software
10+
# distributed under the License is distributed on an "AS IS" BASIS,
11+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
# See the License for the specific language governing permissions and
13+
# limitations under the License.
14+
15+
# pylint: disable=abstract-method
16+
17+
from appium.webdriver.common.mobileby import MobileBy
18+
19+
from .base_search_context import BaseSearchContext
20+
21+
22+
class iOSSearchContext(BaseSearchContext):
23+
"""Define search context for iOS"""
24+
25+
def find_element_by_ios_uiautomation(self, uia_string):
26+
"""Finds an element by uiautomation in iOS.
27+
28+
Args:
29+
uia_string (str): The element name in the iOS UIAutomation library
30+
31+
Usage:
32+
driver.find_element_by_ios_uiautomation('.elements()[1].cells()[2]')
33+
34+
Returns:
35+
`appium.webdriver.webelement.WebElement`
36+
37+
# To enable auto completion in PyCharm(IDE)
38+
:rtype: `appium.webdriver.webelement.WebElement`
39+
"""
40+
return self.find_element(by=MobileBy.IOS_UIAUTOMATION, value=uia_string)
41+
42+
def find_elements_by_ios_uiautomation(self, uia_string):
43+
"""Finds elements by uiautomation in iOS.
44+
45+
Args:
46+
uia_string (str): The element name in the iOS UIAutomation library
47+
48+
Usage:
49+
driver.find_elements_by_ios_uiautomation('.elements()[1].cells()[2]')
50+
51+
Returns:
52+
:obj:`list` of :obj:`appium.webdriver.webelement.WebElement`
53+
54+
:rtype: list of `appium.webdriver.webelement.WebElement`
55+
"""
56+
return self.find_elements(by=MobileBy.IOS_UIAUTOMATION, value=uia_string)
57+
58+
def find_element_by_ios_predicate(self, predicate_string):
59+
"""Find an element by ios predicate string.
60+
61+
Args:
62+
predicate_string (str): The predicate string
63+
64+
Usage:
65+
driver.find_element_by_ios_predicate('label == "myLabel"')
66+
67+
Returns:
68+
`appium.webdriver.webelement.WebElement`
69+
70+
:rtype: `appium.webdriver.webelement.WebElement`
71+
"""
72+
return self.find_element(by=MobileBy.IOS_PREDICATE, value=predicate_string)
73+
74+
def find_elements_by_ios_predicate(self, predicate_string):
75+
"""Finds elements by ios predicate string.
76+
77+
Args:
78+
predicate_string (str): The predicate string
79+
80+
Usage:
81+
driver.find_elements_by_ios_predicate('label == "myLabel"')
82+
83+
Returns:
84+
:obj:`list` of :obj:`appium.webdriver.webelement.WebElement`
85+
86+
:rtype: list of `appium.webdriver.webelement.WebElement`
87+
"""
88+
return self.find_elements(by=MobileBy.IOS_PREDICATE, value=predicate_string)
89+
90+
def find_element_by_ios_class_chain(self, class_chain_string):
91+
"""Find an element by ios class chain string.
92+
93+
Args:
94+
class_chain_string (str): The class chain string
95+
96+
Usage:
97+
driver.find_element_by_ios_class_chain('XCUIElementTypeWindow/XCUIElementTypeButton[3]')
98+
99+
Returns:
100+
`appium.webdriver.webelement.WebElement`
101+
102+
:rtype: `appium.webdriver.webelement.WebElement`
103+
"""
104+
return self.find_element(by=MobileBy.IOS_CLASS_CHAIN, value=class_chain_string)
105+
106+
def find_elements_by_ios_class_chain(self, class_chain_string):
107+
"""Finds elements by ios class chain string.
108+
109+
Args:
110+
class_chain_string (str): The class chain string
111+
112+
Usage:
113+
driver.find_elements_by_ios_class_chain('XCUIElementTypeWindow[2]/XCUIElementTypeAny[-2]')
114+
115+
Returns:
116+
:obj:`list` of :obj:`appium.webdriver.webelement.WebElement`
117+
118+
:rtype: list of `appium.webdriver.webelement.WebElement`
119+
"""
120+
return self.find_elements(by=MobileBy.IOS_CLASS_CHAIN, value=class_chain_string)

0 commit comments

Comments
 (0)