Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Question]: Missing X server or $DISPLAY error while running xvfb-run in docker #14250

Closed
denismur opened this issue May 18, 2022 · 13 comments
Closed

Comments

@denismur
Copy link

denismur commented May 18, 2022

Your question

I'm trying to run playwright script in docker with headless=False option and with hvfb-run but got an error

╔════════════════════════════════════════════════════════════════════════════════════════════════╗
║ Looks like you launched a headed browser without having a XServer running.                     ║
║ Set either 'headless: true' or use 'xvfb-run <your-playwright-app>' before running Playwright. ║
║                                                                                                ║
║ <3 Playwright Team                                                                             ║
╚════════════════════════════════════════════════════════════════════════════════════════════════╝

=========================== logs ===========================

<launching> /ms-playwright/chromium-1005/chrome-linux/chrome --disable-field-trial-config --disable-background-networking --enable-features=NetworkService,NetworkServiceInProcess --disable-background-timer-throttling --disable-backgrounding-occluded-windows --disable-breakpad --disable-client-side-phishing-detection --disable-component-extensions-with-background-pages --disable-default-apps --disable-dev-shm-usage --disable-extensions --disable-features=ImprovedCookieControls,LazyFrameLoading,GlobalMediaControls,DestroyProfileOnBrowserClose,MediaRouter,DialMediaRouteProvider,AcceptCHFrame,AutoExpandDetailsElement,CertificateTransparencyComponentUpdater,AvoidUnnecessaryBeforeUnloadCheckSync --allow-pre-commit-input --disable-hang-monitor --disable-ipc-flooding-protection --disable-popup-blocking --disable-prompt-on-repost --disable-renderer-backgrounding --disable-sync --force-color-profile=srgb --metrics-recording-only --no-first-run --enable-automation --password-store=basic --use-mock-keychain --no-service-autorun --export-tagged-pdf --no-sandbox --window-size=1300,570 --window-position=000,000 --disable-dev-shm-usage --no-sandbox --disable-web-security --disable-features=site-per-process --disable-setuid-sandbox --disable-accelerated-2d-canvas --no-first-run --no-zygote --single-process --disable-gpu --use-gl=egl --disable-blink-features=AutomationControlled --disable-background-networking --enable-features=NetworkService,NetworkServiceInProcess --disable-background-timer-throttling --disable-backgrounding-occluded-windows --disable-breakpad --disable-client-side-phishing-detection --disable-component-extensions-with-background-pages --disable-default-apps --disable-extensions --disable-features=Translate --disable-hang-monitor --disable-ipc-flooding-protection --disable-popup-blocking --disable-prompt-on-repost --disable-renderer-backgrounding --disable-sync --force-color-profile=srgb --metrics-recording-only --enable-automation --password-store=basic --use-mock-keychain --hide-scrollbars --mute-audio --user-data-dir=/tmp/playwright_chromiumdev_profile-1XCxqn --remote-debugging-pipe --no-startup-window

<launched> pid=155

[pid=155][err] [155:155:0517/235522.027129:ERROR:ozone_platform_x11.cc(247)] Missing X server or $DISPLAY

[pid=155][err] [155:155:0517/235522.052874:ERROR:env.cc(226)] The platform failed to initialize.  Exiting.

============================================================

I use a mcr.microsoft.com/playwright/python:v1.22.0-focal image,
ENV DISPLAY :99
and my CMD look's like:
xvfb-run --auto-servernum --server-num=1 --server-args='-screen 0, 1920x1080x24' python3 browser.py param

Any ideas what am I doing wrong?

@denismur denismur changed the title [Question]: xvfb-run + docker [Question]: Missing X server or $DISPLAY error while running xvfb-run in docker May 18, 2022
@mxschmitt mxschmitt transferred this issue from microsoft/playwright-python May 18, 2022
@SidduMirji
Copy link

I'm also getting the same error. Running the test from docker container with jenkins pipeline.

@mxschmitt
Copy link
Member

I tried to reproduce but it works for me:

  1. use the official Docker image
  2. Run a headed browser instance and create a page, without xvfb it will yield to the error
  3. Add xvfb-run then the error will be gone

could you share with us a repro without Jenkins etc?

@denismur
Copy link
Author

Could you share your Dockerfile?

I tried to reproduce but it works for me:

  1. use the official Docker image
  2. Run a headed browser instance and create a page, without xvfb it will yield to the error
  3. Add xvfb-run then the error will be gone

could you share with us a repro without Jenkins etc?

@mxschmitt
Copy link
Member

I did the following: docker run -it mcr.microsoft.com/playwright/python:v1.22.0-focal /bin/bash in step 1

And used an snippet from the docs which launches a browser instance.

@denismur
Copy link
Author

I've used the same docker image, but I've reinstalled python to 3.9

Dockerfile:

FROM mcr.microsoft.com/playwright/python:latest

RUN apt-get update && DEBIAN_FRONTEND="noninteractive" TZ="Europe/Moscow" apt-get install -y tzdata

# === INSTALL Python ===
RUN apt-get update && apt-get install -y python3.9 python3-pip && \
    update-alternatives --install /usr/bin/pip pip /usr/bin/pip3 1 && \
    update-alternatives --install /usr/bin/python python /usr/bin/python3 1 && \
    update-alternatives --install /usr/bin/python3 python3 /usr/bin/python3.9 1

RUN apt-get update && \
    apt-get upgrade -y && \
    apt-get install -y git gnupg2

RUN apt-get update && apt-get install -y --no-install-recommends apt-utils

COPY . /usr/src/test
WORKDIR /usr/src/test
RUN pip install --upgrade pip
RUN pip install --no-cache-dir -r requirements.txt

requirements.txt:

aiodocker
beautifulsoup4
EasyProcess
elasticsearch[async]
motor
pandas
pillow
playwright
playwright_stealth
pymongo
pydantic
python_ghost_cursor
requests

I did the following: docker run -it mcr.microsoft.com/playwright/python:v1.22.0-focal /bin/bash in step 1

And used an snippet from the docs which launches a browser instance.

@mxschmitt
Copy link
Member

How does browser.py look like? something which I can easily run locally would be nice!

@denismur
Copy link
Author

denismur commented May 18, 2022

Here is a short version without additional parameters

from playwright.async_api import Playwright, async_playwright, expect
from playwright_stealth import stealth_async, StealthConfig
from python_ghost_cursor.playwright_async import create_cursor
import asyncio

async def run(playwright: Playwright) -> None:
    browser_args = [
        '--window-size=1300,570',
        '--window-position=000,000',
        '--disable-dev-shm-usage',
        '--no-sandbox',
        '--disable-web-security',
        '--disable-features=site-per-process',
        '--disable-setuid-sandbox',
        '--disable-accelerated-2d-canvas',
        '--no-first-run',
        '--no-zygote',
        '--single-process',
        '--disable-gpu',
        '--use-gl=egl',
        '--disable-blink-features=AutomationControlled',
        '--disable-background-networking',
        '--enable-features=NetworkService,NetworkServiceInProcess',
        '--disable-background-timer-throttling',
        '--disable-backgrounding-occluded-windows',
        '--disable-breakpad',
        '--disable-client-side-phishing-detection',
        '--disable-component-extensions-with-background-pages',
        '--disable-default-apps',
        '--disable-extensions',
        '--disable-features=Translate',
        '--disable-hang-monitor',
        '--disable-ipc-flooding-protection',
        '--disable-popup-blocking',
        '--disable-prompt-on-repost',
        '--disable-renderer-backgrounding',
        '--disable-sync',
        '--force-color-profile=srgb',
        '--metrics-recording-only',
        '--enable-automation',
        '--password-store=basic',
        '--use-mock-keychain',
        '--hide-scrollbars',
        '--mute-audio'
    ]         
    chromium = playwright.chromium
    browser = await chromium.launch(
        headless=False,
        args=browser_args,
    )

    context = await browser.new_context(
        ignore_https_errors=True,
        locale='en-US',
        permissions=['notifications'],
    )

    page = await context.new_page()
    await stealth_async(page)
    cursor = create_cursor(page)

    await page.goto('https://google.com', wait_until='networkidle')
    print(page.url)

    await context.close()
    await browser.close()
async def main():
    async with async_playwright() as playwright:
        await run(playwright)

if __name__ == '__main__':
    loop = asyncio.get_event_loop()
    loop.run_until_complete(main())
loop.close()

By the way:
OS: macOS Monterey 12.3.1
Docker Engine: 20.10.14
Python 3.9
Playwright 1.22

@mxschmitt
Copy link
Member

mxschmitt commented May 19, 2022

This is using playwright_stealth which is not supported. I did the following which makes it work for me:

  • removed playwright_stealth
  • removed create_cursor
  • removed the args:
    •     '--single-process',
      
    •    '--disable-gpu',
      

Then it was working for me.

@denismur
Copy link
Author

denismur commented May 20, 2022

@mxschmitt Doesn't worked for me. No output, just script freeze on run.
Could you share the details of your script? On what python version you've tested?

@mxschmitt
Copy link
Member

I was using the official Docker image: docker run -it mcr.microsoft.com/playwright/python:v1.22.0-focal /bin/bash

@yury-s
Copy link
Member

yury-s commented May 26, 2022

@mxschmitt Doesn't worked for me. No output, just script freeze on run.
Could you share the details of your script? On what python version you've tested?

Works for me as well, the command I ran inside docker is :

xvfb-run --auto-servernum --server-num=1 --server-args='-screen 0, 1920x1080x24' python test.py
# test.py
from playwright.async_api import Playwright, async_playwright, expect
import asyncio

async def run(playwright: Playwright) -> None:
    browser_args = [
        '--window-size=1300,570',
        '--window-position=000,000',
        '--disable-dev-shm-usage',
        '--no-sandbox',
        '--disable-web-security',
        '--disable-features=site-per-process',
        '--disable-setuid-sandbox',
        '--disable-accelerated-2d-canvas',
        '--no-first-run',
        '--no-zygote',
        '--use-gl=egl',
        '--disable-blink-features=AutomationControlled',
        '--disable-background-networking',
        '--enable-features=NetworkService,NetworkServiceInProcess',
        '--disable-background-timer-throttling',
        '--disable-backgrounding-occluded-windows',
        '--disable-breakpad',
        '--disable-client-side-phishing-detection',
        '--disable-component-extensions-with-background-pages',
        '--disable-default-apps',
        '--disable-extensions',
        '--disable-features=Translate',
        '--disable-hang-monitor',
        '--disable-ipc-flooding-protection',
        '--disable-popup-blocking',
        '--disable-prompt-on-repost',
        '--disable-renderer-backgrounding',
        '--disable-sync',
        '--force-color-profile=srgb',
        '--metrics-recording-only',
        '--enable-automation',
        '--password-store=basic',
        '--use-mock-keychain',
        '--hide-scrollbars',
        '--mute-audio'
    ]         
    chromium = playwright.chromium
    browser = await chromium.launch(
        headless=False,
        args=browser_args,
    )

    context = await browser.new_context(
        ignore_https_errors=True,
        locale='en-US',
        permissions=['notifications'],
    )

    page = await context.new_page()

    await page.goto('https://google.com', wait_until='networkidle')
    print(page.url)

    await context.close()
    await browser.close()
async def main():
    async with async_playwright() as playwright:
        await run(playwright)

if __name__ == '__main__':
    loop = asyncio.get_event_loop()
    loop.run_until_complete(main())
loop.close()

This is the output:

root@4f7680af8851:~# xvfb-run --auto-servernum --server-num=1 --server-args='-screen 0, 1920x1080x24' python test.py 
https://www.google.com/
root@4f7680af8851:~#

@aslushnikov
Copy link
Collaborator

Closing this since there's no repro. If this still happens for you and you think the issue is on Playwright side, please re-file with a repro that we can debug!

@Ayan-Bandyopadhyay
Copy link

I'm running into this issue while trying to run a fastapi server with poetry. The error message is Looks like you launched a headed browser without having a XServer running. Set either 'headless: true' or use 'xvfb-run <your-playwright-app>' before running Playwright.

Here is my Dockerfile:

FROM mcr.microsoft.com/playwright/python:v1.47.0-jammy

ENV POETRY_HOME=/opt/poetry
ENV POETRY_VENV=/opt/poetry-venv
ENV POETRY_DATA_DIR=/opt/poetry-data
ENV POETRY_CONFIG_DIR=/opt/poetry-config
# Tell Poetry where to place its cache and virtual environment
ENV POETRY_CACHE_DIR=/opt/.cache

VOLUME ./.poetry-data-cache /opt/poetry-data
VOLUME ./.poetry-cache /opt/.cache

RUN python -m pip install poetry==1.7.1
WORKDIR /workspace
RUN poetry config virtualenvs.create false

COPY ./pyproject.toml ./pyproject.toml
COPY ./poetry.lock ./poetry.lock
# install only deps in dependency list first and lockfile to cache them
RUN poetry install --no-root --only main

COPY . .
# then install our own module
RUN poetry install --only main

EXPOSE 8000

ENTRYPOINT ["xvfb-run", "--auto-servernum", "--server-num=1", "--server-args='-screen 0, 1920x1080x24'", "poetry", "run", "start" ]

And here is the fastapi endpoint that throws the above error:

@app.get("/test")
async def test():
    browser_args = [
        "--window-size=1300,570",
        "--window-position=000,000",
        "--disable-dev-shm-usage",
        "--no-sandbox",
        "--disable-web-security",
        "--disable-features=site-per-process",
        "--disable-setuid-sandbox",
        "--disable-accelerated-2d-canvas",
        "--no-first-run",
        "--no-zygote",
        "--use-gl=egl",
        "--disable-blink-features=AutomationControlled",
        "--disable-background-networking",
        "--enable-features=NetworkService,NetworkServiceInProcess",
        "--disable-background-timer-throttling",
        "--disable-backgrounding-occluded-windows",
        "--disable-breakpad",
        "--disable-client-side-phishing-detection",
        "--disable-component-extensions-with-background-pages",
        "--disable-default-apps",
        "--disable-extensions",
        "--disable-features=Translate",
        "--disable-hang-monitor",
        "--disable-ipc-flooding-protection",
        "--disable-popup-blocking",
        "--disable-prompt-on-repost",
        "--disable-renderer-backgrounding",
        "--disable-sync",
        "--force-color-profile=srgb",
        "--metrics-recording-only",
        "--enable-automation",
        "--password-store=basic",
        "--use-mock-keychain",
        "--hide-scrollbars",
        "--mute-audio",
    ]
    async with async_playwright() as pw:
        browser = await pw.chromium.launch(
            args=browser_args + [f"--remote-debugging-port=9222"],
            headless=False,
        )
        context = await browser.new_context()
        page = await context.new_page()
        await page.goto("https://example.com")
        html = await page.content()
        await browser.close()

    return {"html": html}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

6 participants