Skip to content

Commit

Permalink
Update CDP Mode
Browse files Browse the repository at this point in the history
  • Loading branch information
mdmintz committed Nov 30, 2024
1 parent c81ab62 commit b3aa59e
Show file tree
Hide file tree
Showing 5 changed files with 145 additions and 120 deletions.
4 changes: 4 additions & 0 deletions examples/cdp_mode/ReadMe.md
Original file line number Diff line number Diff line change
Expand Up @@ -419,6 +419,10 @@ sb.cdp.assert_text(text, selector="html")
sb.cdp.assert_exact_text(text, selector="html")
sb.cdp.assert_true()
sb.cdp.assert_false()
sb.cdp.assert_equal(first, second)
sb.cdp.assert_not_equal(first, second)
sb.cdp.assert_in(first, second)
sb.cdp.assert_not_in(first, second)
sb.cdp.scroll_into_view(selector)
sb.cdp.scroll_to_y(y)
sb.cdp.scroll_to_top()
Expand Down
4 changes: 4 additions & 0 deletions seleniumbase/core/browser_launcher.py
Original file line number Diff line number Diff line change
Expand Up @@ -703,6 +703,10 @@ def uc_open_with_cdp_mode(driver, url=None):
cdp.assert_exact_text = CDPM.assert_exact_text
cdp.assert_true = CDPM.assert_true
cdp.assert_false = CDPM.assert_false
cdp.assert_equal = CDPM.assert_equal
cdp.assert_not_equal = CDPM.assert_not_equal
cdp.assert_in = CDPM.assert_in
cdp.assert_not_in = CDPM.assert_not_in
cdp.scroll_into_view = CDPM.scroll_into_view
cdp.scroll_to_y = CDPM.scroll_to_y
cdp.scroll_to_top = CDPM.scroll_to_top
Expand Down
49 changes: 28 additions & 21 deletions seleniumbase/core/sb_cdp.py
Original file line number Diff line number Diff line change
Expand Up @@ -135,23 +135,10 @@ def find_element(
self.__add_light_pause()
selector = self.__convert_to_css_if_xpath(selector)
early_failure = False
if (":contains(" in selector):
tag_name = selector.split(":contains(")[0].split(" ")[-1]
text = selector.split(":contains(")[1].split(")")[0][1:-1]
with suppress(Exception):
self.loop.run_until_complete(
self.page.select(tag_name, timeout=timeout)
)
self.loop.run_until_complete(
self.page.find(text, timeout=timeout)
)
elements = []
with suppress(Exception):
elements = self.find_elements_by_text(text, tag_name=tag_name)
if elements:
return self.__add_sync_methods(elements[0])
else:
early_failure = True
if (":contains(") in selector:
selector, _ = page_utils.recalculate_selector(
selector, by="css selector", xp_ok=True
)
failure = False
try:
if early_failure:
Expand Down Expand Up @@ -726,12 +713,16 @@ def set_value(self, selector, text, timeout=settings.SMALL_TIMEOUT):

def evaluate(self, expression):
"""Run a JavaScript expression and return the result."""
if expression.startswith("return "):
expression = expression[len("return "):]
return self.loop.run_until_complete(
self.page.evaluate(expression)
)

def js_dumps(self, obj_name):
"""Similar to evaluate(), but for dictionary results."""
if obj_name.startswith("return "):
obj_name = obj_name[len("return "):]
return self.loop.run_until_complete(
self.page.js_dumps(obj_name)
)
Expand Down Expand Up @@ -1648,11 +1639,11 @@ def assert_text(
text = text.strip()
element = None
try:
element = self.select(selector, timeout=timeout)
element = self.find_element(selector, timeout=timeout)
except Exception:
raise Exception("Element {%s} not found!" % selector)
for i in range(30):
if self.is_element_visible(selector) and text in element.text_all:
if text in element.text_all:
return True
time.sleep(0.1)
raise Exception(
Expand Down Expand Up @@ -1683,11 +1674,27 @@ def assert_exact_text(

def assert_true(self, expression):
if not expression:
raise AssertionError("%s is not true")
raise AssertionError("%s is not true" % expression)

def assert_false(self, expression):
if expression:
raise AssertionError("%s is not false")
raise AssertionError("%s is not false" % expression)

def assert_equal(self, first, second):
if first != second:
raise AssertionError("%s is not equal to %s" % (first, second))

def assert_not_equal(self, first, second):
if first == second:
raise AssertionError("%s is equal to %s" % (first, second))

def assert_in(self, first, second):
if first not in second:
raise AssertionError("%s is not in %s" % (first, second))

def assert_not_in(self, first, second):
if first in second:
raise AssertionError("%s is in %s" % (first, second))

def scroll_into_view(self, selector):
self.find_element(selector).scroll_into_view()
Expand Down
28 changes: 15 additions & 13 deletions seleniumbase/fixtures/base_case.py
Original file line number Diff line number Diff line change
Expand Up @@ -392,7 +392,7 @@ def click(
original_by = by
selector, by = self.__recalculate_selector(selector, by)
if self.__is_cdp_swap_needed():
self.cdp.click(selector)
self.cdp.click(selector, timeout=timeout)
return
if delay and (type(delay) in [int, float]) and delay > 0:
time.sleep(delay)
Expand Down Expand Up @@ -885,7 +885,7 @@ def update_text(
timeout = self.__get_new_timeout(timeout)
selector, by = self.__recalculate_selector(selector, by)
if self.__is_cdp_swap_needed():
self.cdp.type(selector, text)
self.cdp.type(selector, text, timeout=timeout)
return
if self.__is_shadow_selector(selector):
self.__shadow_type(selector, text, timeout)
Expand Down Expand Up @@ -1112,7 +1112,7 @@ def send_keys(self, selector, text, by="css selector", timeout=None):
def press_keys(self, selector, text, by="css selector", timeout=None):
"""Use send_keys() to press one key at a time."""
if self.__is_cdp_swap_needed():
self.cdp.press_keys(selector, text)
self.cdp.press_keys(selector, text, timeout=timeout)
return
self.wait_for_ready_state_complete()
element = self.wait_for_element_present(
Expand Down Expand Up @@ -1597,7 +1597,7 @@ def click_link_text(self, link_text, timeout=None):
"""This method clicks link text on a page."""
self.__check_scope()
if self.__is_cdp_swap_needed():
self.cdp.find_element(link_text).click()
self.cdp.find_element(link_text, timeout=timeout).click()
return
self.__skip_if_esc()
if not timeout:
Expand Down Expand Up @@ -3380,6 +3380,8 @@ def open_html_file(self, html_file):

def execute_script(self, script, *args, **kwargs):
self.__check_scope()
if self.__is_cdp_swap_needed():
return self.cdp.evaluate(script)
self._check_browser()
return self.driver.execute_script(script, *args, **kwargs)

Expand Down Expand Up @@ -6308,7 +6310,7 @@ def js_click(
If "all_matches" is False, only the first match is clicked.
If "scroll" is False, won't scroll unless running in Demo Mode."""
if self.__is_cdp_swap_needed():
self.cdp.click(selector)
self.cdp.click(selector, timeout=timeout)
return
self.wait_for_ready_state_complete()
if not timeout or timeout is True:
Expand Down Expand Up @@ -8245,7 +8247,7 @@ def enter_mfa_code(
timeout = settings.SMALL_TIMEOUT
if self.__is_cdp_swap_needed():
mfa_code = self.get_mfa_code(totp_key)
self.cdp.type(selector, mfa_code + "\n")
self.cdp.type(selector, mfa_code + "\n", timeout=timeout)
return
self.wait_for_element_visible(selector, by=by, timeout=timeout)
if self.recorder_mode and self.__current_url_is_recordable():
Expand Down Expand Up @@ -9003,7 +9005,7 @@ def wait_for_element_visible(
original_selector = selector
selector, by = self.__recalculate_selector(selector, by)
if self.__is_cdp_swap_needed():
return self.cdp.select(selector)
return self.cdp.select(selector, timeout=timeout)
if self.__is_shadow_selector(selector):
return self.__get_shadow_element(selector, timeout)
return page_actions.wait_for_element_visible(
Expand All @@ -9026,7 +9028,7 @@ def wait_for_element_clickable(
original_selector = selector
selector, by = self.__recalculate_selector(selector, by)
if self.__is_cdp_swap_needed():
return self.cdp.select(selector)
return self.cdp.select(selector, timeout=timeout)
elif self.__is_shadow_selector(selector):
# If a shadow selector, use visible instead of clickable
return self.__wait_for_shadow_element_visible(selector, timeout)
Expand Down Expand Up @@ -9427,7 +9429,7 @@ def wait_for_element_present(
original_selector = selector
selector, by = self.__recalculate_selector(selector, by)
if self.__is_cdp_swap_needed():
return self.cdp.select(selector)
return self.cdp.select(selector, timeout=timeout)
elif self.__is_shadow_selector(selector):
return self.__wait_for_shadow_element_present(selector, timeout)
return page_actions.wait_for_element_present(
Expand All @@ -9449,7 +9451,7 @@ def wait_for_element(self, selector, by="css selector", timeout=None):
original_selector = selector
selector, by = self.__recalculate_selector(selector, by)
if self.__is_cdp_swap_needed():
return self.cdp.select(selector)
return self.cdp.select(selector, timeout=timeout)
if self.recorder_mode and self.__current_url_is_recordable():
if self.get_session_storage_item("pause_recorder") == "no":
if by == By.XPATH:
Expand Down Expand Up @@ -9492,7 +9494,7 @@ def wait_for_query_selector(
timeout = self.__get_new_timeout(timeout)
css_selector = self.convert_to_css_selector(selector, by=by)
if self.__is_cdp_swap_needed():
return self.cdp.select(css_selector)
return self.cdp.select(css_selector, timeout=timeout)
return js_utils.wait_for_css_query_selector(
self.driver, css_selector, timeout
)
Expand Down Expand Up @@ -9713,7 +9715,7 @@ def wait_for_text_visible(
text = self.__get_type_checked_text(text)
selector, by = self.__recalculate_selector(selector, by)
if self.__is_cdp_swap_needed():
return self.cdp.find_element(selector)
return self.cdp.find_element(selector, timeout=timeout)
elif self.__is_shadow_selector(selector):
return self.__wait_for_shadow_text_visible(text, selector, timeout)
return page_actions.wait_for_text_visible(
Expand Down Expand Up @@ -10093,7 +10095,7 @@ def assert_link_text(self, link_text, timeout=None):
if self.timeout_multiplier and timeout == settings.SMALL_TIMEOUT:
timeout = self.__get_new_timeout(timeout)
if self.__is_cdp_swap_needed():
self.cdp.find_element(link_text)
self.cdp.find_element(link_text, timeout=timeout)
return
self.wait_for_link_text_visible(link_text, timeout=timeout)
if self.demo_mode:
Expand Down
Loading

0 comments on commit b3aa59e

Please sign in to comment.