How to Use Botright for Web Automation in 2025

Botright is an open-source automation framework that combines Playwright's power with advanced fingerprint-changing, bot detection evasion, and AI-powered CAPTCHA solving—all without requiring paid APIs.

Unlike standard browser automation tools that get blocked within seconds, Botright masquerades as a real user by leveraging genuine Chromium browsers and self-scraped fingerprints.

In this guide, we'll show you how to set up Botright, bypass modern anti-bot systems, and solve CAPTCHAs programmatically using nothing but Python and some clever techniques.

Why Botright Beats Standard Automation Tools

Before diving into the implementation, let's address the elephant in the room: why should you use Botright instead of vanilla Selenium or Puppeteer?

Modern websites deploy sophisticated anti-bot systems like DataDome, Imperva, and Cloudflare that can detect automation tools through:

  • Browser fingerprinting (canvas, WebGL, audio context)
  • JavaScript execution anomalies
  • Missing browser APIs
  • Predictable automation patterns
  • The infamous navigator.webdriver flag

Botright uses a vast amount of techniques to hide its functionality as a bot from websites. To enhance stealth, since Version 0.3, it uses a real Chromium-based browser from the local machine to start up a botted browser. This isn't just another Selenium wrapper—it's a complete reimagining of browser automation.

Prerequisites and Installation Quirks

Here's where things get interesting. Botright requires Python 3.10.11 or lower—newer versions won't work due to dependency conflicts. This might seem like a limitation, but it's actually a blessing in disguise for avoiding detection (older Python versions have different SSL handshakes that can help evade some fingerprinting).

Step 1: Set Up Your Environment

First, install Python 3.10 or lower. If you're running multiple Python versions (which you should for different projects), create a dedicated virtual environment:

# Create virtual environment with Python 3.10
python3.10 -m venv botright_env
source botright_env/bin/activate  # On Windows: botright_env\Scripts\activate

Now for the installation—but here's the trick: use the --use-pep517 flag to avoid dependency hell:

pip install --use-pep517 botright
playwright install

Step 2: Install Ungoogled Chromium (The Stealth Boost)

This is where most tutorials stop, but we're going deeper. For best stealth, you want to install Ungoogled Chromium. This browser variant strips out Google's tracking and telemetry, making your automation significantly harder to detect.

Download Ungoogled Chromium from the official repository and install it. Botright will automatically detect and use it, giving you an instant stealth upgrade without any configuration.

Step 3: Your First Undetectable Script

Let's start with a basic script that showcases Botright's core capabilities:

import asyncio
import botright

async def main():
    # Initialize Botright with stealth settings
    botright_client = await botright.Botright(
        headless=False,  # Set to True for production
    )
    
    # Create a new browser instance
    browser = await botright_client.new_browser()
    
    # Create a new page
    page = await browser.new_page()
    
    # Navigate to a bot-detection test site
    await page.goto("https://bot.sannysoft.com")
    
    # Take a screenshot to verify we're undetected
    await page.screenshot(path="bot_test.png", full_page=True)
    
    # Wait a bit to see the results
    await page.wait_for_timeout(5000)
    
    await botright_client.close()

if __name__ == "__main__":
    asyncio.run(main())

Run this script and check the screenshot—you'll see green checkmarks where standard Selenium would show red flags.

Step 4: Advanced Fingerprint Manipulation

Here's where we get into the real tech tricks. Botright allows you to customize fingerprints dynamically:

async def advanced_stealth():
    botright_client = await botright.Botright(
        headless=False,
        mask_fingerprint=True,  # Enable fingerprint spoofing
    )
    
    # Create browser with proxy support
    browser = await botright_client.new_browser(
        proxy="username:password@ip:port",  # Use residential proxies for best results
        viewport={"width": 1920, "height": 1080},
        locale="en-US",
        timezone_id="America/New_York"
    )
    
    page = await browser.new_page()
    
    # Inject custom behavior to appear more human
    await page.evaluate("""
        // Override automation indicators
        delete navigator.__proto__.webdriver;
        
        // Add realistic mouse movements
        document.addEventListener('mousemove', (e) => {
            console.log('Natural mouse movement detected');
        });
    """)
    
    await page.goto("https://abrahamjuliot.github.io/creepjs/")
    await page.wait_for_timeout(10000)
    
    await botright_client.close()

Step 5: Solving CAPTCHAs Without Paying a Dime

This is Botright's killer feature—free CAPTCHA solving using AI. It uses Computer Vision/Artificial Intelligence and other Methods to solve these Captchas. You dont need to pay for any Captcha Solving APIs and you can solve Captchas with just one simple function call.

Solving Google reCAPTCHA

async def solve_recaptcha_demo():
    botright_client = await botright.Botright()
    browser = await botright_client.new_browser()
    page = await browser.new_page()
    
    # Navigate to a page with reCAPTCHA
    await page.goto("https://recaptcha-demo.appspot.com/recaptcha-v2-checkbox.php")
    
    # Magic happens here - Botright solves it automatically
    captcha_solution = await page.solve_recaptcha()
    
    if captcha_solution:
        print(f"CAPTCHA solved! Token: {captcha_solution[:50]}...")
        # Now you can submit the form
        await page.click('input[type="submit"]')
    
    await botright_client.close()

Solving hCaptcha (The Trickier One)

hCaptcha is harder, but Botright has tricks up its sleeve:

async def solve_hcaptcha_advanced():
    botright_client = await botright.Botright()
    browser = await botright_client.new_browser()
    page = await browser.new_page()
    
    # For hCaptcha, we can mock the challenge response
    await page.goto("https://accounts.hcaptcha.com/demo")
    
    # Solve hCaptcha with custom parameters
    solution = await page.solve_hcaptcha(
        sitekey="00000000-0000-0000-0000-000000000000",  # Replace with actual sitekey
        rq_data=None  # Can be used to mock specific challenges
    )
    
    if solution:
        print("hCaptcha defeated!")
    
    await botright_client.close()

The Dark Arts: Bypassing Specific Anti-Bot Systems

Cloudflare Bypass Technique

While Botright can take up to 15 seconds to solve a reCAPTCHA, here's a faster approach for Cloudflare challenges:

async def bypass_cloudflare():
    botright_client = await botright.Botright(
        headless=False,
        mask_fingerprint=True
    )
    
    browser = await botright_client.new_browser(
        # Critical: Use residential proxy
        proxy="residential_proxy_here",
        # Mimic real browser session
        viewport={"width": 1366, "height": 768},
        user_agent="Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36"
    )
    
    page = await browser.new_page()
    
    # Pre-load cookies from a legitimate session (if available)
    cookies = [
        {"name": "cf_clearance", "value": "your_clearance_token", "domain": ".target.com"}
    ]
    await page.context.add_cookies(cookies)
    
    # Navigate with retry logic
    max_retries = 3
    for attempt in range(max_retries):
        try:
            await page.goto("https://protected-site.com", wait_until="networkidle")
            # Check if we bypassed the challenge
            if "challenge" not in page.url:
                break
        except:
            await asyncio.sleep(2)
    
    await botright_client.close()

DataDome Evasion

DataDome is particularly aggressive, but here's a workaround:

async def evade_datadome():
    botright_client = await botright.Botright()
    
    # Create multiple browser contexts to distribute requests
    browsers = []
    for i in range(3):
        browser = await botright_client.new_browser(
            viewport={"width": 1920 - i*100, "height": 1080 - i*50}  # Vary dimensions
        )
        browsers.append(browser)
    
    # Rotate between browsers
    for i, target_url in enumerate(urls_to_scrape):
        browser = browsers[i % len(browsers)]
        page = await browser.new_page()
        
        # Add random delays between actions
        await asyncio.sleep(random.uniform(2, 5))
        
        await page.goto(target_url)
        # Process page...
        await page.close()
    
    # Cleanup
    for browser in browsers:
        await browser.close()
    await botright_client.close()

Step 6: Production-Ready Implementation with Error Handling

Here's a robust scraper that handles real-world scenarios:

import asyncio
import logging
from typing import Optional, List
import botright

class StealthScraper:
    def __init__(self, headless: bool = True):
        self.headless = headless
        self.client: Optional[botright.Botright] = None
        self.browser = None
        logging.basicConfig(level=logging.INFO)
        self.logger = logging.getLogger(__name__)
    
    async def initialize(self):
        """Initialize Botright with optimal settings"""
        self.client = await botright.Botright(
            headless=self.headless,
            mask_fingerprint=True
        )
        self.browser = await self.client.new_browser(
            viewport={"width": 1920, "height": 1080},
            locale="en-US"
        )
    
    async def scrape_with_retry(self, url: str, max_retries: int = 3) -> Optional[str]:
        """Scrape URL with automatic retry and CAPTCHA handling"""
        for attempt in range(max_retries):
            page = None
            try:
                page = await self.browser.new_page()
                
                # Navigate to URL
                response = await page.goto(url, wait_until="domcontentloaded")
                
                # Check for CAPTCHA
                if await page.query_selector(".g-recaptcha"):
                    self.logger.info("reCAPTCHA detected, solving...")
                    await page.solve_recaptcha()
                
                elif await page.query_selector(".h-captcha"):
                    self.logger.info("hCaptcha detected, solving...")
                    await page.solve_hcaptcha()
                
                # Get page content
                content = await page.content()
                return content
                
            except Exception as e:
                self.logger.error(f"Attempt {attempt + 1} failed: {e}")
                if attempt == max_retries - 1:
                    raise
                await asyncio.sleep(2 ** attempt)  # Exponential backoff
                
            finally:
                if page:
                    await page.close()
        
        return None
    
    async def cleanup(self):
        """Clean up resources"""
        if self.browser:
            await self.browser.close()
        if self.client:
            await self.client.close()

# Usage
async def main():
    scraper = StealthScraper(headless=False)
    await scraper.initialize()
    
    try:
        content = await scraper.scrape_with_retry("https://example.com")
        if content:
            print("Successfully scraped!")
    finally:
        await scraper.cleanup()

if __name__ == "__main__":
    asyncio.run(main())

Performance Optimization Tricks

Thread Safety Workaround

Botright´s API is not thread-safe. If you are using Botright in a multi-threaded environment, you should create a botright instance per thread. Here's how to handle concurrent scraping properly:

import asyncio
from concurrent.futures import ThreadPoolExecutor

async def scrape_worker(url: str):
    """Independent worker with its own Botright instance"""
    client = await botright.Botright(headless=True)
    browser = await client.new_browser()
    page = await browser.new_page()
    
    try:
        await page.goto(url)
        content = await page.content()
        return content
    finally:
        await client.close()

async def parallel_scraping(urls: List[str]):
    """Scrape multiple URLs in parallel"""
    tasks = [scrape_worker(url) for url in urls]
    results = await asyncio.gather(*tasks)
    return results

Memory Management for Large-Scale Operations

async def memory_efficient_scraping(urls: List[str], batch_size: int = 5):
    """Process URLs in batches to manage memory"""
    results = []
    
    for i in range(0, len(urls), batch_size):
        batch = urls[i:i + batch_size]
        
        # Create fresh instance for each batch
        client = await botright.Botright(headless=True)
        browser = await client.new_browser()
        
        batch_results = []
        for url in batch:
            page = await browser.new_page()
            await page.goto(url)
            content = await page.content()
            batch_results.append(content)
            await page.close()  # Close page immediately
        
        results.extend(batch_results)
        await client.close()  # Clean up after batch
        
        # Give system time to reclaim memory
        await asyncio.sleep(1)
    
    return results

Common Pitfalls and Solutions

Issue: Detection on Headless Mode

Some sites detect headless browsers even with Botright. Solution:

# Force headed mode for tough sites
botright_client = await botright.Botright(
    headless=False,
    # Run in virtual display for servers
    args=["--start-maximized", "--disable-blink-features=AutomationControlled"]
)

Issue: Slow CAPTCHA Solving

In real-world scenarios, Botright can take up to 15 seconds to solve a reCAPTCHA. For faster results:

# Pre-warm the CAPTCHA solver
async def prewarm_captcha_solver():
    client = await botright.Botright()
    browser = await client.new_browser()
    page = await browser.new_page()
    
    # Load CAPTCHA libraries in advance
    await page.goto("https://www.google.com/recaptcha/api2/demo")
    await page.wait_for_timeout(2000)
    
    # Now ready for faster solving
    return client, browser

Limitations and When to Look Elsewhere

While Botright is powerful, it has limitations:

  • hCaptcha success rate is up to 90% but can be inconsistent
  • Python version restrictions (3.10.11 or lower)
  • Not thread-safe without workarounds
  • Resource-intensive for large-scale operations

For enterprise-scale operations or when you need 100% reliability, consider:

  • Using Botright for proof-of-concept, then investing in commercial solutions
  • Combining Botright with rotating residential proxies
  • Implementing a hybrid approach with multiple tools

Next Steps

You now have the knowledge to bypass most anti-bot systems using Botright. Remember:

  1. Always respect robots.txt and rate limits
  2. Use residential proxies for better success rates
  3. Implement proper error handling and retries
  4. Monitor your success rates and adjust strategies

The key to successful automation isn't just the tools—it's understanding how detection works and staying one step ahead. Botright gives you that edge, combining legitimate browser behavior with clever evasion techniques.

Start with the basic examples, then gradually add complexity as you encounter different anti-bot systems. And remember: the best bypass is the one that doesn't look like a bypass at all.

Marius Bernard

Marius Bernard

Marius Bernard is a Product Advisor, Technical SEO, & Brand Ambassador at Roundproxies. He was the lead author for the SEO chapter of the 2024 Web and a reviewer for the 2023 SEO chapter.