Update SeleniumBase Visual Testing

This commit is contained in:
Michael Mintz 2022-08-17 02:07:39 -04:00
parent 5f4a611669
commit bcc5208bf8
2 changed files with 132 additions and 57 deletions

View File

@ -1,4 +1,5 @@
import os
from seleniumbase.core import log_helper
from seleniumbase.fixtures import constants
VISUAL_BASELINE_DIR = constants.VisualBaseline.STORAGE_FOLDER
@ -17,3 +18,91 @@ def visual_baseline_folder_setup():
os.makedirs(visual_baseline_path)
except Exception:
pass # Should only be reachable during multi-threaded runs
def get_sbs_head():
head = (
'<head><meta charset="utf-8">'
'<meta name="viewport" content="shrink-to-fit=no">'
'<link rel="shortcut icon" href="%s">'
"<title>Visual Comparison</title>"
"</head>" % (constants.SideBySide.SIDE_BY_SIDE_PNG)
)
return head
def get_sbs_table_row(baseline="baseline.png", diff="baseline_diff.png"):
row = (
'<tbody class="compare results-table-row">'
'<tr style="background-color: #F4F4FE;">'
'<td><img src="%s" width="100%%" /></td>'
'<td><img src="%s" width="100%%" /></td>'
"</tr></tbody>"
"" % (baseline, diff)
)
return row
def get_sbs_table_html(baseline="baseline.png", diff="baseline_diff.png"):
table_html = (
'<table border="3px solid #E6E6E6;" width="100%;" padding: 12px;'
' font-size="16px;" text-align="left;" id="results-table"'
' style="background-color: #FAFAFA;">'
'<thead id="results-table-head">'
"<tr>"
'<th style="background-color: rgba(0, 128, 0, 0.25);"'
' col="baseline">Baseline Screenshot</th>'
'<th style="background-color: rgba(128, 0, 0, 0.25);"'
' col="failure">Visual Diff Failure Screenshot</th>'
"</tr></thead>"
)
row = get_sbs_table_row(baseline, diff)
table_html += row
table_html += "</table>"
return table_html
def get_sbs_gen_by():
gen_by = (
'<p><div>Generated by: <b><a href="https://seleniumbase.io/">'
"SeleniumBase</a></b></div></p><p></p>"
)
return gen_by
def get_sbs_header_text():
header_text = "SeleniumBase Visual Comparison"
return header_text
def get_sbs_header():
header_text = get_sbs_header_text()
header = '<h3 align="center">%s</h3>' % header_text
return header
def get_sbs_footer():
footer = "<br /><b>Last updated:</b> "
timestamp, the_date, the_time = log_helper.get_master_time()
last_updated = "%s at %s" % (the_date, the_time)
footer = footer + "%s" % last_updated
gen_by = get_sbs_gen_by()
footer = footer + gen_by
return footer
def get_sbs_html(baseline="baseline.png", diff="baseline_diff.png"):
head = get_sbs_head()
header = get_sbs_header()
table_html = get_sbs_table_html(baseline, diff)
footer = get_sbs_footer()
the_html = (
'<html lang="en">'
+ head
+ '<body style="background-color: #FCFCF4;">'
+ header
+ table_html
+ footer
+ "</body>"
)
return the_html

View File

@ -105,6 +105,7 @@ class BaseCase(unittest.TestCase):
self.__start_time_ms = None
self.__requests_timeout = None
self.__screenshot_count = 0
self.__level_0_visual_f = False
self.__will_be_skipped = False
self.__passed_then_skipped = False
self.__visual_baseline_copies = []
@ -10957,56 +10958,10 @@ class BaseCase(unittest.TestCase):
self.__create_log_path_as_needed(test_logpath)
shutil.copy(latest_png_path, latest_copy_path)
if len(self.__visual_baseline_copies) != 1:
return # Only possible when deferred visual asserts are used
head = (
'<head><meta charset="utf-8">'
'<meta name="viewport" content="shrink-to-fit=no">'
'<link rel="shortcut icon" href="%s">'
"<title>Visual Comparison</title>"
"</head>" % (constants.SideBySide.SIDE_BY_SIDE_PNG)
)
table_html = (
'<table border="3px solid #E6E6E6;" width="100%;" padding: 12px;'
' font-size="16px;" text-align="left;" id="results-table"'
' style="background-color: #FAFAFA;">'
'<thead id="results-table-head">'
"<tr>"
'<th style="background-color: rgba(0, 128, 0, 0.25);"'
' col="baseline">Baseline Screenshot</th>'
'<th style="background-color: rgba(128, 0, 0, 0.25);"'
' col="failure">Visual Diff Failure Screenshot</th>'
"</tr></thead>"
)
row = (
'<tbody class="compare results-table-row">'
'<tr style="background-color: #F4F4FE;">'
'<td><img src="%s" width="100%%" /></td>'
'<td><img src="%s" width="100%%" /></td>'
"</tr></tbody>"
"" % ("baseline.png", "baseline_diff.png")
)
header_text = "SeleniumBase Visual Comparison"
header = '<h3 align="center">%s</h3>' % header_text
table_html += row
table_html += "</table>"
footer = "<br /><b>Last updated:</b> "
timestamp, the_date, the_time = log_helper.get_master_time()
last_updated = "%s at %s" % (the_date, the_time)
footer = footer + "%s" % last_updated
gen_by = (
'<p><div>Generated by: <b><a href="https://seleniumbase.io/">'
"SeleniumBase</a></b></div></p><p></p>"
)
footer = footer + gen_by
the_html = (
'<html lang="en">'
+ head
+ '<body style="background-color: #FCFCF4;">'
+ header
+ table_html
+ footer
+ "</body>"
)
return # Skip the rest when deferred visual asserts are used
from seleniumbase.core import visual_helper
the_html = visual_helper.get_sbs_html()
file_path = os.path.join(test_logpath, constants.SideBySide.HTML_FILE)
out_file = codecs.open(file_path, "w+", encoding="utf-8")
out_file.writelines(the_html)
@ -11120,15 +11075,15 @@ class BaseCase(unittest.TestCase):
visual_helper.visual_baseline_folder_setup()
baseline_dir = constants.VisualBaseline.STORAGE_FOLDER
visual_baseline_path = baseline_dir + "/" + test_id + "/" + name
page_url_file = visual_baseline_path + "/page_url.txt"
visual_baseline_path = os.path.join(baseline_dir, test_id, name)
page_url_file = os.path.join(visual_baseline_path, "page_url.txt")
baseline_png = "baseline.png"
baseline_png_path = visual_baseline_path + "/%s" % baseline_png
baseline_png_path = os.path.join(visual_baseline_path, baseline_png)
latest_png = "latest.png"
latest_png_path = visual_baseline_path + "/%s" % latest_png
level_1_file = visual_baseline_path + "/tags_level_1.txt"
level_2_file = visual_baseline_path + "/tags_level_2.txt"
level_3_file = visual_baseline_path + "/tags_level_3.txt"
latest_png_path = os.path.join(visual_baseline_path, latest_png)
level_1_file = os.path.join(visual_baseline_path, "tags_level_1.txt")
level_2_file = os.path.join(visual_baseline_path, "tags_level_2.txt")
level_3_file = os.path.join(visual_baseline_path, "tags_level_3.txt")
set_baseline = False
if baseline or self.visual_baseline:
@ -11188,6 +11143,7 @@ class BaseCase(unittest.TestCase):
)
self.__visual_baseline_copies.append(baseline_copy_tuple)
is_level_0_failure = False
if not set_baseline:
self.save_screenshot(
latest_png, visual_baseline_path, selector="body"
@ -11287,9 +11243,38 @@ class BaseCase(unittest.TestCase):
)
except Exception as e:
print(e) # Level-0 Dry Run (Only print the differences)
is_level_0_failure = True
unittest.TestCase.maxDiff = None # Reset unittest.TestCase.maxDiff
# Since the check passed, do not save an extra copy of the baseline
del self.__visual_baseline_copies[-1] # .pop() returns the element
if is_level_0_failure:
# Generating the side_by_side.html file for Level-0 failures
test_logpath = os.path.join(self.log_path, self.__get_test_id())
if (
not os.path.exists(baseline_path)
or not os.path.exists(latest_png_path)
):
return
self.__level_0_visual_f = True
if not os.path.exists(test_logpath):
self.__create_log_path_as_needed(test_logpath)
baseline_copy_path = os.path.join(test_logpath, baseline_copy_name)
latest_copy_path = os.path.join(test_logpath, latest_copy_name)
if (
not os.path.exists(baseline_copy_path)
and not os.path.exists(latest_copy_path)
):
shutil.copy(baseline_path, baseline_copy_path)
shutil.copy(latest_png_path, latest_copy_path)
the_html = visual_helper.get_sbs_html(
baseline_copy_name, latest_copy_name
)
alpha_n_d_name = "".join([x if x.isalnum() else "_" for x in name])
side_by_side_name = "side_by_side_%s.html" % alpha_n_d_name
file_path = os.path.join(test_logpath, side_by_side_name)
out_file = codecs.open(file_path, "w+", encoding="utf-8")
out_file.writelines(the_html)
out_file.close()
############
@ -13102,6 +13087,7 @@ class BaseCase(unittest.TestCase):
has_exception
or self.save_screenshot_after_test
or self.__screenshot_count > 0
or self.__level_0_visual_f
or self.__will_be_skipped
):
sb_config._d_t_log_path[test_id] = os.path.join(log_dir, ft_id)