Skip to content

Commit 90ebcab

Browse files
authored
Merge pull request #2586 from seleniumbase/more-methods-and-uc-mode-updates
More methods and UC Mode updates
2 parents 5bd9f74 + aaae4b4 commit 90ebcab

15 files changed

+136
-13
lines changed

examples/raw_bing_captcha.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -9,4 +9,4 @@
99
sb.activate_demo_mode() # See asserts as they happen
1010
sb.assert_element("svg#success-icon")
1111
sb.assert_text("Success!", "span#success-text")
12-
sb.highlight("div#success", loops=10)
12+
sb.highlight("div#success")

examples/raw_cdp_logging.py

+3-1
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,9 @@
33

44
driver = Driver(uc=True, log_cdp=True)
55
try:
6-
driver.get("https://seleniumbase.io/apps/invisible_recaptcha")
6+
driver.uc_open_with_reconnect("https://seleniumbase.io/apps/turnstile")
7+
driver.uc_switch_to_frame("iframe")
8+
driver.uc_click("span.mark")
79
driver.sleep(3)
810
pprint(driver.get_log("performance"))
911
finally:

examples/raw_nopecha.py

+4-3
Original file line numberDiff line numberDiff line change
@@ -1,17 +1,18 @@
11
from seleniumbase import SB
22

33
with SB(uc=True, test=True) as sb:
4-
sb.driver.uc_open_with_reconnect("https://nopecha.com/demo/turnstile", 5)
4+
sb.driver.uc_open_with_reconnect("https://nopecha.com/demo/turnstile", 4)
55
sb.driver.uc_switch_to_frame("#example-container5 iframe")
6-
sb.driver.uc_click("span.mark")
6+
sb.driver.uc_click("span.mark", reconnect_time=1)
77

88
if sb.is_element_visible("#example-container0 iframe"):
99
sb.switch_to_frame("#example-container0 iframe")
1010
if not sb.is_element_visible("circle.success-circle"):
11-
sb.driver.uc_click("span.mark")
11+
sb.driver.uc_click("span.mark", reconnect_time=1)
1212
sb.switch_to_frame("#example-container0 iframe")
1313
sb.assert_element("circle.success-circle")
1414
sb.switch_to_parent_frame()
15+
1516
sb.switch_to_frame("#example-container5 iframe")
1617
sb.assert_element("svg#success-icon", timeout=3)
1718
sb.switch_to_parent_frame()

examples/raw_robot.py

+17
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
from seleniumbase import SB
2+
3+
with SB(enable_3d_apis=True, test=True) as sb:
4+
sb.open("threejs.org/examples/#webgl_animation_skinning_morph")
5+
sb.switch_to_frame("iframe#viewer")
6+
sb.set_text_content("#info p", "Hi, I'm Michael Mintz")
7+
sb.add_css_style("#info p{zoom: 2.54}")
8+
sb.sleep(0.8)
9+
sb.click('button:contains("Wave")')
10+
sb.highlight("#info p")
11+
sb.select_option_by_text("select", "Idle")
12+
sb.click('button:contains("ThumbsUp")')
13+
sb.set_text_content("#info p", "I created SeleniumBase")
14+
sb.highlight("#info p")
15+
sb.sleep(0.8)
16+
sb.click('button:contains("Jump")')
17+
sb.sleep(1.5)

examples/raw_uc_mode.py

+3-1
Original file line numberDiff line numberDiff line change
@@ -7,5 +7,7 @@
77
if not sb.is_text_visible("Username", '[for="user_login"]'):
88
sb.driver.uc_open_with_reconnect(url, 4)
99
sb.assert_text("Username", '[for="user_login"]', timeout=3)
10-
sb.highlight('label[for="user_login"]', loops=3)
10+
sb.assert_element('label[for="user_login"]')
11+
sb.highlight('button:contains("Sign in")')
12+
sb.highlight('h1:contains("GitLab.com")')
1113
sb.post_message("SeleniumBase wasn't detected", duration=4)

examples/test_3d_apis.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
from seleniumbase import BaseCase
2-
BaseCase.main(__name__, __file__)
2+
BaseCase.main(__name__, __file__, "--enable-3d-apis")
33

44

55
class ThreeJSTests(BaseCase):

help_docs/method_summary.md

+15
Original file line numberDiff line numberDiff line change
@@ -370,6 +370,8 @@ self.highlight_type(selector, text, by="css selector", loops=3, scroll=True, tim
370370
# self.highlight_update_text(
371371
# selector, text, by="css selector", loops=3, scroll=True, timeout=None)
372372

373+
self.highlight_if_visible(selector, by="css selector", loops=4, scroll=True)
374+
373375
self.highlight(selector, by="css selector", loops=4, scroll=True, timeout=None)
374376

375377
self.press_up_arrow(selector="html", times=1, by="css selector")
@@ -742,6 +744,7 @@ self.generate_traffic_chain(pages, loops=1)
742744

743745
self.get_element(selector, by="css selector", timeout=None)
744746
# Duplicates:
747+
# self.wait_for_selector(selector, by="css selector", timeout=None)
745748
# self.locator(selector, by="css selector", timeout=None)
746749
# self.wait_for_element_present(selector, by="css selector", timeout=None)
747750

@@ -957,6 +960,12 @@ driver.assert_exact_text(text, selector)
957960

958961
driver.wait_for_element(selector)
959962

963+
driver.wait_for_element_visible(selector)
964+
965+
driver.wait_for_element_present(selector)
966+
967+
driver.wait_for_selector(selector)
968+
960969
driver.wait_for_text(text, selector)
961970

962971
driver.wait_for_exact_text(text, selector)
@@ -991,6 +1000,8 @@ driver.highlight(selector)
9911000

9921001
driver.highlight_click(selector)
9931002

1003+
driver.highlight_if_visible(selector)
1004+
9941005
driver.sleep(seconds)
9951006

9961007
driver.locator(selector)
@@ -1015,6 +1026,10 @@ driver.uc_open_with_reconnect(url, reconnect_time=None)
10151026

10161027
driver.reconnect(timeout)
10171028

1029+
driver.disconnect()
1030+
1031+
driver.connect()
1032+
10181033
driver.uc_click(
10191034
selector, by="css selector",
10201035
timeout=settings.SMALL_TIMEOUT, reconnect_time=None)

requirements.txt

+1-1
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,7 @@ pluggy==1.2.0;python_version<"3.8"
3939
pluggy==1.4.0;python_version>="3.8"
4040
py==1.11.0
4141
pytest==7.4.4;python_version<"3.8"
42-
pytest==8.0.2;python_version>="3.8"
42+
pytest==8.1.1;python_version>="3.8"
4343
pytest-html==2.0.1
4444
pytest-metadata==3.0.0;python_version<"3.8"
4545
pytest-metadata==3.1.1;python_version>="3.8"

seleniumbase/__version__.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,2 +1,2 @@
11
# seleniumbase package
2-
__version__ = "4.24.4"
2+
__version__ = "4.24.5"

seleniumbase/core/browser_launcher.py

+14-3
Original file line numberDiff line numberDiff line change
@@ -169,6 +169,9 @@ def extend_driver(driver):
169169
driver.assert_text = DM.assert_text
170170
driver.assert_exact_text = DM.assert_exact_text
171171
driver.wait_for_element = DM.wait_for_element
172+
driver.wait_for_element_visible = DM.wait_for_element_visible
173+
driver.wait_for_element_present = DM.wait_for_element_present
174+
driver.wait_for_selector = DM.wait_for_selector
172175
driver.wait_for_text = DM.wait_for_text
173176
driver.wait_for_exact_text = DM.wait_for_exact_text
174177
driver.wait_for_and_accept_alert = DM.wait_for_and_accept_alert
@@ -186,6 +189,7 @@ def extend_driver(driver):
186189
driver.get_user_agent = DM.get_user_agent
187190
driver.highlight = DM.highlight
188191
driver.highlight_click = DM.highlight_click
192+
driver.highlight_if_visible = DM.highlight_if_visible
189193
driver.sleep = time.sleep
190194
driver.get_attribute = DM.get_attribute
191195
driver.get_page_source = DM.get_page_source
@@ -458,27 +462,34 @@ def uc_click(
458462
by = "css selector"
459463
except Exception:
460464
pass
461-
element = driver.wait_for_element(selector, by=by, timeout=timeout)
465+
element = driver.wait_for_selector(selector, by=by, timeout=timeout)
466+
if not element.tag_name == "span": # Element must be "visible"
467+
element = driver.wait_for_element(selector, by=by, timeout=timeout)
462468
try:
463469
element.uc_click(
464470
driver, selector, by=by, reconnect_time=reconnect_time
465471
)
466472
except ElementClickInterceptedException:
473+
time.sleep(0.16)
467474
driver.js_click(selector, by=by, timeout=timeout)
475+
if not reconnect_time:
476+
driver.reconnect(0.1)
477+
else:
478+
driver.reconnect(reconnect_time)
468479

469480

470481
def uc_switch_to_frame(driver, frame, reconnect_time=None):
471482
from selenium.webdriver.remote.webelement import WebElement
472483
if isinstance(frame, WebElement):
473484
if not reconnect_time:
474-
driver.reconnect(0.15)
485+
driver.reconnect(0.1)
475486
else:
476487
driver.reconnect(reconnect_time)
477488
driver.switch_to.frame(frame)
478489
else:
479490
iframe = driver.locator(frame)
480491
if not reconnect_time:
481-
driver.reconnect(0.15)
492+
driver.reconnect(0.1)
482493
else:
483494
driver.reconnect(reconnect_time)
484495
driver.switch_to.frame(iframe)

seleniumbase/core/sb_driver.py

+19
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,15 @@ def assert_exact_text(self, *args, **kwargs):
9797
def wait_for_element(self, *args, **kwargs):
9898
return page_actions.wait_for_element(self.driver, *args, **kwargs)
9999

100+
def wait_for_element_visible(self, *args, **kwargs):
101+
return page_actions.wait_for_element(self.driver, *args, **kwargs)
102+
103+
def wait_for_element_present(self, *args, **kwargs):
104+
return page_actions.wait_for_selector(self.driver, *args, **kwargs)
105+
106+
def wait_for_selector(self, *args, **kwargs):
107+
return page_actions.wait_for_selector(self.driver, *args, **kwargs)
108+
100109
def wait_for_text(self, *args, **kwargs):
101110
return page_actions.wait_for_text(self.driver, *args, **kwargs)
102111

@@ -147,6 +156,8 @@ def get_user_agent(self, *args, **kwargs):
147156
return js_utils.get_user_agent(self.driver, *args, **kwargs)
148157

149158
def highlight(self, *args, **kwargs):
159+
if "scroll" in kwargs:
160+
kwargs.pop("scroll")
150161
w_args = kwargs.copy()
151162
if "loops" in w_args:
152163
w_args.pop("loops")
@@ -161,8 +172,16 @@ def highlight_click(self, *args, **kwargs):
161172
self.highlight(*args, **kwargs)
162173
if "loops" in kwargs:
163174
kwargs.pop("loops")
175+
if "scroll" in kwargs:
176+
kwargs.pop("scroll")
164177
page_actions.click(self.driver, *args, **kwargs)
165178

179+
def highlight_if_visible(
180+
self, selector, by="css selector", loops=4, scroll=True
181+
):
182+
if self.is_element_visible(selector, by=by):
183+
self.highlight(selector, by=by, loops=loops, scroll=scroll)
184+
166185
def switch_to_frame(self, frame):
167186
if isinstance(frame, WebElement):
168187
self.driver.switch_to.frame(frame)

seleniumbase/fixtures/base_case.py

+13
Original file line numberDiff line numberDiff line change
@@ -5601,6 +5601,14 @@ def highlight_type(
56015601
self.__highlight(selector, by=by, loops=loops, scroll=scroll)
56025602
self.update_text(selector, text, by=by)
56035603

5604+
def highlight_if_visible(
5605+
self, selector, by="css selector", loops=4, scroll=True,
5606+
):
5607+
"""Highlights the element if the element is visible."""
5608+
self.__check_scope()
5609+
if self.is_element_visible(selector, by=by):
5610+
self.__highlight(selector, by=by, loops=loops, scroll=scroll)
5611+
56045612
def __highlight(
56055613
self, selector, by="css selector", loops=None, scroll=True
56065614
):
@@ -9089,6 +9097,11 @@ def locator(self, selector, by="css selector", timeout=None):
90899097
The element does not need be visible (it may be hidden)."""
90909098
return self.wait_for_element_present(selector, by=by, timeout=timeout)
90919099

9100+
def wait_for_selector(self, selector, by="css selector", timeout=None):
9101+
"""Same as wait_for_element_present() - returns the element.
9102+
The element does not need be visible (it may be hidden)."""
9103+
return self.wait_for_element_present(selector, by=by, timeout=timeout)
9104+
90929105
def wait_for_query_selector(
90939106
self, selector, by="css selector", timeout=None
90949107
):

seleniumbase/fixtures/page_actions.py

+21
Original file line numberDiff line numberDiff line change
@@ -1752,6 +1752,27 @@ def wait_for_element(
17521752
)
17531753

17541754

1755+
def wait_for_selector(
1756+
driver,
1757+
selector,
1758+
by="css selector",
1759+
timeout=settings.LARGE_TIMEOUT,
1760+
):
1761+
original_selector = None
1762+
if page_utils.is_valid_by(by):
1763+
original_selector = selector
1764+
elif page_utils.is_valid_by(selector):
1765+
original_selector = by
1766+
selector, by = page_utils.recalculate_selector(selector, by)
1767+
return wait_for_element_present(
1768+
driver=driver,
1769+
selector=selector,
1770+
by=by,
1771+
timeout=timeout,
1772+
original_selector=original_selector,
1773+
)
1774+
1775+
17551776
def wait_for_text(
17561777
driver,
17571778
text,

seleniumbase/undetected/__init__.py

+22
Original file line numberDiff line numberDiff line change
@@ -442,6 +442,28 @@ def reconnect(self, timeout=0.1):
442442
except Exception:
443443
pass
444444

445+
def disconnect(self):
446+
"""Stops the chromedriver service that runs in the background.
447+
To use driver methods again, you MUST call driver.connect()"""
448+
if hasattr(self, "service"):
449+
try:
450+
self.service.stop()
451+
except Exception:
452+
pass
453+
454+
def connect(self):
455+
"""Starts the chromedriver service that runs in the background
456+
and recreates the session."""
457+
if hasattr(self, "service"):
458+
try:
459+
self.service.start()
460+
except Exception:
461+
pass
462+
try:
463+
self.start_session()
464+
except Exception:
465+
pass
466+
445467
def start_session(self, capabilities=None):
446468
if not capabilities:
447469
capabilities = self.options.to_capabilities()

setup.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -187,7 +187,7 @@
187187
'pluggy==1.4.0;python_version>="3.8"',
188188
"py==1.11.0",
189189
'pytest==7.4.4;python_version<"3.8"',
190-
'pytest==8.0.2;python_version>="3.8"',
190+
'pytest==8.1.1;python_version>="3.8"',
191191
"pytest-html==2.0.1", # Newer ones had issues
192192
'pytest-metadata==3.0.0;python_version<"3.8"',
193193
'pytest-metadata==3.1.1;python_version>="3.8"',

0 commit comments

Comments
 (0)