Simulate realistic mouse paths
mastergetCoalescedEvents logic) that match screen frequencies or higher.repository·master·Indexed 21 days ago
https://github.com/ttlns/selenium-driverlessA Python library for controlling Chrome using Selenium-like syntax without chromedriver to avoid bot detection. It supports asyncio, multiple isolated contexts, and advanced CDP-based interactions, including human-like mouse paths, randomized element clicks, and network request interception via NetworkInterceptor.
getCoalescedEvents logic) that match screen frequencies or higher.To use selenium-driverless, import webdriver from selenium_driverless. The library is designed for asynchronous execution using asyncio. You should use an async with context manager to manage the lifecycle of the webdriver.Chrome instance.
Key capabilities demonstrated in the example:
driver.get(url, wait_load=True).driver.wait_for_cdp(event_name, timeout).driver.find_element(By, selector, timeout).elem.click(move_to=True).driver.switch_to.alert.from selenium_driverless import webdriver
from selenium_driverless.types.by import By
import asyncio
async def main():
options = webdriver.ChromeOptions()
async with webdriver.Chrome(options=options) as driver:
await driver.get('http://nowsecure.nl#relax', wait_load=True)
await driver.sleep(0.5)
await driver.wait_for_cdp("Page.domContentEventFired", timeout=15)
# wait 10s for elem to exist
elem = await driver.find_element(By.XPATH, '/html/body/div[2]/div/main/p[2]/a', timeout=10)
await elem.click(move_to=True)
alert = await driver.switch_to.alert
print(alert.text)
await alert.accept()
print(await driver.title)
asyncio.run(main())The recommended way to use selenium-driverless is with asyncio. This allows for efficient handling of multiple tabs and asynchronous operations. Use async with webdriver.Chrome(...) to manage the driver lifecycle.
Key features in the async API:
driver.get(url, wait_load=True): Navigates to a URL.driver.wait_for_cdp(event, timeout): Waits for a specific Chrome DevTools Protocol event.driver.find_element(by, selector, timeout): Finds an element with a specified timeout.elem.click(move_to=True): Performs a click, optionally moving the pointer to the element first.from selenium_driverless import webdriver
from selenium_driverless.types.by import By
import asyncio
async def main():
options = webdriver.ChromeOptions()
async with webdriver.Chrome(options=options) as driver:
await driver.get('http://nowsecure.nl#relax', wait_load=True)
await driver.sleep(0.5)
await driver.wait_for_cdp("Page.domContentEventFired", timeout=15)
# wait 10s for elem to exist
elem = await driver.find_element(By.XPATH, '/html/body/div[2]/div/main/p[2]/a', timeout=10)
await elem.click(move_to=True)
alert = await driver.switch_to.alert
print(alert.text)
await alert.accept()
print(await driver.title)
asyncio.run(main())To work with multiple tabs in parallel, use asyncio.gather along with driver.new_window("tab", activate=False) to create new tabs without losing focus on the current one. Each tab can be treated as a target object.
from selenium_driverless.sync import webdriver
from selenium_driverless.utils.utils import read
from selenium_driverless import webdriver
import asyncio
async def target_1_handler(target):
await target.get('https://abrahamjuliot.github.io/creepjs/')
print(await target.title)
async def target_2_handler(target):
await target.get("about:blank")
await target.execute_script(await script=read("/files/js/show_mousemove.js"))
await target.pointer.move_to(500, 500, total_time=2)
async def main():
options = webdriver.ChromeOptions()
async with webdriver.Chrome(options=options) as driver:
target_1 = await driver.current_target
target_2 = await driver.new_window("tab", activate=False)
await asyncio.gather(
target_1_handler(target_1),
target_2_handler(target_2)
)
await target_1.focus()
input("press ENTER to exit")
asyncio.run(main())To use selenium-driverless, ensure you have Python >= 3.8 and Google-Chrome installed (Chromium is not tested).
Install the package via pip:
pip install selenium-driverlessIf you want to use the latest implementations from the development branch, you can install directly from GitHub:
pip uninstall -y selenium-driverless
pip install https://github.com/kaliiiiiiiiii/Selenium-Driverless/archive/refs/heads/dev.zippip install selenium-driverlessA synchronous API is available via selenium_driverless.sync. Note that this is an asyncified wrapper, so bugs may be expected.
Use with webdriver.Chrome(options=options) to manage the driver context.
from selenium_driverless.sync import webdriver
options = webdriver.ChromeOptions()
with webdriver.Chrome(options=options) as driver:
driver.get('http://nowsecure.nl#relax')
driver.sleep(0.5)
driver.wait_for_cdp("Page.domContentEventFired", timeout=15)
title = driver.title
url = driver.current_url
source = driver.page_source
print(title)Use the NetworkInterceptor class to monitor and intercept network traffic within selenium-driverless. The interceptor acts as an asynchronous iterator that yields InterceptedRequest objects, allowing you to inspect or modify requests as they occur.
# Example usage pattern for request interception
from selenium_driverless.scripts.network_interceptor import NetworkInterceptor
async def intercept_example(driver):
async with NetworkInterceptor(driver) as interceptor:
async for intercepted_request in interceptor:
# Handle the intercepted request
print(f"Intercepted: {intercepted_request.url}")Install or upgrade the selenium-driverless package using pip to get the latest version.
python -m pip install --upgrade selenium-driverlessYou can set Chrome preferences using options.update_pref() or by updating the options.prefs dictionary directly. This is useful for settings like disabling download prompts.
from selenium_driverless import webdriver
options = webdriver.ChromeOptions()
# recommended usage
options.update_pref("download.prompt_for_download", False)
# or
options.prefs.update({"download": {"prompt_for_download": False}})
# or
options.add_experimental_option("prefs", {"download": {"prompt_for_download": False}})The Context class allows you to drive the browser without using chromedriver. It manages browser targets, windows, and session-level configurations like incognito mode and download behaviors. You can use it as an asynchronous context manager to ensure the session is properly started and quit.
async with Context(base_target=my_target, is_incognito=True) as context:
await context.get("https://example.com")
# perform actions
# session is automatically quit hereThe Options class (equivalent to webdriver.ChromeOptions) is used to configure the Chrome browser instance.
Important: Options objects should not be reused across different driver instances.
Key capabilities include:
from selenium_driverless import webdriver
options = webdriver.ChromeOptions()
# Configure options here
async with webdriver.Chrome(options=options) as driver:
await driver.get('https://example.com')