D4Vinci/Scrapling · error · ValueError

Browser executable is not an absolute path: {value}

Error message

Browser executable is not an absolute path: {value}

What it means

Raised when executable_path is a valid existing file but given as a relative path — the validator requires Path(value).is_absolute(). This guards against the browser subprocess resolving the path against a different working directory.

Source

Thrown at scrapling/engines/_browsers/_validators.py:133

            self.cookies = []
        if not self.extra_flags:
            self.extra_flags = []
        if not self.selector_config:
            self.selector_config = {}
        if not self.additional_args:
            self.additional_args = {}
        if not self.capture_xhr:
            self.capture_xhr = None

        if self.init_script is not None:
            validation_msg = _is_invalid_file_path(self.init_script)
            if validation_msg:
                raise ValueError(validation_msg)

        if self.executable_path is not None:
            validation_msg = _is_invalid_file_path(self.executable_path, "Browser executable")
            if validation_msg:
                raise ValueError(validation_msg)

        if self.block_ads:
            from scrapling.engines.toolbelt.ad_domains import AD_DOMAINS

            if self.blocked_domains:
                self.blocked_domains = self.blocked_domains | set(AD_DOMAINS)
            else:
                self.blocked_domains = set(AD_DOMAINS)


class StealthConfig(PlaywrightConfig, kw_only=True, frozen=False, weakref=True):
    allow_webgl: bool = True
    hide_canvas: bool = False
    block_webrtc: bool = False
    solve_cloudflare: bool = False

    def __post_init__(self):
        """Custom validation after msgspec validation"""

View on GitHub (pinned to 5d213a2d47)

Solutions

  1. Resolve at runtime: str(Path('./browsers/chromium').resolve())
  2. Or use shutil.which(), which already returns an absolute path

Example fix

// before
session = StealthySession(executable_path='browsers/chrome')

// after
session = StealthySession(executable_path=str(Path('browsers/chrome').resolve()))
Defensive patterns

Strategy: validation

Validate before calling

from pathlib import Path
p = str(Path(executable_path).resolve())
assert Path(p).is_file()
session = StealthySession(executable_path=p)

Type guard

def is_absolute_binary_path(p: str) -> bool:
    from pathlib import Path
    return Path(p).is_absolute()

Prevention

When it happens

Trigger: Passing executable_path='chrome/chrome' or './browsers/chromium' that exists relative to the current directory but is not absolute.

Common situations: Bundling a browser in the project folder and referencing it relatively; portable deployments with relative layout assumptions.

Related errors


AI-assisted analysis of D4Vinci/Scrapling@5d213a2d47 (2026-08-14). Data as JSON: /api/errors/37b527eb55a5ff83. Report an issue: GitHub.