seleniumbase 4.48.4__tar.gz → 4.49.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (163) hide show
  1. {seleniumbase-4.48.4/seleniumbase.egg-info → seleniumbase-4.49.0}/PKG-INFO +86 -36
  2. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/README.md +73 -23
  3. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/requirements.txt +9 -9
  4. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/__version__.py +1 -1
  5. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/fixtures/base_case.py +13 -0
  6. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/undetected/__init__.py +7 -2
  7. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/undetected/cdp_driver/cdp_util.py +3 -0
  8. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/undetected/cdp_driver/config.py +51 -3
  9. {seleniumbase-4.48.4 → seleniumbase-4.49.0/seleniumbase.egg-info}/PKG-INFO +86 -36
  10. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase.egg-info/requires.txt +10 -10
  11. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/setup.py +30 -12
  12. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/.gitignore +0 -0
  13. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/LICENSE +0 -0
  14. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/MANIFEST.in +0 -0
  15. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/install.sh +0 -0
  16. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/pyproject.toml +0 -0
  17. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/pytest.ini +0 -0
  18. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/sbase/__init__.py +0 -0
  19. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/sbase/__main__.py +0 -0
  20. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/sbase/steps.py +0 -0
  21. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/__init__.py +0 -0
  22. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/__main__.py +0 -0
  23. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/behave/__init__.py +0 -0
  24. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/behave/behave_helper.py +0 -0
  25. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/behave/behave_sb.py +0 -0
  26. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/behave/steps.py +0 -0
  27. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/common/__init__.py +0 -0
  28. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/common/decorators.py +0 -0
  29. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/common/encryption.py +0 -0
  30. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/common/exceptions.py +0 -0
  31. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/common/obfuscate.py +0 -0
  32. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/common/unobfuscate.py +0 -0
  33. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/config/__init__.py +0 -0
  34. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/config/ad_block_list.py +0 -0
  35. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/config/proxy_list.py +0 -0
  36. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/config/settings.py +0 -0
  37. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/console_scripts/__init__.py +0 -0
  38. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/console_scripts/logo_helper.py +0 -0
  39. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/console_scripts/rich_helper.py +0 -0
  40. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/console_scripts/run.py +0 -0
  41. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/console_scripts/sb_behave_gui.py +0 -0
  42. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/console_scripts/sb_caseplans.py +0 -0
  43. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/console_scripts/sb_commander.py +0 -0
  44. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/console_scripts/sb_install.py +0 -0
  45. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/console_scripts/sb_mkchart.py +0 -0
  46. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/console_scripts/sb_mkdir.py +0 -0
  47. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/console_scripts/sb_mkfile.py +0 -0
  48. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/console_scripts/sb_mkpres.py +0 -0
  49. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/console_scripts/sb_mkrec.py +0 -0
  50. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/console_scripts/sb_objectify.py +0 -0
  51. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/console_scripts/sb_print.py +0 -0
  52. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/console_scripts/sb_recorder.py +0 -0
  53. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/__init__.py +0 -0
  54. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/application_manager.py +0 -0
  55. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/browser_launcher.py +0 -0
  56. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/capabilities_parser.py +0 -0
  57. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/colored_traceback.py +0 -0
  58. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/create_db_tables.sql +0 -0
  59. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/detect_b_ver.py +0 -0
  60. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/download_helper.py +0 -0
  61. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/encoded_images.py +0 -0
  62. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/jqc_helper.py +0 -0
  63. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/log_helper.py +0 -0
  64. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/mysql.py +0 -0
  65. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/nest_asyncio.py +0 -0
  66. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/proxy_helper.py +0 -0
  67. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/recorder_helper.py +0 -0
  68. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/report_helper.py +0 -0
  69. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/s3_manager.py +0 -0
  70. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/sb_cdp.py +0 -0
  71. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/sb_driver.py +0 -0
  72. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/session_helper.py +0 -0
  73. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/settings_parser.py +0 -0
  74. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/style_sheet.py +0 -0
  75. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/testcase_manager.py +0 -0
  76. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/tour_helper.py +0 -0
  77. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/core/visual_helper.py +0 -0
  78. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/drivers/__init__.py +0 -0
  79. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/drivers/atlas_drivers/__init__.py +0 -0
  80. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/drivers/brave_drivers/__init__.py +0 -0
  81. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/drivers/cft_drivers/__init__.py +0 -0
  82. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/drivers/chromium_drivers/__init__.py +0 -0
  83. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/drivers/chs_drivers/__init__.py +0 -0
  84. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/drivers/comet_drivers/__init__.py +0 -0
  85. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/drivers/opera_drivers/__init__.py +0 -0
  86. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/extensions/__init__.py +0 -0
  87. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/extensions/ad_block.zip +0 -0
  88. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/extensions/disable_csp.zip +0 -0
  89. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/extensions/recorder.zip +0 -0
  90. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/extensions/sbase_ext.zip +0 -0
  91. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/fixtures/__init__.py +0 -0
  92. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/fixtures/constants.py +0 -0
  93. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/fixtures/css_to_xpath.py +0 -0
  94. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/fixtures/errors.py +0 -0
  95. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/fixtures/js_utils.py +0 -0
  96. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/fixtures/page_actions.py +0 -0
  97. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/fixtures/page_utils.py +0 -0
  98. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/fixtures/shared_utils.py +0 -0
  99. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/fixtures/unittest_helper.py +0 -0
  100. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/fixtures/words.py +0 -0
  101. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/fixtures/xpath_to_css.py +0 -0
  102. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/js_code/__init__.py +0 -0
  103. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/js_code/active_css_js.py +0 -0
  104. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/js_code/live_js.py +0 -0
  105. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/js_code/recorder_js.py +0 -0
  106. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/masterqa/__init__.py +0 -0
  107. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/masterqa/master_qa.py +0 -0
  108. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/plugins/__init__.py +0 -0
  109. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/plugins/base_plugin.py +0 -0
  110. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/plugins/basic_test_info.py +0 -0
  111. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/plugins/db_reporting_plugin.py +0 -0
  112. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/plugins/driver_manager.py +0 -0
  113. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/plugins/page_source.py +0 -0
  114. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/plugins/pytest_plugin.py +0 -0
  115. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/plugins/s3_logging_plugin.py +0 -0
  116. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/plugins/sb_manager.py +0 -0
  117. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/plugins/screen_shots.py +0 -0
  118. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/plugins/selenium_plugin.py +0 -0
  119. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/resources/__init__.py +0 -0
  120. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/translate/__init__.py +0 -0
  121. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/translate/chinese.py +0 -0
  122. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/translate/dutch.py +0 -0
  123. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/translate/french.py +0 -0
  124. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/translate/italian.py +0 -0
  125. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/translate/japanese.py +0 -0
  126. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/translate/korean.py +0 -0
  127. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/translate/master_dict.py +0 -0
  128. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/translate/portuguese.py +0 -0
  129. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/translate/russian.py +0 -0
  130. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/translate/spanish.py +0 -0
  131. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/translate/translator.py +0 -0
  132. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/undetected/cdp.py +0 -0
  133. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/undetected/cdp_driver/__init__.py +0 -0
  134. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/undetected/cdp_driver/_contradict.py +0 -0
  135. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/undetected/cdp_driver/browser.py +0 -0
  136. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/undetected/cdp_driver/connection.py +0 -0
  137. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/undetected/cdp_driver/element.py +0 -0
  138. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/undetected/cdp_driver/tab.py +0 -0
  139. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/undetected/dprocess.py +0 -0
  140. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/undetected/options.py +0 -0
  141. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/undetected/patcher.py +0 -0
  142. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/undetected/reactor.py +0 -0
  143. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/undetected/webelement.py +0 -0
  144. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/utilities/__init__.py +0 -0
  145. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/utilities/selenium_grid/__init__.py +0 -0
  146. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/utilities/selenium_grid/download_selenium_server.py +0 -0
  147. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/utilities/selenium_grid/font_color +0 -0
  148. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/utilities/selenium_grid/grid-hub +0 -0
  149. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/utilities/selenium_grid/grid-node +0 -0
  150. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/utilities/selenium_grid/grid_hub.py +0 -0
  151. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/utilities/selenium_grid/grid_node.py +0 -0
  152. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/utilities/selenium_grid/register-grid-node.bat +0 -0
  153. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/utilities/selenium_grid/register-grid-node.sh +0 -0
  154. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/utilities/selenium_grid/start-grid-hub.bat +0 -0
  155. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/utilities/selenium_grid/start-grid-hub.sh +0 -0
  156. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/utilities/selenium_ide/__init__.py +0 -0
  157. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase/utilities/selenium_ide/convert_ide.py +0 -0
  158. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase.egg-info/SOURCES.txt +0 -0
  159. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase.egg-info/dependency_links.txt +0 -0
  160. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase.egg-info/entry_points.txt +0 -0
  161. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/seleniumbase.egg-info/top_level.txt +0 -0
  162. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/setup.cfg +0 -0
  163. {seleniumbase-4.48.4 → seleniumbase-4.49.0}/virtualenv_install.sh +0 -0
@@ -1,7 +1,7 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: seleniumbase
3
- Version: 4.48.4
4
- Summary: A complete web automation framework for end-to-end testing.
3
+ Version: 4.49.0
4
+ Summary: Stealthy automation (via CDP Mode) that passes every bot detection test with any Chromium browser you want. Includes a test framework.
5
5
  Home-page: https://github.com/seleniumbase/SeleniumBase
6
6
  Author: Michael Mintz
7
7
  Author-email: mdmintz@gmail.com
@@ -16,7 +16,7 @@ Project-URL: PyPI, https://pypi.org/project/seleniumbase/
16
16
  Project-URL: Source, https://github.com/seleniumbase/SeleniumBase
17
17
  Project-URL: Repository, https://github.com/seleniumbase/SeleniumBase
18
18
  Project-URL: Documentation, https://seleniumbase.io/
19
- Keywords: pytest,selenium,framework,automation,browser,testing,webdriver,seleniumbase,sbase,crawling,scraping
19
+ Keywords: pytest,selenium,framework,automation,browser,testing,webdriver,seleniumbase,sbase,web-crawling,web-scraping,scraping,stealth,chromium,playwright,anti-detect,antidetect,undetected,bot-detection,fingerprint,recaptcha,cloudflare,turnstile,datadome,captcha,headless
20
20
  Platform: Windows
21
21
  Platform: Linux
22
22
  Platform: Mac OS-X
@@ -59,7 +59,7 @@ Requires-Python: >=3.9
59
59
  Description-Content-Type: text/markdown
60
60
  License-File: LICENSE
61
61
  Requires-Dist: pip>=26.0.1; python_version < "3.10"
62
- Requires-Dist: pip>=26.1; python_version >= "3.10"
62
+ Requires-Dist: pip>=26.1.1; python_version >= "3.10"
63
63
  Requires-Dist: packaging>=26.2
64
64
  Requires-Dist: setuptools~=70.2; python_version < "3.10"
65
65
  Requires-Dist: setuptools>=82.0.1; python_version >= "3.10"
@@ -81,7 +81,7 @@ Requires-Dist: sbvirtualdisplay>=1.4.0
81
81
  Requires-Dist: MarkupSafe>=3.0.3
82
82
  Requires-Dist: Jinja2>=3.1.6
83
83
  Requires-Dist: six>=1.17.0
84
- Requires-Dist: parse>=1.21.1
84
+ Requires-Dist: parse>=1.22.0
85
85
  Requires-Dist: parse-type>=0.6.6
86
86
  Requires-Dist: colorama>=0.4.6
87
87
  Requires-Dist: pyyaml>=6.0.3
@@ -89,12 +89,12 @@ Requires-Dist: pygments>=2.20.0
89
89
  Requires-Dist: pyreadline3>=3.5.4; platform_system == "Windows"
90
90
  Requires-Dist: tabcompleter>=1.4.1
91
91
  Requires-Dist: pdbp>=1.8.2
92
- Requires-Dist: idna>=3.13
92
+ Requires-Dist: idna>=3.15
93
93
  Requires-Dist: charset-normalizer<4,>=3.4.7
94
94
  Requires-Dist: urllib3<2,>=1.26.20; python_version < "3.10"
95
- Requires-Dist: urllib3<3,>=1.26.20; python_version >= "3.10"
95
+ Requires-Dist: urllib3<3,>=2.7.0; python_version >= "3.10"
96
96
  Requires-Dist: requests~=2.32.5; python_version < "3.10"
97
- Requires-Dist: requests~=2.33.1; python_version >= "3.10"
97
+ Requires-Dist: requests~=2.34.2; python_version >= "3.10"
98
98
  Requires-Dist: sniffio==1.3.1
99
99
  Requires-Dist: h11==0.16.0
100
100
  Requires-Dist: outcome==1.3.0.post0
@@ -105,7 +105,7 @@ Requires-Dist: wsproto==1.2.0; python_version < "3.10"
105
105
  Requires-Dist: wsproto~=1.3.2; python_version >= "3.10"
106
106
  Requires-Dist: websocket-client~=1.9.0
107
107
  Requires-Dist: selenium==4.32.0; python_version < "3.10"
108
- Requires-Dist: selenium==4.43.0; python_version >= "3.10"
108
+ Requires-Dist: selenium==4.44.0; python_version >= "3.10"
109
109
  Requires-Dist: cssselect==1.3.0; python_version < "3.10"
110
110
  Requires-Dist: cssselect<2,>=1.4.0; python_version >= "3.10"
111
111
  Requires-Dist: sortedcontainers==2.4.0
@@ -120,7 +120,7 @@ Requires-Dist: pytest-html==4.0.2
120
120
  Requires-Dist: pytest-metadata==3.1.1
121
121
  Requires-Dist: pytest-ordering==0.6
122
122
  Requires-Dist: pytest-rerunfailures==16.0.1; python_version < "3.10"
123
- Requires-Dist: pytest-rerunfailures==16.1; python_version >= "3.10"
123
+ Requires-Dist: pytest-rerunfailures==16.2; python_version >= "3.10"
124
124
  Requires-Dist: pytest-xdist==3.8.0
125
125
  Requires-Dist: parameterized==0.9.0
126
126
  Requires-Dist: behave==1.2.6
@@ -130,7 +130,7 @@ Requires-Dist: pyotp==2.9.0
130
130
  Requires-Dist: python-xlib==0.33; platform_system == "Linux"
131
131
  Requires-Dist: PyAutoGUI>=0.9.54; platform_system == "Linux"
132
132
  Requires-Dist: markdown-it-py==3.0.0; python_version < "3.10"
133
- Requires-Dist: markdown-it-py==4.0.0; python_version >= "3.10"
133
+ Requires-Dist: markdown-it-py==4.2.0; python_version >= "3.10"
134
134
  Requires-Dist: mdurl==0.1.2
135
135
  Requires-Dist: rich<16,>=15.0.0
136
136
  Provides-Extra: allure
@@ -139,7 +139,7 @@ Requires-Dist: allure-python-commons>=2.13.5; extra == "allure"
139
139
  Requires-Dist: allure-behave>=2.13.5; extra == "allure"
140
140
  Provides-Extra: coverage
141
141
  Requires-Dist: coverage>=7.10.7; python_version < "3.10" and extra == "coverage"
142
- Requires-Dist: coverage>=7.13.5; python_version >= "3.10" and extra == "coverage"
142
+ Requires-Dist: coverage>=7.14.0; python_version >= "3.10" and extra == "coverage"
143
143
  Requires-Dist: pytest-cov>=7.1.0; extra == "coverage"
144
144
  Provides-Extra: flake8
145
145
  Requires-Dist: flake8==7.3.0; extra == "flake8"
@@ -154,7 +154,7 @@ Requires-Dist: mss==10.2.0; extra == "mss"
154
154
  Provides-Extra: pdfminer
155
155
  Requires-Dist: pdfminer.six==20251107; python_version < "3.10" and extra == "pdfminer"
156
156
  Requires-Dist: pdfminer.six==20260107; python_version >= "3.10" and extra == "pdfminer"
157
- Requires-Dist: cryptography==47.0.0; extra == "pdfminer"
157
+ Requires-Dist: cryptography==48.0.0; extra == "pdfminer"
158
158
  Requires-Dist: cffi==2.0.0; extra == "pdfminer"
159
159
  Requires-Dist: pycparser==2.23; python_version < "3.10" and extra == "pdfminer"
160
160
  Requires-Dist: pycparser==3.0; python_version >= "3.10" and extra == "pdfminer"
@@ -212,24 +212,29 @@ Dynamic: summary
212
212
 
213
213
  <p align="center"><a href="https://github.com/seleniumbase/SeleniumBase/"><img src="https://seleniumbase.github.io/cdn/img/nice_logo_8t.png" alt="SeleniumBase" width="424" /></a></p>
214
214
 
215
- <p align="center" class="hero__title"><b>All-in-one Browser Automation Framework:<br />Web Crawling / Testing / Scraping / Stealth</b></p>
216
-
217
- <p align="center"><a href="https://pypi.python.org/pypi/seleniumbase" target="_blank"><img src="https://img.shields.io/pypi/v/seleniumbase.svg?color=3399EE" alt="PyPI version" /></a> <a href="https://github.com/seleniumbase/SeleniumBase/actions" target="_blank"><img src="https://github.com/seleniumbase/SeleniumBase/workflows/CI%20build/badge.svg" alt="SeleniumBase GitHub Actions" /></a> <a href="https://seleniumbase.io"><img src="https://img.shields.io/badge/docs-seleniumbase.io-11BBAA.svg" alt="SeleniumBase Docs" /></a> <a href="https://pepy.tech/projects/seleniumbase?timeRange=threeMonths&category=version&includeCIDownloads=true&granularity=daily&viewType=line&versions=*" target="_blank"><img src="https://static.pepy.tech/badge/seleniumbase" alt="SeleniumBase PyPI downloads" /></a> <a href="https://discord.gg/EdhQTn3EyE" target="_blank"><img src="https://img.shields.io/discord/727927627830001734?color=7289DA&label=Discord&logo=discord&logoColor=white"/></a></p>
215
+ <p align="center"><a href="https://pypi.python.org/pypi/seleniumbase" target="_blank"><img src="https://img.shields.io/pypi/v/seleniumbase.svg?color=3399EE" alt="PyPI version" /></a> <a href="https://pepy.tech/projects/seleniumbase?timeRange=threeMonths&category=version&includeCIDownloads=true&granularity=daily&viewType=line&versions=*" target="_blank"><img src="https://static.pepy.tech/badge/seleniumbase" alt="SeleniumBase PyPI downloads" /></a> <a href="https://discord.gg/EdhQTn3EyE" target="_blank"><img src="https://img.shields.io/discord/727927627830001734?color=7289DA&label=Discord&logo=discord&logoColor=white"/></a><br /> <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/LICENSE"><img src="https://img.shields.io/badge/license-MIT-22BBCC.svg" title="SeleniumBase" /></a> <a href="https://github.com/seleniumbase/SeleniumBase/actions" target="_blank"><img src="https://github.com/seleniumbase/SeleniumBase/workflows/CI%20build/badge.svg" alt="SeleniumBase GitHub Actions" /></a> <a href="https://seleniumbase.io"><img src="https://img.shields.io/badge/docs-seleniumbase.io-11BBAA.svg" alt="SeleniumBase Docs" /></a></p>
218
216
  <p align="center"></p>
219
217
 
218
+ <h3 align="center">Stealthy automation that passes every bot detection test.</h3>
219
+
220
+ <table align="center"><tr><td>
221
+ <b>Verified using multiple different Chromium browsers:<br />Chrome, Chrome-for-Testing, Chromium, Edge, Brave.</b>
222
+ </td></tr></table>
223
+
224
+
220
225
  <p align="center">
221
226
  <a href="#python_installation">🚀 Start</a> |
222
227
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/features_list.md">🏰 Features</a> |
223
228
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/customizing_test_runs.md">🎛️ Options</a> |
224
229
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/ReadMe.md">📚 Examples</a> |
225
- <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/seleniumbase/console_scripts/ReadMe.md">🪄 Scripts</a> |
226
- <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/mobile_testing.md">📱 Mobile</a>
230
+ <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/seleniumbase/console_scripts/ReadMe.md">💻 Scripts</a> |
231
+ <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/locale_codes.md">🗾 Locale</a>
227
232
  <br />
228
- <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/method_summary.md">📘 The API</a> |
229
- <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/syntax_formats.md"> 🔠 SyntaxFormats</a> |
233
+ <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/method_summary.md">📗 API</a> |
234
+ <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/cdp_mode_methods.md">📘 Stealth API</a> |
235
+ <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/syntax_formats.md"> 🔠 DesignPatterns</a> |
230
236
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/recorder_mode.md">🔴 Recorder</a> |
231
- <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/example_logs/ReadMe.md">📊 Dashboard</a> |
232
- <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/locale_codes.md">🗾 Locale</a>
237
+ <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/example_logs/ReadMe.md">📊 Dashboard</a>
233
238
  <br />
234
239
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/commander.md">🎖️ GUI</a> |
235
240
  <a href="https://seleniumbase.io/demo_page">📰 TestPage</a> |
@@ -245,7 +250,7 @@ Dynamic: summary
245
250
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/tour_examples/ReadMe.md">🚎 Tours</a>
246
251
  <br />
247
252
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/integrations/github/workflows/ReadMe.md">🤖 CI/CD</a> |
248
- <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/js_package_manager.md">❇️ JSMgr</a> |
253
+ <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/js_package_manager.md">🟨 JSMgr</a> |
249
254
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/translations.md">🌏 Translator</a> |
250
255
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/presenter/ReadMe.md">🎞️ Presenter</a> |
251
256
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/visual_testing/ReadMe.md">🖼️ Visual</a> |
@@ -253,9 +258,7 @@ Dynamic: summary
253
258
  <br />
254
259
  </p>
255
260
 
256
- 📊 <a href="https://github.com/seleniumbase/SeleniumBase/"><b translate="no">SeleniumBase</b></a> is a complete framework for browser automation and testing with Python and <a href="https://docs.pytest.org/en/latest/how-to/usage.html">pytest</a>. Includes stealth options and other advanced features.
257
-
258
- 🐙 Stealth modes: <a translate="no" href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/uc_mode.md">UC Mode</a> and <a translate="no" href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/ReadMe.md"><b>CDP Mode</b></a> can bypass bot-detection, handle CAPTCHAs, and call methods from the <a href="https://chromedevtools.github.io/devtools-protocol/" translate="no">Chrome Devtools Protocol</a>. CDP Mode includes <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/playwright/ReadMe.md"><b><span translate="no">Stealthy Playwright Mode</span></b></a>, which makes Playwright stealthy.
261
+ 🐙 <a translate="no" href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/ReadMe.md"><b>CDP Mode</b></a> bypasses bot-detection and handles CAPTCHAs by driving the browser directly through the <a href="https://chromedevtools.github.io/devtools-protocol/" translate="no">Chrome DevTools Protocol</a>. Includes <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/playwright/ReadMe.md"><b><span translate="no">Stealthy Playwright Mode</span></b></a>, which extends these advanced anti-detection patches to Playwright scripts.
259
262
 
260
263
  📚 The [SeleniumBase/examples/](https://github.com/seleniumbase/SeleniumBase/tree/master/examples) folder includes over 100 ready-to-run examples. Examples that start with `test_` or end with `_test.py`/`_tests.py` are specifically designed to run with `pytest`. Other examples run directly with raw `python` (those files generally start with `raw_` to avoid confusion).
261
264
 
@@ -265,13 +268,62 @@ Dynamic: summary
265
268
 
266
269
  <h3 align="left">⚙️ Stealthy architecture flowchart:</h3>
267
270
 
268
- <img src="https://seleniumbase.github.io/other/sb_stealth.png" width="596" alt="Stealthy architecture flowchart" />
271
+ <img src="https://seleniumbase.github.io/other/sb_architecture.png" width="596" alt="Stealthy architecture flowchart" />
269
272
 
270
273
  (For maximum stealth, use <a translate="no" href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/ReadMe.md">CDP Mode</a>, which includes <a translate="no" href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/playwright/ReadMe.md">Stealthy Playwright Mode</a>)
271
274
 
272
275
  --------
273
276
 
274
- <p align="left">📗 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/raw_cdp_yc_news.py" target="_blank">This example</a> scrapes Hacker News listings with <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/ReadMe.md#-pure-cdp-mode-sb_cdp">Pure CDP Mode</a>:
277
+ <p align="left">📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/raw_cdp_browserscan.py" target="_blank">This example</a> verifies that <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/ReadMe.md#-pure-cdp-mode-sb_cdp">Pure CDP Mode</a> is stealthy on <a href="https://www.browserscan.net/bot-detection">BrowserScan</a>:
278
+
279
+ ```python
280
+ from seleniumbase import sb_cdp
281
+
282
+ url = "https://www.browserscan.net/bot-detection"
283
+ sb = sb_cdp.Chrome(url, locale="en", ad_block=True)
284
+ sb.flash("Test Results", duration=3, pause=1)
285
+ sb.assert_element('strong:contains("Normal")')
286
+ print("Bot Not detected")
287
+ sb.flash('strong:contains("Normal")', duration=3, pause=2)
288
+ ```
289
+
290
+ <img src="https://seleniumbase.github.io/other/b_scan_results.jpg" width="628" alt="Stealthy architecture flowchart" />
291
+
292
+ 📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/playwright/raw_browserscan_sync.py">This</a> also works as a drop-in replacement for Playwright (making it stealthy):
293
+
294
+ ```python
295
+ from playwright.sync_api import sync_playwright
296
+ from seleniumbase import sb_cdp
297
+
298
+ sb = sb_cdp.Chrome(locale="en", ad_block=True)
299
+ endpoint_url = sb.get_endpoint_url()
300
+
301
+ with sync_playwright() as p:
302
+ browser = p.chromium.connect_over_cdp(endpoint_url)
303
+ page = browser.contexts[0].pages[0]
304
+ page.goto("https://www.browserscan.net/bot-detection")
305
+ page.wait_for_timeout(500)
306
+ sb.flash("Test Results", duration=3, pause=1)
307
+ sb.assert_element('strong:contains("Normal")')
308
+ sb.flash('strong:contains("Normal")', duration=3, pause=2)
309
+ ```
310
+
311
+ --------
312
+
313
+ For choosing which Chromium browser to use, you can set command-line options:
314
+
315
+ ```zsh
316
+ python SCRIPT.py --use-chromium # Use the unbranded Chromium browser
317
+ python SCRIPT.py --cft # Use Chrome-for-testing
318
+ python SCRIPT.py --edge # Use Microsoft Edge
319
+ python SCRIPT.py --brave # Use Brave browser
320
+ ```
321
+
322
+ (Google Chrome is the default browser if not specified.)
323
+
324
+ --------
325
+
326
+ <p align="left">📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/raw_cdp_yc_news.py" target="_blank">This example</a> scrapes Hacker News listings with <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/ReadMe.md#-pure-cdp-mode-sb_cdp">Pure CDP Mode</a>:
275
327
 
276
328
  ```python
277
329
  from seleniumbase import sb_cdp
@@ -281,12 +333,11 @@ sb = sb_cdp.Chrome(url)
281
333
  elements = sb.find_elements("span.titleline > a")
282
334
  for element in elements:
283
335
  print("* " + element.text)
284
- sb.driver.stop()
285
336
  ```
286
337
 
287
338
  --------
288
339
 
289
- <p align="left">📗 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/raw_google.py" target="_blank">This example</a> saves Google Search results with UC + CDP Mode:<br />(Results are saved as PDF, HTML, and PNG files)</p>
340
+ <p align="left">📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/raw_google.py" target="_blank">This example</a> saves Google Search results with UC + CDP Mode:<br />(Results are saved as PDF, HTML, and PNG files)</p>
290
341
 
291
342
  ```python
292
343
  from seleniumbase import SB
@@ -307,7 +358,7 @@ with SB(uc=True, test=True) as sb:
307
358
 
308
359
  --------
309
360
 
310
- <p align="left">📗 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/raw_gitlab.py" target="_blank">This example</a> bypasses Cloudflare's challenge page with UC + CDP Mode:
361
+ <p align="left">📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/raw_gitlab.py" target="_blank">This example</a> bypasses Cloudflare's challenge page with UC + CDP Mode:
311
362
 
312
363
  ```python
313
364
  from seleniumbase import SB
@@ -329,7 +380,7 @@ with SB(uc=True, test=True, locale="en") as sb:
329
380
 
330
381
  ----
331
382
 
332
- <p align="left">📗 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/raw_cdp_gitlab.py" target="_blank">This example</a> handles a CAPTCHA page with Pure CDP Mode:
383
+ <p align="left">📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/raw_cdp_gitlab.py" target="_blank">This example</a> handles a CAPTCHA page with Pure CDP Mode:
333
384
 
334
385
  ```python
335
386
  from seleniumbase import sb_cdp
@@ -340,12 +391,11 @@ sb.sleep(2)
340
391
  sb.solve_captcha()
341
392
  sb.highlight('h1:contains("GitLab")')
342
393
  sb.highlight('button:contains("Sign in")')
343
- sb.driver.stop()
344
394
  ```
345
395
 
346
396
  --------
347
397
 
348
- <p align="left">📗 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/test_get_swag.py" target="_blank">This example</a> tests an e-commerce site with <code>pytest</code>:
398
+ <p align="left">📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/test_get_swag.py" target="_blank">This example</a> tests an e-commerce site with <code>pytest</code>:
349
399
 
350
400
  ```python
351
401
  from seleniumbase import BaseCase
@@ -375,7 +425,7 @@ class MyTestClass(BaseCase):
375
425
 
376
426
  --------
377
427
 
378
- <p align="left">📗 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/test_coffee_cart.py" target="_blank">This example</a> tests another e-commerce site with <code>pytest</code>:
428
+ <p align="left">📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/test_coffee_cart.py" target="_blank">This example</a> tests another e-commerce site with <code>pytest</code>:
379
429
 
380
430
  ```zsh
381
431
  pytest test_coffee_cart.py --demo
@@ -389,7 +439,7 @@ pytest test_coffee_cart.py --demo
389
439
 
390
440
  <a id="multiple_examples"></a>
391
441
 
392
- <p align="left">📗 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/test_demo_site.py" target="_blank">This example</a> covers multiple actions with <code>pytest</code>:
442
+ <p align="left">📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/test_demo_site.py" target="_blank">This example</a> covers multiple actions with <code>pytest</code>:
393
443
 
394
444
  ```zsh
395
445
  pytest test_demo_site.py
@@ -11,24 +11,29 @@
11
11
 
12
12
  <p align="center"><a href="https://github.com/seleniumbase/SeleniumBase/"><img src="https://seleniumbase.github.io/cdn/img/nice_logo_8t.png" alt="SeleniumBase" width="424" /></a></p>
13
13
 
14
- <p align="center" class="hero__title"><b>All-in-one Browser Automation Framework:<br />Web Crawling / Testing / Scraping / Stealth</b></p>
15
-
16
- <p align="center"><a href="https://pypi.python.org/pypi/seleniumbase" target="_blank"><img src="https://img.shields.io/pypi/v/seleniumbase.svg?color=3399EE" alt="PyPI version" /></a> <a href="https://github.com/seleniumbase/SeleniumBase/actions" target="_blank"><img src="https://github.com/seleniumbase/SeleniumBase/workflows/CI%20build/badge.svg" alt="SeleniumBase GitHub Actions" /></a> <a href="https://seleniumbase.io"><img src="https://img.shields.io/badge/docs-seleniumbase.io-11BBAA.svg" alt="SeleniumBase Docs" /></a> <a href="https://pepy.tech/projects/seleniumbase?timeRange=threeMonths&category=version&includeCIDownloads=true&granularity=daily&viewType=line&versions=*" target="_blank"><img src="https://static.pepy.tech/badge/seleniumbase" alt="SeleniumBase PyPI downloads" /></a> <a href="https://discord.gg/EdhQTn3EyE" target="_blank"><img src="https://img.shields.io/discord/727927627830001734?color=7289DA&label=Discord&logo=discord&logoColor=white"/></a></p>
14
+ <p align="center"><a href="https://pypi.python.org/pypi/seleniumbase" target="_blank"><img src="https://img.shields.io/pypi/v/seleniumbase.svg?color=3399EE" alt="PyPI version" /></a> <a href="https://pepy.tech/projects/seleniumbase?timeRange=threeMonths&category=version&includeCIDownloads=true&granularity=daily&viewType=line&versions=*" target="_blank"><img src="https://static.pepy.tech/badge/seleniumbase" alt="SeleniumBase PyPI downloads" /></a> <a href="https://discord.gg/EdhQTn3EyE" target="_blank"><img src="https://img.shields.io/discord/727927627830001734?color=7289DA&label=Discord&logo=discord&logoColor=white"/></a><br /> <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/LICENSE"><img src="https://img.shields.io/badge/license-MIT-22BBCC.svg" title="SeleniumBase" /></a> <a href="https://github.com/seleniumbase/SeleniumBase/actions" target="_blank"><img src="https://github.com/seleniumbase/SeleniumBase/workflows/CI%20build/badge.svg" alt="SeleniumBase GitHub Actions" /></a> <a href="https://seleniumbase.io"><img src="https://img.shields.io/badge/docs-seleniumbase.io-11BBAA.svg" alt="SeleniumBase Docs" /></a></p>
17
15
  <p align="center"></p>
18
16
 
17
+ <h3 align="center">Stealthy automation that passes every bot detection test.</h3>
18
+
19
+ <table align="center"><tr><td>
20
+ <b>Verified using multiple different Chromium browsers:<br />Chrome, Chrome-for-Testing, Chromium, Edge, Brave.</b>
21
+ </td></tr></table>
22
+
23
+
19
24
  <p align="center">
20
25
  <a href="#python_installation">🚀 Start</a> |
21
26
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/features_list.md">🏰 Features</a> |
22
27
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/customizing_test_runs.md">🎛️ Options</a> |
23
28
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/ReadMe.md">📚 Examples</a> |
24
- <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/seleniumbase/console_scripts/ReadMe.md">🪄 Scripts</a> |
25
- <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/mobile_testing.md">📱 Mobile</a>
29
+ <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/seleniumbase/console_scripts/ReadMe.md">💻 Scripts</a> |
30
+ <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/locale_codes.md">🗾 Locale</a>
26
31
  <br />
27
- <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/method_summary.md">📘 The API</a> |
28
- <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/syntax_formats.md"> 🔠 SyntaxFormats</a> |
32
+ <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/method_summary.md">📗 API</a> |
33
+ <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/cdp_mode_methods.md">📘 Stealth API</a> |
34
+ <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/syntax_formats.md"> 🔠 DesignPatterns</a> |
29
35
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/recorder_mode.md">🔴 Recorder</a> |
30
- <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/example_logs/ReadMe.md">📊 Dashboard</a> |
31
- <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/locale_codes.md">🗾 Locale</a>
36
+ <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/example_logs/ReadMe.md">📊 Dashboard</a>
32
37
  <br />
33
38
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/commander.md">🎖️ GUI</a> |
34
39
  <a href="https://seleniumbase.io/demo_page">📰 TestPage</a> |
@@ -44,7 +49,7 @@
44
49
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/tour_examples/ReadMe.md">🚎 Tours</a>
45
50
  <br />
46
51
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/integrations/github/workflows/ReadMe.md">🤖 CI/CD</a> |
47
- <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/js_package_manager.md">❇️ JSMgr</a> |
52
+ <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/js_package_manager.md">🟨 JSMgr</a> |
48
53
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/translations.md">🌏 Translator</a> |
49
54
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/presenter/ReadMe.md">🎞️ Presenter</a> |
50
55
  <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/visual_testing/ReadMe.md">🖼️ Visual</a> |
@@ -52,9 +57,7 @@
52
57
  <br />
53
58
  </p>
54
59
 
55
- 📊 <a href="https://github.com/seleniumbase/SeleniumBase/"><b translate="no">SeleniumBase</b></a> is a complete framework for browser automation and testing with Python and <a href="https://docs.pytest.org/en/latest/how-to/usage.html">pytest</a>. Includes stealth options and other advanced features.
56
-
57
- 🐙 Stealth modes: <a translate="no" href="https://github.com/seleniumbase/SeleniumBase/blob/master/help_docs/uc_mode.md">UC Mode</a> and <a translate="no" href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/ReadMe.md"><b>CDP Mode</b></a> can bypass bot-detection, handle CAPTCHAs, and call methods from the <a href="https://chromedevtools.github.io/devtools-protocol/" translate="no">Chrome Devtools Protocol</a>. CDP Mode includes <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/playwright/ReadMe.md"><b><span translate="no">Stealthy Playwright Mode</span></b></a>, which makes Playwright stealthy.
60
+ 🐙 <a translate="no" href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/ReadMe.md"><b>CDP Mode</b></a> bypasses bot-detection and handles CAPTCHAs by driving the browser directly through the <a href="https://chromedevtools.github.io/devtools-protocol/" translate="no">Chrome DevTools Protocol</a>. Includes <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/playwright/ReadMe.md"><b><span translate="no">Stealthy Playwright Mode</span></b></a>, which extends these advanced anti-detection patches to Playwright scripts.
58
61
 
59
62
  📚 The [SeleniumBase/examples/](https://github.com/seleniumbase/SeleniumBase/tree/master/examples) folder includes over 100 ready-to-run examples. Examples that start with `test_` or end with `_test.py`/`_tests.py` are specifically designed to run with `pytest`. Other examples run directly with raw `python` (those files generally start with `raw_` to avoid confusion).
60
63
 
@@ -64,13 +67,62 @@
64
67
 
65
68
  <h3 align="left">⚙️ Stealthy architecture flowchart:</h3>
66
69
 
67
- <img src="https://seleniumbase.github.io/other/sb_stealth.png" width="596" alt="Stealthy architecture flowchart" />
70
+ <img src="https://seleniumbase.github.io/other/sb_architecture.png" width="596" alt="Stealthy architecture flowchart" />
68
71
 
69
72
  (For maximum stealth, use <a translate="no" href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/ReadMe.md">CDP Mode</a>, which includes <a translate="no" href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/playwright/ReadMe.md">Stealthy Playwright Mode</a>)
70
73
 
71
74
  --------
72
75
 
73
- <p align="left">📗 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/raw_cdp_yc_news.py" target="_blank">This example</a> scrapes Hacker News listings with <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/ReadMe.md#-pure-cdp-mode-sb_cdp">Pure CDP Mode</a>:
76
+ <p align="left">📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/raw_cdp_browserscan.py" target="_blank">This example</a> verifies that <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/ReadMe.md#-pure-cdp-mode-sb_cdp">Pure CDP Mode</a> is stealthy on <a href="https://www.browserscan.net/bot-detection">BrowserScan</a>:
77
+
78
+ ```python
79
+ from seleniumbase import sb_cdp
80
+
81
+ url = "https://www.browserscan.net/bot-detection"
82
+ sb = sb_cdp.Chrome(url, locale="en", ad_block=True)
83
+ sb.flash("Test Results", duration=3, pause=1)
84
+ sb.assert_element('strong:contains("Normal")')
85
+ print("Bot Not detected")
86
+ sb.flash('strong:contains("Normal")', duration=3, pause=2)
87
+ ```
88
+
89
+ <img src="https://seleniumbase.github.io/other/b_scan_results.jpg" width="628" alt="Stealthy architecture flowchart" />
90
+
91
+ 📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/playwright/raw_browserscan_sync.py">This</a> also works as a drop-in replacement for Playwright (making it stealthy):
92
+
93
+ ```python
94
+ from playwright.sync_api import sync_playwright
95
+ from seleniumbase import sb_cdp
96
+
97
+ sb = sb_cdp.Chrome(locale="en", ad_block=True)
98
+ endpoint_url = sb.get_endpoint_url()
99
+
100
+ with sync_playwright() as p:
101
+ browser = p.chromium.connect_over_cdp(endpoint_url)
102
+ page = browser.contexts[0].pages[0]
103
+ page.goto("https://www.browserscan.net/bot-detection")
104
+ page.wait_for_timeout(500)
105
+ sb.flash("Test Results", duration=3, pause=1)
106
+ sb.assert_element('strong:contains("Normal")')
107
+ sb.flash('strong:contains("Normal")', duration=3, pause=2)
108
+ ```
109
+
110
+ --------
111
+
112
+ For choosing which Chromium browser to use, you can set command-line options:
113
+
114
+ ```zsh
115
+ python SCRIPT.py --use-chromium # Use the unbranded Chromium browser
116
+ python SCRIPT.py --cft # Use Chrome-for-testing
117
+ python SCRIPT.py --edge # Use Microsoft Edge
118
+ python SCRIPT.py --brave # Use Brave browser
119
+ ```
120
+
121
+ (Google Chrome is the default browser if not specified.)
122
+
123
+ --------
124
+
125
+ <p align="left">📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/raw_cdp_yc_news.py" target="_blank">This example</a> scrapes Hacker News listings with <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/ReadMe.md#-pure-cdp-mode-sb_cdp">Pure CDP Mode</a>:
74
126
 
75
127
  ```python
76
128
  from seleniumbase import sb_cdp
@@ -80,12 +132,11 @@ sb = sb_cdp.Chrome(url)
80
132
  elements = sb.find_elements("span.titleline > a")
81
133
  for element in elements:
82
134
  print("* " + element.text)
83
- sb.driver.stop()
84
135
  ```
85
136
 
86
137
  --------
87
138
 
88
- <p align="left">📗 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/raw_google.py" target="_blank">This example</a> saves Google Search results with UC + CDP Mode:<br />(Results are saved as PDF, HTML, and PNG files)</p>
139
+ <p align="left">📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/raw_google.py" target="_blank">This example</a> saves Google Search results with UC + CDP Mode:<br />(Results are saved as PDF, HTML, and PNG files)</p>
89
140
 
90
141
  ```python
91
142
  from seleniumbase import SB
@@ -106,7 +157,7 @@ with SB(uc=True, test=True) as sb:
106
157
 
107
158
  --------
108
159
 
109
- <p align="left">📗 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/raw_gitlab.py" target="_blank">This example</a> bypasses Cloudflare's challenge page with UC + CDP Mode:
160
+ <p align="left">📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/raw_gitlab.py" target="_blank">This example</a> bypasses Cloudflare's challenge page with UC + CDP Mode:
110
161
 
111
162
  ```python
112
163
  from seleniumbase import SB
@@ -128,7 +179,7 @@ with SB(uc=True, test=True, locale="en") as sb:
128
179
 
129
180
  ----
130
181
 
131
- <p align="left">📗 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/raw_cdp_gitlab.py" target="_blank">This example</a> handles a CAPTCHA page with Pure CDP Mode:
182
+ <p align="left">📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/cdp_mode/raw_cdp_gitlab.py" target="_blank">This example</a> handles a CAPTCHA page with Pure CDP Mode:
132
183
 
133
184
  ```python
134
185
  from seleniumbase import sb_cdp
@@ -139,12 +190,11 @@ sb.sleep(2)
139
190
  sb.solve_captcha()
140
191
  sb.highlight('h1:contains("GitLab")')
141
192
  sb.highlight('button:contains("Sign in")')
142
- sb.driver.stop()
143
193
  ```
144
194
 
145
195
  --------
146
196
 
147
- <p align="left">📗 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/test_get_swag.py" target="_blank">This example</a> tests an e-commerce site with <code>pytest</code>:
197
+ <p align="left">📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/test_get_swag.py" target="_blank">This example</a> tests an e-commerce site with <code>pytest</code>:
148
198
 
149
199
  ```python
150
200
  from seleniumbase import BaseCase
@@ -174,7 +224,7 @@ class MyTestClass(BaseCase):
174
224
 
175
225
  --------
176
226
 
177
- <p align="left">📗 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/test_coffee_cart.py" target="_blank">This example</a> tests another e-commerce site with <code>pytest</code>:
227
+ <p align="left">📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/test_coffee_cart.py" target="_blank">This example</a> tests another e-commerce site with <code>pytest</code>:
178
228
 
179
229
  ```zsh
180
230
  pytest test_coffee_cart.py --demo
@@ -188,7 +238,7 @@ pytest test_coffee_cart.py --demo
188
238
 
189
239
  <a id="multiple_examples"></a>
190
240
 
191
- <p align="left">📗 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/test_demo_site.py" target="_blank">This example</a> covers multiple actions with <code>pytest</code>:
241
+ <p align="left">📝 <a href="https://github.com/seleniumbase/SeleniumBase/blob/master/examples/test_demo_site.py" target="_blank">This example</a> covers multiple actions with <code>pytest</code>:
192
242
 
193
243
  ```zsh
194
244
  pytest test_demo_site.py
@@ -1,5 +1,5 @@
1
1
  pip>=26.0.1;python_version<"3.10"
2
- pip>=26.1;python_version>="3.10"
2
+ pip>=26.1.1;python_version>="3.10"
3
3
  packaging>=26.2
4
4
  setuptools~=70.2;python_version<"3.10"
5
5
  setuptools>=82.0.1;python_version>="3.10"
@@ -21,7 +21,7 @@ sbvirtualdisplay>=1.4.0
21
21
  MarkupSafe>=3.0.3
22
22
  Jinja2>=3.1.6
23
23
  six>=1.17.0
24
- parse>=1.21.1
24
+ parse>=1.22.0
25
25
  parse-type>=0.6.6
26
26
  colorama>=0.4.6
27
27
  pyyaml>=6.0.3
@@ -29,12 +29,12 @@ pygments>=2.20.0
29
29
  pyreadline3>=3.5.4;platform_system=="Windows"
30
30
  tabcompleter>=1.4.1
31
31
  pdbp>=1.8.2
32
- idna>=3.13
32
+ idna>=3.15
33
33
  charset-normalizer>=3.4.7,<4
34
34
  urllib3>=1.26.20,<2;python_version<"3.10"
35
- urllib3>=1.26.20,<3;python_version>="3.10"
35
+ urllib3>=2.7.0,<3;python_version>="3.10"
36
36
  requests~=2.32.5;python_version<"3.10"
37
- requests~=2.33.1;python_version>="3.10"
37
+ requests~=2.34.2;python_version>="3.10"
38
38
  sniffio==1.3.1
39
39
  h11==0.16.0
40
40
  outcome==1.3.0.post0
@@ -45,7 +45,7 @@ wsproto==1.2.0;python_version<"3.10"
45
45
  wsproto~=1.3.2;python_version>="3.10"
46
46
  websocket-client~=1.9.0
47
47
  selenium==4.32.0;python_version<"3.10"
48
- selenium==4.43.0;python_version>="3.10"
48
+ selenium==4.44.0;python_version>="3.10"
49
49
  cssselect==1.3.0;python_version<"3.10"
50
50
  cssselect>=1.4.0,<2;python_version>="3.10"
51
51
  sortedcontainers==2.4.0
@@ -60,7 +60,7 @@ pytest-html==4.0.2
60
60
  pytest-metadata==3.1.1
61
61
  pytest-ordering==0.6
62
62
  pytest-rerunfailures==16.0.1;python_version<"3.10"
63
- pytest-rerunfailures==16.1;python_version>="3.10"
63
+ pytest-rerunfailures==16.2;python_version>="3.10"
64
64
  pytest-xdist==3.8.0
65
65
  parameterized==0.9.0
66
66
  behave==1.2.6
@@ -70,7 +70,7 @@ pyotp==2.9.0
70
70
  python-xlib==0.33;platform_system=="Linux"
71
71
  PyAutoGUI>=0.9.54;platform_system=="Linux"
72
72
  markdown-it-py==3.0.0;python_version<"3.10"
73
- markdown-it-py==4.0.0;python_version>="3.10"
73
+ markdown-it-py==4.2.0;python_version>="3.10"
74
74
  mdurl==0.1.2
75
75
  rich>=15.0.0,<16
76
76
 
@@ -78,7 +78,7 @@ rich>=15.0.0,<16
78
78
  # ("pip install -r requirements.txt" also installs this, but "pip install -e ." won't.)
79
79
 
80
80
  coverage>=7.10.7;python_version<"3.10"
81
- coverage>=7.13.5;python_version>="3.10"
81
+ coverage>=7.14.0;python_version>="3.10"
82
82
  pytest-cov>=7.1.0
83
83
  flake8==7.3.0
84
84
  mccabe==0.7.0
@@ -1,2 +1,2 @@
1
1
  # seleniumbase package
2
- __version__ = "4.48.4"
2
+ __version__ = "4.49.0"
@@ -5082,6 +5082,14 @@ class BaseCase(unittest.TestCase):
5082
5082
  self.driver.uc_open_with_cdp_mode(url, **kwargs)
5083
5083
  else:
5084
5084
  self.get_new_driver(undetectable=True)
5085
+ if self.browser == "edge":
5086
+ raise Exception(
5087
+ 'For stealth with Edge, use "Pure CDP Mode"! Eg:\n'
5088
+ '```python\n'
5089
+ 'from seleniumbase import sb_cdp\n'
5090
+ 'sb = sb_cdp.Chrome(url, browser="edge")\n'
5091
+ '```'
5092
+ )
5085
5093
  self.driver.uc_open_with_cdp_mode(url, **kwargs)
5086
5094
  self.cdp = self.driver.cdp
5087
5095
  if hasattr(self.cdp, "solve_captcha"):
@@ -16893,6 +16901,11 @@ class BaseCase(unittest.TestCase):
16893
16901
  )
16894
16902
  raise Exception(message)
16895
16903
  # *** Start tearDown() officially ***
16904
+ if hasattr(self.driver, "_already_quit") and self.driver._already_quit:
16905
+ logging.warning(
16906
+ " The driver was already quit in a mode"
16907
+ " that quits the driver automatically."
16908
+ )
16896
16909
  page_actions._reconnect_if_disconnected(self.driver)
16897
16910
  self.__slow_mode_pause_if_active()
16898
16911
  has_exception = self.__has_exception()
@@ -517,8 +517,12 @@ class Chrome(selenium.webdriver.chrome.webdriver.WebDriver):
517
517
  with suppress(Exception):
518
518
  self.service.start()
519
519
  with suppress(Exception):
520
- self.start_session()
521
- time.sleep(0.0075)
520
+ already_quit = False
521
+ if hasattr(self, "_already_quit") and self._already_quit:
522
+ already_quit = True
523
+ if not already_quit:
524
+ self.start_session()
525
+ time.sleep(0.0075)
522
526
  with suppress(Exception):
523
527
  for window_handle in self.window_handles:
524
528
  self.switch_to.window(window_handle)
@@ -559,6 +563,7 @@ class Chrome(selenium.webdriver.chrome.webdriver.WebDriver):
559
563
  try:
560
564
  logger.debug("Terminating the UC browser")
561
565
  os.kill(self.browser_pid, 15)
566
+ self._already_quit = True
562
567
  if "linux" in sys.platform:
563
568
  os.waitpid(self.browser_pid, 0)
564
569
  time.sleep(0.02)