# Desktop environment
<subtitle>Sandbox with Ubuntu desktop and VNC access. </subtitle>

This template creates a sandbox with a complete Ubuntu 22.04 desktop environment, including the XFCE desktop, common applications, and VNC streaming for remote access. It is ideal for building AI agents that need to interact with graphical user interfaces.

The template includes:
- **Ubuntu 22.04** with XFCE desktop environment
- **VNC streaming**: Browser-based access via [noVNC](https://novnc.com/)
- **Preinstalled Apps**: LibreOffice, text editor, file manager and common tools
- **Automation tools**: [xdotool](https://github.com/jordansissel/xdotool) and [scrot](https://github.com/resurrecting-open-source-projects/scrot), for programmatic control of the desktop

## Template definition

This template installs the desktop environment, sets up VNC streaming via [x11vnc](https://github.com/LibVNC/x11vnc) and noVNC, and configures the startup script.

```python
# template.py
from ucloud_sandbox import Template, wait_for_port

template = (
    Template()
    .from_image("ubuntu:22.04")
    # Initial system setup and packages
    # .apt_install() is not used here because some software packages have interactive prompts (keyboard layout settings, etc.)
    .run_cmd(
        [
            "yes | unminimize",
            "apt-get update",
            "apt-get install -y \
                xserver-xorg \
                xorg \
                x11-xserver-utils \
                xvfb \
                x11-utils \
                xauth \
                xfce4 \
                xfce4-goodies \
                util-linux \
                sudo \
                curl \
                git \
                wget \
                python3-pip \
                xdotool \
                scrot \
                ffmpeg \
                x11vnc \
                net-tools \
                netcat \
                x11-apps \
                libreoffice \
                xpdf \
                gedit \
                xpaint \
                tint2 \
                galculator \
                pcmanfm",
            "apt-get clean",
            "rm -rf /var/lib/apt/lists/*",
        ]
    )
    # Set up NoVNC and websockify
    .run_cmd(
        [
            "git clone --branch e2b-desktop https://github.com/e2b-dev/noVNC.git /opt/noVNC",
            "ln -s /opt/noVNC/vnc.html /opt/noVNC/index.html",
            "git clone --branch v0.12.0 https://github.com/novnc/websockify /opt/noVNC/utils/websockify",
        ]
    )
    # Set default terminal
    .run_cmd(
        "ln -sf /usr/bin/xfce4-terminal.wrapper /etc/alternatives/x-terminal-emulator"
    )
    #Copy startup command
    .copy("start_command.sh", "/start_command.sh")
    .run_cmd("chmod +x /start_command.sh")
    # Set the startup command to start the desktop environment
    .set_start_cmd("/start_command.sh", wait_for_port(6080))
)
```

##Startup script

The startup script initializes the virtual display using [Xvfb](https://www.x.org/releases/X11R7.6/doc/man/man1/Xvfb.1.xhtml) (X virtual framebuffer), starts an XFCE desktop session, starts the VNC server, and exposes the desktop via noVNC on port 6080. This script runs automatically when the sandbox starts.

```bash
#!/bin/bash

# Set display
export DISPLAY=${DISPLAY:-:0}

# Start Xvfb
Xvfb $DISPLAY -ac -screen 0 1024x768x24 -nolisten tcp &
sleep 2

# Start XFCE session
startxfce4 &
sleep 5

# Start VNC server
x11vnc -bg -display $DISPLAY -forever -wait 50 -shared -rfbport 5900 -nopw \
    -noxdamage -noxfixes -nowf -noscr -ping 1 -repeat -speeds lan &
sleep 2

# Start noVNC server
cd /opt/noVNC/utils && ./novnc_proxy --vnc localhost:5900 --listen 6080 --web /opt/noVNC --heartbeat 30 &
sleep 2
```

## Build template

Templates are built with higher CPU and memory allocations to handle the installation of desktop environments. Due to the size of the package to be installed, the build process may take several minutes.

```python
# build.py
from ucloud_sandbox import Template, default_build_logger
from .template import template as desktopTemplate

Template.build(desktopTemplate, 'desktop',
    cpu_count=8,
    memory_mb=8192,
    on_build_logs=default_build_logger(),
)
```
