Skip to content

Commit 1dba6ee

Browse files
authored
Merge pull request #596 from seleniumbase/sb-mkfile
Massive Release with Lots of Changes
2 parents 9b761f7 + 7381e47 commit 1dba6ee

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

56 files changed

+1710
-775
lines changed

README.md

Lines changed: 14 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,11 @@
11
<meta property="og:site_name" content="SeleniumBase | Docs">
2-
<meta property="og:title" content="SeleniumBase | Reliable Test Automation" />
3-
<meta property="og:description" content="Simple browser automation and testing with Python." />
4-
<meta property="og:image" content="https://seleniumbase.io/img/sb_logo_7.png" />
2+
<meta property="og:title" content="SeleniumBase | Easy Test Automation" />
3+
<meta property="og:description" content="Browser automation and testing with Python." />
4+
<meta property="og:image" content="https://seleniumbase.io/img/sb_logo_10.png" />
55
<link rel="icon" href="https://seleniumbase.io/img/logo3a.png" />
66

77
<p align="center"><a href="https://github.com/seleniumbase/SeleniumBase/">
8-
<img src="https://seleniumbase.io/img/sb_logo_7.png" alt="SeleniumBase" width="260" />
8+
<img src="https://seleniumbase.io/img/sb_logo_10.png" alt="SeleniumBase" width="260" />
99
</a></p>
1010
<p align="center">
1111
<b>Everything you need to test websites.</b>
@@ -68,7 +68,7 @@ python setup.py install
6868
```
6969
If multiple versions of Python are installed, be specific (E.g. use ``python3`` instead of ``python``).
7070

71-
* You can also install ``seleniumbase`` from [pypi](https://pypi.python.org/pypi/seleniumbase):
71+
* You can also install ``seleniumbase`` from [pypi](https://pypi.python.org/pypi/seleniumbase).
7272
```bash
7373
pip install seleniumbase
7474
```
@@ -112,17 +112,17 @@ from seleniumbase import BaseCase
112112
class MyTestClass(BaseCase):
113113

114114
def test_basic(self):
115+
self.open("https://store.xkcd.com/search")
116+
self.type('input[name="q"]', "xkcd book\n")
117+
self.assert_text("xkcd: volume 0", "h3")
115118
self.open("https://xkcd.com/353/")
116119
self.assert_title("xkcd: Python")
117120
self.assert_element('img[alt="Python"]')
118121
self.click('a[rel="license"]')
119122
self.assert_text("free to copy and reuse")
120123
self.go_back()
121-
self.click("link=About")
122-
self.assert_text("xkcd.com", "h2")
123-
self.open("://store.xkcd.com/collections/everything")
124-
self.update_text("input.search-input", "xkcd book\n")
125-
self.assert_exact_text("xkcd: volume 0", "h3")
124+
self.click_link_text("About")
125+
self.assert_exact_text("xkcd.com", "h2")
126126
```
127127

128128
* By default, **[CSS Selectors](https://www.w3schools.com/cssref/css_selectors.asp)** are used for finding page elements.
@@ -132,7 +132,7 @@ class MyTestClass(BaseCase):
132132
```python
133133
self.open(URL) # Navigate to the web page
134134
self.click(SELECTOR) # Click a page element
135-
self.update_text(SELECTOR, TEXT) # Type text (Add "\n" to text for pressing enter/return.)
135+
self.type(SELECTOR, TEXT) # Type text (Add "\n" to text for pressing enter/return.)
136136
self.assert_element(SELECTOR) # Assert element is visible
137137
self.assert_text(TEXT) # Assert text is visible (has optional SELECTOR arg)
138138
self.assert_title(PAGE_TITLE) # Assert page title
@@ -163,7 +163,7 @@ SeleniumBase automatically handles common WebDriver actions such as spinning up
163163
SeleniumBase uses simple syntax for commands, such as:
164164

165165
```python
166-
self.update_text("input", "dogs\n")
166+
self.type("input", "dogs\n")
167167
```
168168

169169
The same command with regular WebDriver is very messy:
@@ -523,10 +523,10 @@ self.click("div#my_id")
523523

524524
<h4>Typing Text</h4>
525525

526-
self.update_text(selector, text) # updates the text from the specified element with the specified value. An exception is raised if the element is missing or if the text field is not editable. Example:
526+
self.type(selector, text) # updates the text from the specified element with the specified value. An exception is raised if the element is missing or if the text field is not editable. Example:
527527

528528
```python
529-
self.update_text("input#id_value", "2012")
529+
self.type("input#id_value", "2012")
530530
```
531531
You can also use self.add_text() or the WebDriver .send_keys() command, but those won't clear the text box first if there's already text inside.
532532
If you want to type in special keys, that's easy too. Here's an example:

docs/img/sb_logo_10.png

58.7 KB
Loading

examples/basic_test.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -8,9 +8,9 @@
88
class MyTestClass(BaseCase):
99

1010
def test_basic(self):
11+
self.open("https://store.xkcd.com/search")
12+
self.type('input[name="q"]', "xkcd book\n")
1113
self.open("https://xkcd.com/353/")
1214
self.click('a[rel="license"]')
1315
self.go_back()
14-
self.click("link=About")
15-
self.open("://store.xkcd.com/collections/everything")
16-
self.update_text("input.search-input", "xkcd book\n")
16+
self.click_link_text("About")

examples/boilerplates/samples/google_test.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ class GoogleTests(BaseCase):
1010

1111
def test_google_dot_com(self):
1212
self.open('https://google.com/ncr')
13-
self.update_text(HomePage.search_box, 'github')
13+
self.type(HomePage.search_box, 'github')
1414
self.assert_element(HomePage.list_box)
1515
self.assert_element(HomePage.search_button)
1616
self.assert_element(HomePage.feeling_lucky_button)

examples/github_test.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ def test_github(self):
1818
"""AppleWebKit/537.36 (KHTML, like Gecko) """
1919
"""Chrome/75.0.3770.100 Safari/537.36""")
2020
self.open("https://github.com/")
21-
self.update_text("input.header-search-input", "SeleniumBase\n")
21+
self.type("input.header-search-input", "SeleniumBase\n")
2222
self.slow_click('a[href="/seleniumbase/SeleniumBase"]')
2323
self.assert_element("div.repository-content")
2424
self.assert_text("SeleniumBase", "h1")

examples/master_qa/masterqa_test_1.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,8 +16,8 @@ def test_xkcd(self):
1616
self.verify("Can you find the moon?")
1717
self.click('a[rel="next"]')
1818
self.verify("Do the drones look safe?")
19-
self.open("https://store.xkcd.com/collections/everything")
20-
self.update_text("input.search-input", "book\n")
19+
self.open("https://store.xkcd.com/search")
20+
self.type("input.search-input", "book\n")
2121
self.verify("Do you see books in the search results?")
2222
self.open("https://xkcd.com/213/")
2323
for i in range(5):

examples/my_first_test.py

Lines changed: 57 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -4,17 +4,17 @@
44
class MyTestClass(BaseCase):
55

66
def test_basic(self):
7+
self.open("https://store.xkcd.com/search")
8+
self.type('input[name="q"]', "xkcd book\n")
9+
self.assert_text("xkcd: volume 0", "h3")
710
self.open("https://xkcd.com/353/")
811
self.assert_title("xkcd: Python")
912
self.assert_element('img[alt="Python"]')
1013
self.click('a[rel="license"]')
1114
self.assert_text("free to copy and reuse")
1215
self.go_back()
13-
self.click("link=About")
14-
self.assert_text("xkcd.com", "h2")
15-
self.open("://store.xkcd.com/collections/everything")
16-
self.update_text("input.search-input", "xkcd book\n")
17-
self.assert_exact_text("xkcd: volume 0", "h3")
16+
self.click_link_text("About")
17+
self.assert_exact_text("xkcd.com", "h2")
1818

1919
####
2020

@@ -23,14 +23,17 @@ def test_basic(self):
2323
# **** NOTES / USEFUL INFO ****
2424
#
2525
# 1. By default, CSS Selectors are used to identify elements.
26-
# Other options include: "LINK_TEXT", "PARTIAL_LINK_TEXT", "NAME",
26+
# CSS Guide: "https://www.w3schools.com/cssref/css_selectors.asp".
27+
# Other selectors include: "LINK_TEXT", "PARTIAL_LINK_TEXT", "NAME",
2728
# "CLASS_NAME", and "ID", but most of those can be expressed as CSS.
29+
#
2830
# Here's an example of changing the "by":
2931
# [
3032
# from selenium.webdriver.common.by import By
3133
# ...
3234
# self.click('Next', by=By.PARTIAL_LINK_TEXT)
3335
# ]
36+
#
3437
# XPath is used by default if the arg starts with "/", "./", or "(":
3538
# [
3639
# self.click('/html/body/div[3]/div[4]/p[2]/a')
@@ -39,27 +42,46 @@ def test_basic(self):
3942
# If you're completely new to CSS selectors, right-click on a
4043
# web page and select "Inspect" to see the CSS in the html.
4144
#
42-
# 2. Most methods have the optional `timeout` argument. Ex:
45+
# 2. Most methods have the optional "timeout" argument.
46+
# Here's an example of changing the "timeout":
4347
# [
4448
# self.assert_element('img[alt="Python"]', timeout=15)
4549
# ]
46-
# The `timeout` argument tells the method how many seconds to wait
47-
# for an element to appear before raising an exception. This is
50+
# The "timeout" argument tells the method how many seconds to wait
51+
# for an element to appear before failing the test. This is
4852
# useful if a web page needs additional time to load an element.
49-
# If you don't specify a `timeout`, a default timeout is used.
53+
# If you don't specify a "timeout", a default timeout is used.
5054
# Default timeouts are configured in seleniumbase/config/settings.py
5155
#
52-
# 3. SeleniumBase methods are very versatile. For example,
53-
# self.update_text(SELECTOR, TEXT) does the following:
54-
# * Waits for the element to be visible
55-
# * Waits for the element to be interactive
56-
# * Clears the text field
57-
# * Types in the new text
58-
# * Hits Enter/Submit (if the text ends in "\n")
56+
# 3. SeleniumBase methods often perform multiple actions. For example,
57+
# self.type(SELECTOR, TEXT) will do the following:
58+
# * Wait for the element to be visible
59+
# * Wait for the element to be interactive
60+
# * Clear the text field
61+
# * Type in the new text
62+
# * Press Enter/Submit if the text ends in "\n"
5963
#
60-
# self.update_text(S, T) can also be written as self.input(S, T)
64+
# 4. Duplicate method names may exist for the same method:
65+
# (This makes it easier to switch over from other test frameworks.)
66+
# Example:
67+
# self.open() = self.visit() = self.open_url() = self.goto()
68+
# self.type() = self.update_text() = self.input()
69+
# self.send_keys() = self.add_text()
70+
# self.get_element() = self.wait_for_element_present()
71+
# self.find_element() = self.wait_for_element_visible()
72+
# = self.wait_for_element()
73+
# self.assert_element() = self.assert_element_visible()
74+
# self.assert_text() = self.assert_text_visible()
75+
# self.find_text() = self.wait_for_text_visible()
76+
# = self.wait_for_text()
77+
# self.click_link_text(text) = self.click(link=text)
78+
# = self.click_link(text)
79+
# * self.get(url) is SPECIAL: *
80+
# If {url} is a valid URL, self.get() works just like self.open()
81+
# Otherwise {url} becomes a selector for calling self.get_element()
6182
#
62-
# 4. There's usually more than one way to do the same thing. Ex:
83+
# 5. There's usually more than one way to do the same thing.
84+
# Example 1:
6385
# [
6486
# self.assert_text("xkcd: volume 0", "h3")
6587
# ]
@@ -68,33 +90,37 @@ def test_basic(self):
6890
# text = self.get_text("h3")
6991
# self.assert_true("xkcd: volume 0" in text)
7092
# ]
71-
# Or:
93+
# Is also the same as:
7294
# [
73-
# text = self.find_element("h3").text
95+
# element = self.find_element("h3")
96+
# text = element.text
7497
# self.assert_true("xkcd: volume 0" in text)
7598
# ]
7699
#
77-
# And the following line:
100+
# Example 2:
101+
# [
102+
# self.assert_exact_text("xkcd.com", "h2")
103+
# ]
104+
# Is the same as:
105+
# [
106+
# text = self.get_text("h2").strip()
107+
# self.assert_true("xkcd.com".strip() == text)
108+
# ]
109+
#
110+
# Example 3:
78111
# [
79112
# title = self.get_attribute("#comic img", "title")
80113
# ]
81-
# Can also be written as:
114+
# Is the same as:
82115
# [
83116
# element = self.find_element("#comic img")
84117
# title = element.get_attribute("title")
85118
# ]
86119
#
87-
# 5. self.assert_exact_text(TEXT) ignores leading and trailing
120+
# 6. self.assert_exact_text(TEXT) ignores leading and trailing
88121
# whitespace in the TEXT assertion.
89122
# So, self.assert_exact_text("Some Text") will find [" Some Text "].
90123
#
91-
# 6. For backwards-compatibilty, some SeleniumBase methods that do the
92-
# same thing have multiple names, kept on from previous versions.
93-
# Ex: self.wait_for_element() is the same as self.find_element().
94-
# Both search for and return the element, and raise an exception if
95-
# the element does not appear on the page within the timeout limit.
96-
# And self.assert_element() does this too (without returning it).
97-
#
98124
# 7. If a URL starts with "://", then "https://" is automatically used.
99125
# Example: [self.open("://URL")] becomes [self.open("https://URL")]
100126
# This helps by reducing the line length by 5 characters.

examples/offline_examples/test_demo_page.py

Lines changed: 7 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -21,10 +21,10 @@ def test_demo_page(self):
2121
# Assert that the text appears within a given element
2222
self.assert_text("Demo Page", "h1")
2323

24-
# Update the text of various text fields on the page
25-
self.update_text("#myTextInput", "This is Automated")
26-
self.update_text("textarea.area1", "Testing Time!\n")
27-
self.update_text('[name="preText2"]', "Typing Text!")
24+
# Type/update text in text fields on the page
25+
self.type("#myTextInput", "This is Automated")
26+
self.type("textarea.area1", "Testing Time!\n")
27+
self.type('[name="preText2"]', "Typing Text!")
2828

2929
# Verify that a hover dropdown link changes page text
3030
self.assert_text("Automation Practice", "h3")
@@ -92,9 +92,8 @@ def test_demo_page(self):
9292
# Assert link text - Use click_link_text() to click
9393
self.assert_link_text("seleniumbase.com")
9494
self.assert_link_text("SeleniumBase on GitHub")
95-
96-
# Assert the title of the current web page
97-
self.assert_link_text("seleniumbase.com")
98-
self.assert_link_text("SeleniumBase on GitHub")
9995
self.assert_link_text("seleniumbase.io")
10096
self.assert_link_text("SeleniumBase Demo Page")
97+
98+
# Assert exact text
99+
self.assert_exact_text("Demo Page", "h1")

examples/parameterized_test.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,6 @@ class GoogleTestClass(BaseCase):
1111
])
1212
def test_parameterized_google_search(self, search_term, expected_text):
1313
self.open('https://google.com/ncr')
14-
self.update_text('input[title="Search"]', search_term + '\n')
14+
self.type('input[title="Search"]', search_term + '\n')
1515
self.assert_element('#result-stats')
1616
self.assert_text(expected_text, '#search')

examples/swag_labs_suite.py

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -10,8 +10,8 @@ def login(self, username="standard_user"):
1010
self.open("https://www.saucedemo.com/")
1111
if username not in self.get_text("#login_credentials"):
1212
self.fail("Invalid user for login: %s" % username)
13-
self.update_text("#user-name", username)
14-
self.update_text("#password", "secret_sauce")
13+
self.type("#user-name", username)
14+
self.type("#password", "secret_sauce")
1515
self.click('input[type="submit"]')
1616
self.assert_element("#inventory_container")
1717
self.assert_text("Products", "div.product_label")
@@ -58,9 +58,9 @@ def test_swag_labs_basic_functional_flow(self, username):
5858
self.click("link=CHECKOUT")
5959
self.assert_exact_text("Checkout: Your Information", "div.subheader")
6060
self.assert_element("a.cart_cancel_link")
61-
self.update_text("#first-name", "SeleniumBase")
62-
self.update_text("#last-name", "Rocks")
63-
self.update_text("#postal-code", "01720")
61+
self.type("#first-name", "SeleniumBase")
62+
self.type("#last-name", "Rocks")
63+
self.type("#postal-code", "01720")
6464

6565
# Checkout - Overview
6666
self.click("input.btn_primary")

examples/test_apple_site.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ def test_apple_developer_site_webdriver_instructions(self):
1010
self.message_duration = 2.0
1111
self.open("https://developer.apple.com/search/")
1212
title = "Testing with WebDriver in Safari"
13-
self.update_text('[placeholder*="developer.apple.com"]', title + "\n")
13+
self.type('[placeholder*="developer.apple.com"]', title + "\n")
1414
self.click("link=%s" % title)
1515
self.assert_element('[href="/documentation"]')
1616
self.assert_text(title, "h1")

examples/test_demo_site.py

Lines changed: 10 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -15,10 +15,10 @@ def test_demo_site(self):
1515
# Assert that the text appears within a given element
1616
self.assert_text("Demo Page", "h1")
1717

18-
# Update the text of various text fields on the page
19-
self.update_text("#myTextInput", "This is Automated")
20-
self.update_text("textarea.area1", "Testing Time!\n")
21-
self.update_text('[name="preText2"]', "Typing Text!")
18+
# Type/update text in text fields on the page
19+
self.type("#myTextInput", "This is Automated")
20+
self.type("textarea.area1", "Testing Time!\n")
21+
self.type('[name="preText2"]', "Typing Text!")
2222

2323
# Verify that a hover dropdown link changes page text
2424
self.assert_text("Automation Practice", "h3")
@@ -93,3 +93,9 @@ def test_demo_site(self):
9393

9494
# Assert exact text
9595
self.assert_exact_text("Demo Page", "h1")
96+
97+
# Assert no broken links
98+
self.assert_no_404_errors()
99+
100+
# Assert no JavaScript errors
101+
self.assert_no_js_errors()

examples/test_event_firing.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,6 @@ def test_event_firing_webdriver(self):
3333
print("\n* EventFiringWebDriver example *")
3434
self.open("https://xkcd.com/1862/")
3535
self.click("link=About")
36-
self.open("https://store.xkcd.com/collections/everything")
37-
self.update_text("input.search-input", "xkcd book\n")
36+
self.open("https://store.xkcd.com/search")
37+
self.type('input[name="q"]', "xkcd book\n")
3838
self.open("https://xkcd.com/1822/")

examples/test_hack_search.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ def test_hack_search(self):
1313
self.assert_element('input[title="Search"]')
1414
self.set_attribute('[action="/search"]', "action", "//bing.com/search")
1515
self.set_attributes('[value="Google Search"]', "value", "Bing Search")
16-
self.update_text('input[title="Search"]', "SeleniumBase GitHub")
16+
self.type('input[title="Search"]', "SeleniumBase GitHub")
1717
self.click('[value="Bing Search"]')
1818
self.assert_element("h1.b_logo")
1919
self.click('[href*="github.com/seleniumbase/SeleniumBase"]')

0 commit comments

Comments
 (0)