From c884f4fd9209b727824c9c8acccb6a24f8dce7c2 Mon Sep 17 00:00:00 2001 From: Michael Stangl Date: Fri, 9 Oct 2026 09:16:04 +0200 Subject: [PATCH] =?UTF-8?q?webscan:=20Pr=C3=BCfung=20auf=20Playwright=20un?= =?UTF-8?q?d=20Browser=20mit=20Installationshinweisen?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - fehlt Playwright oder der Browser, werden die passenden Befehle für Ubuntu/Debian bzw. Arch ausgegeben (erkannt über /etc/os-release), Abbruch mit Exit-Code 2 - doc/README.md: Einrichtung getrennt nach Ubuntu und Arch Co-Authored-By: Claude Opus 5.5 --- doc/README.md | 20 +++++++++++-- libs/webscan.py | 78 +++++++++++++++++++++++++++++++++++++++++++++++-- 2 files changed, 93 insertions(+), 5 deletions(-) diff --git a/doc/README.md b/doc/README.md index 4f87d45..e6c2846 100644 --- a/doc/README.md +++ b/doc/README.md @@ -154,13 +154,27 @@ Konfiguration (in `cfg/webscan.cfg`: 800×500). Einmalig einrichten (Python-Umgebung im Projektverzeichnis): ```sh -python3 -m venv .venv +python3 -m venv .venv # Ubuntu: vorher sudo apt install python3-venv .venv/bin/pip install -r requirements.txt +``` + +Browser unter Ubuntu/Debian: + +```sh +sudo .venv/bin/playwright install-deps chromium .venv/bin/playwright install chromium ``` -Statt des Playwright-Chromiums kann auch ein installiertes Chromium benutzt -werden: `-b /usr/bin/chromium` oder `export PICCREATE_BROWSER=/usr/bin/chromium`. +Browser unter Arch Linux (Playwright unterstützt Arch nicht offiziell, daher +besser das Chromium der Distribution): + +```sh +sudo pacman -S chromium +export PICCREATE_BROWSER=/usr/bin/chromium # oder Option -b /usr/bin/chromium +``` + +Fehlen Playwright oder der Browser, gibt `webscan.py` die passenden Befehle +für die erkannte Distribution aus und bricht mit Exit-Code 2 ab. Eingabedatei, z. B. `in/kunden.csv` (Kopfzeile optional, `http://` wird bei Bedarf ergänzt): diff --git a/libs/webscan.py b/libs/webscan.py index ba9e848..0989e43 100644 --- a/libs/webscan.py +++ b/libs/webscan.py @@ -18,7 +18,70 @@ import optparse import os import sys -from playwright.async_api import async_playwright, Error as PlaywrightError +PROJECT_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) +VENV = os.path.join(PROJECT_DIR, '.venv') + +INSTALL_HINTS = { + 'ubuntu': '''Ubuntu / Debian: + sudo apt install python3-venv + python3 -m venv {venv} + {venv}/bin/pip install -r {project}/requirements.txt + sudo {venv}/bin/playwright install-deps chromium + {venv}/bin/playwright install chromium''', + 'arch': '''Arch Linux: + python -m venv {venv} + {venv}/bin/pip install -r {project}/requirements.txt + then either the browser from Arch (recommended, Playwright does not + officially support Arch): + sudo pacman -S chromium + export PICCREATE_BROWSER=/usr/bin/chromium + or the Playwright browser: + {venv}/bin/playwright install chromium''', +} + +BROWSER_HINTS = { + 'ubuntu': '''Ubuntu / Debian: + sudo {venv}/bin/playwright install-deps chromium + {venv}/bin/playwright install chromium''', + 'arch': '''Arch Linux: + sudo pacman -S chromium + export PICCREATE_BROWSER=/usr/bin/chromium + or the Playwright browser: + {venv}/bin/playwright install chromium''', +} + + +def linux_distro(): + ''' liefert 'ubuntu' oder 'arch' (aus /etc/os-release), sonst None ''' + try: + with open('/etc/os-release', encoding='utf-8') as fh: + info = dict(line.rstrip('\n').split('=', 1) for line in fh if '=' in line) + except OSError: + return None + ids = (info.get('ID', '') + ' ' + info.get('ID_LIKE', '')).replace('"', '').split() + if 'arch' in ids: + return 'arch' + if 'ubuntu' in ids or 'debian' in ids: + return 'ubuntu' + return None + + +def print_hint(hints): + ''' gibt die Installationshinweise für diese Distribution aus + (bei unbekannter Distribution alle) ''' + distro = linux_distro() + keys = [distro] if distro in hints else sorted(hints) + for key in keys: + print(hints[key].format(venv=VENV, project=PROJECT_DIR), file=sys.stderr) + + +try: + from playwright.async_api import async_playwright, Error as PlaywrightError +except ImportError: + print('Playwright is not installed for', sys.executable, file=sys.stderr) + print('Install it into the project environment:', file=sys.stderr) + print_hint(INSTALL_HINTS) + sys.exit(2) from utils import CompleteEnding @@ -92,8 +155,17 @@ async def run(jobs, pic_config, options): async with async_playwright() as p: launch_args = {} if options.browser: + if not os.path.isfile(options.browser): + print('browser', options.browser, 'does not exist.', file=sys.stderr) + print_hint(BROWSER_HINTS) + return None launch_args['executable_path'] = options.browser - browser = await p.chromium.launch(**launch_args) + try: + browser = await p.chromium.launch(**launch_args) + except PlaywrightError as e: + print('could not start the browser:', str(e).splitlines()[0], file=sys.stderr) + print_hint(BROWSER_HINTS) + return None async def worker(customer_id, url): out_path = os.path.join(out_dir, customer_id + '.' + pic_config['format']) @@ -133,6 +205,8 @@ def main(): print('no urls found in', options.infile) return 1 failed = asyncio.run(run(jobs, pic_config, options)) + if failed is None: + return 2 if failed: print(len(failed), 'of', len(jobs), 'pages failed:', ', '.join(failed), file=sys.stderr) return 1