Skip to content

Commit 27ad030

Browse files
authored
Merge pull request #654 from seleniumbase/better-error-handling-and-pkg-updates
Improve error-handling and update Python dependencies
2 parents db1923a + 9a28c2d commit 27ad030

File tree

7 files changed

+100
-45
lines changed

7 files changed

+100
-45
lines changed

examples/github_test.py

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,8 +10,9 @@ def test_github(self):
1010
# To avoid this automation blocker, two steps are being taken:
1111
# 1. self.slow_click() is being used to slow down Selenium actions.
1212
# 2. The browser's User Agent is modified to avoid Selenium-detection
13-
# when running in headless mode on Chrome.
14-
if self.browser == "chrome" and self.headless:
13+
# when running in headless mode on Chrome or Edge (Chromium).
14+
if self.headless and (
15+
self.browser == "chrome" or self.browser == "edge"):
1516
self.driver.quit()
1617
self.get_new_driver(
1718
agent="""Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_4) """

examples/test_apple_site.py

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
# -*- coding: utf-8 -*-
21
from seleniumbase import BaseCase
32

43

@@ -8,6 +7,13 @@ def test_apple_developer_site_webdriver_instructions(self):
87
self.demo_mode = True
98
self.demo_sleep = 0.5
109
self.message_duration = 2.0
10+
if self.headless and (
11+
self.browser == "chrome" or self.browser == "edge"):
12+
self.driver.quit()
13+
self.get_new_driver(
14+
agent="""Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_4) """
15+
"""AppleWebKit/537.36 (KHTML, like Gecko) """
16+
"""Chrome/75.0.3770.100 Safari/537.36""")
1117
self.open("https://developer.apple.com/search/")
1218
title = "Testing with WebDriver in Safari"
1319
self.type('[placeholder*="developer.apple.com"]', title + "\n")

examples/test_tinymce.py

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
import re
2+
from seleniumbase import BaseCase
3+
4+
5+
class MyTestClass(BaseCase):
6+
7+
def click_menu_item(self, text):
8+
self.sleep(0.2)
9+
soup = self.get_beautiful_soup(self.get_page_source())
10+
pattern = re.compile('%s' % text)
11+
the_id = soup.find(text=pattern).parent.parent.attrs["id"]
12+
self.click("#%s" % the_id)
13+
14+
def test_base(self):
15+
self.open("https://seleniumbase.io/other/tinymce")
16+
self.wait_for_element("div.mce-container-body")
17+
self.click_menu_item("File")
18+
self.click_menu_item("New document")
19+
self.click_menu_item("Paragraph")
20+
self.click_menu_item("Heading 2")
21+
self.switch_to_frame("iframe#mce_1_ifr")
22+
self.send_keys("#tinymce", "Automate anything with SeleniumBase!\n")
23+
self.switch_to_default_content()
24+
self.click('button i.mce-i-image')
25+
self.type('input[aria-label="Width"].mce-textbox', "300")
26+
image_url = "https://seleniumbase.io/img/sb_logo_10.png"
27+
self.type("input.mce-textbox", image_url + "\n")
28+
self.switch_to_frame("iframe#mce_1_ifr")
29+
self.click("h2")
30+
self.switch_to_default_content()
31+
self.post_message("Automate anything with SeleniumBase!")
32+
self.click_menu_item("File")
33+
self.click_menu_item("Preview")
34+
self.switch_to_frame('iframe[sandbox="allow-scripts"]')
35+
self.post_message("Learn SeleniumBase Today!")

requirements.txt

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ packaging>=20.4
33
setuptools>=44.1.1;python_version<"3.5"
44
setuptools>=49.6.0;python_version>="3.5"
55
setuptools-scm>=4.1.2
6-
wheel>=0.35.0
6+
wheel>=0.35.1
77
six==1.15.0
88
nose==1.3.7
99
ipdb==0.13.3
@@ -21,7 +21,7 @@ py==1.8.1;python_version<"3.5"
2121
py==1.9.0;python_version>="3.5"
2222
pytest==4.6.11;python_version<"3.5"
2323
pytest==6.0.1;python_version>="3.5"
24-
pytest-cov==2.10.0
24+
pytest-cov==2.10.1
2525
pytest-forked==1.3.0
2626
pytest-html==1.22.1;python_version<"3.6"
2727
pytest-html==2.0.1;python_version>="3.6"
@@ -30,7 +30,8 @@ pytest-metadata==1.10.0;python_version>="3.6"
3030
pytest-ordering==0.6
3131
pytest-rerunfailures==8.0;python_version<"3.6"
3232
pytest-rerunfailures==9.0;python_version>="3.6"
33-
pytest-xdist==1.34.0
33+
pytest-xdist==1.34.0;python_version<"3.5"
34+
pytest-xdist==2.0.0;python_version>="3.5"
3435
parameterized==0.7.4
3536
soupsieve==1.9.6;python_version<"3.5"
3637
soupsieve==2.0.1;python_version>="3.5"
@@ -57,6 +58,6 @@ flake8==3.8.3;python_version>="3.5"
5758
pyflakes==2.1.1;python_version<"3.5"
5859
pyflakes==2.2.0;python_version>="3.5"
5960
certifi>=2020.6.20
60-
allure-pytest==2.8.17
61+
allure-pytest==2.8.18
6162
pdfminer.six==20191110;python_version<"3.5"
6263
pdfminer.six==20200726;python_version>="3.5"

seleniumbase/fixtures/base_case.py

Lines changed: 40 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,14 @@ def __init__(self, *args, **kwargs):
9797

9898
def open(self, url):
9999
""" Navigates the current browser window to the specified page. """
100+
if type(url) is str:
101+
url = url.strip() # Remove leading and trailing whitespace
102+
if (type(url) is not str) or not self.__looks_like_a_page_url(url):
103+
# url should start with one of the following:
104+
# "http:", "https:", "://", "data:", "file:",
105+
# "about:", "chrome:", "opera:", or "edge:".
106+
msg = 'Did you forget to prefix your URL with "http:" or "https:"?'
107+
raise Exception('Invalid URL: "%s"\n%s' % (url, msg))
100108
self.__last_page_load_url = None
101109
js_utils.clear_out_console_logs(self.driver)
102110
if url.startswith("://"):
@@ -5797,9 +5805,10 @@ def __looks_like_a_page_url(self, url):
57975805
navigate to the page if a URL is detected, but will instead call
57985806
self.get_element(URL_AS_A_SELECTOR) if the input in not a URL. """
57995807
if (url.startswith("http:") or url.startswith("https:") or (
5800-
url.startswith("://") or url.startswith("data:") or (
5801-
url.startswith("about:") or url.startswith("chrome:") or (
5802-
url.startswith("file:"))))):
5808+
url.startswith("://") or url.startswith("chrome:") or (
5809+
url.startswith("about:") or url.startswith("data:") or (
5810+
url.startswith("file:") or url.startswith("edge:") or (
5811+
url.startswith("opera:")))))):
58035812
return True
58045813
else:
58055814
return False
@@ -6367,6 +6376,34 @@ def tearDown(self):
63676376
You'll need to add the following line to the subclass's tearDown():
63686377
super(SubClassOfBaseCase, self).tearDown()
63696378
"""
6379+
try:
6380+
with_selenium = self.with_selenium
6381+
except Exception:
6382+
sub_class_name = str(
6383+
self.__class__.__bases__[0]).split('.')[-1].split("'")[0]
6384+
sub_file_name = str(self.__class__.__bases__[0]).split('.')[-2]
6385+
sub_file_name = sub_file_name + ".py"
6386+
class_name = str(self.__class__).split('.')[-1].split("'")[0]
6387+
file_name = str(self.__class__).split('.')[-2] + ".py"
6388+
class_name_used = sub_class_name
6389+
file_name_used = sub_file_name
6390+
if sub_class_name == "BaseCase":
6391+
class_name_used = class_name
6392+
file_name_used = file_name
6393+
fix_setup = "super(%s, self).setUp()" % class_name_used
6394+
fix_teardown = "super(%s, self).tearDown()" % class_name_used
6395+
message = ("You're overriding SeleniumBase's BaseCase setUp() "
6396+
"method with your own setUp() method, which breaks "
6397+
"SeleniumBase. You can fix this by going to your "
6398+
"%s class located in your %s file and adding the "
6399+
"following line of code AT THE BEGINNING of your "
6400+
"setUp() method:\n%s\n\nAlso make sure "
6401+
"you have added the following line of code AT THE "
6402+
"END of your tearDown() method:\n%s\n"
6403+
% (class_name_used, file_name_used,
6404+
fix_setup, fix_teardown))
6405+
raise Exception(message)
6406+
# *** Start tearDown() officially ***
63706407
self.__slow_mode_pause_if_active()
63716408
has_exception = self.__has_exception()
63726409
if self.__deferred_assert_failures:
@@ -6381,33 +6418,6 @@ def tearDown(self):
63816418
if self.is_pytest:
63826419
# pytest-specific code
63836420
test_id = self.__get_test_id()
6384-
try:
6385-
with_selenium = self.with_selenium
6386-
except Exception:
6387-
sub_class_name = str(
6388-
self.__class__.__bases__[0]).split('.')[-1].split("'")[0]
6389-
sub_file_name = str(self.__class__.__bases__[0]).split('.')[-2]
6390-
sub_file_name = sub_file_name + ".py"
6391-
class_name = str(self.__class__).split('.')[-1].split("'")[0]
6392-
file_name = str(self.__class__).split('.')[-2] + ".py"
6393-
class_name_used = sub_class_name
6394-
file_name_used = sub_file_name
6395-
if sub_class_name == "BaseCase":
6396-
class_name_used = class_name
6397-
file_name_used = file_name
6398-
fix_setup = "super(%s, self).setUp()" % class_name_used
6399-
fix_teardown = "super(%s, self).tearDown()" % class_name_used
6400-
message = ("You're overriding SeleniumBase's BaseCase setUp() "
6401-
"method with your own setUp() method, which breaks "
6402-
"SeleniumBase. You can fix this by going to your "
6403-
"%s class located in your %s file and adding the "
6404-
"following line of code AT THE BEGINNING of your "
6405-
"setUp() method:\n%s\n\nAlso make sure "
6406-
"you have added the following line of code AT THE "
6407-
"END of your tearDown() method:\n%s\n"
6408-
% (class_name_used, file_name_used,
6409-
fix_setup, fix_teardown))
6410-
raise Exception(message)
64116421
if with_selenium:
64126422
# Save a screenshot if logging is on when an exception occurs
64136423
if has_exception:

seleniumbase/fixtures/page_utils.py

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -106,9 +106,10 @@ def is_valid_url(url):
106106
r'\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3})' # ...or ip
107107
r'(?::\d+)?' # optional port
108108
r'(?:/?|[/?]\S+)$', re.IGNORECASE)
109-
if regex.match(url) or ((url.startswith('about:') or (
110-
url.startswith('data:') or url.startswith('chrome:')))
111-
and " " not in url):
109+
if regex.match(url) or ((url.startswith("about:") or (
110+
url.startswith("data:") or url.startswith("chrome:") or (
111+
url.startswith("edge:") or url.startswith("opera:") or (
112+
url.startswith("file:")))))):
112113
return True
113114
else:
114115
return False

setup.py

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -54,7 +54,7 @@
5454

5555
setup(
5656
name='seleniumbase',
57-
version='1.46.4',
57+
version='1.46.5',
5858
description='Web Automation and Test Framework - https://seleniumbase.io',
5959
long_description=long_description,
6060
long_description_content_type='text/markdown',
@@ -95,7 +95,7 @@
9595
'setuptools>=44.1.1;python_version<"3.5"',
9696
'setuptools>=49.6.0;python_version>="3.5"',
9797
'setuptools-scm',
98-
'wheel>=0.35.0',
98+
'wheel>=0.35.1',
9999
'six',
100100
'nose',
101101
'ipdb',
@@ -113,7 +113,7 @@
113113
'py==1.9.0;python_version>="3.5"',
114114
'pytest==4.6.11;python_version<"3.5"',
115115
'pytest==6.0.1;python_version>="3.5"',
116-
'pytest-cov==2.10.0',
116+
'pytest-cov==2.10.1',
117117
'pytest-forked==1.3.0',
118118
'pytest-html==1.22.1;python_version<"3.6"',
119119
'pytest-html==2.0.1;python_version>="3.6"',
@@ -122,7 +122,8 @@
122122
'pytest-ordering==0.6',
123123
'pytest-rerunfailures==8.0;python_version<"3.6"',
124124
'pytest-rerunfailures==9.0;python_version>="3.6"',
125-
'pytest-xdist==1.34.0',
125+
'pytest-xdist==1.34.0;python_version<"3.5"',
126+
'pytest-xdist==2.0.0;python_version>="3.5"',
126127
'parameterized==0.7.4',
127128
'soupsieve==1.9.6;python_version<"3.5"',
128129
'soupsieve==2.0.1;python_version>="3.5"',
@@ -149,7 +150,7 @@
149150
'pyflakes==2.1.1;python_version<"3.5"',
150151
'pyflakes==2.2.0;python_version>="3.5"',
151152
'certifi>=2020.6.20',
152-
'allure-pytest==2.8.17',
153+
'allure-pytest==2.8.18',
153154
'pdfminer.six==20191110;python_version<"3.5"',
154155
'pdfminer.six==20200726;python_version>="3.5"',
155156
],

0 commit comments

Comments
 (0)