Стримаємо екран на кілька пристроїв через мережу

Стримаємо екран на кілька пристроїв через мережу

Виникла у мене необхідність виводити дашборд із моніторингом на кілька екранів в офісі. У розпорядженні є кілька старих Raspberry Pi Model B + і гіпервізор з майже необмеженою кількістю ресурсів.

Мабуть, Raspberry Pi Model B+ не має достатньої довільності, щоб тримати постійно запущеним браузер і малювати велику кількість графіки в ньому, через що буває, що сторінка частково глючить і часто вилітає.

Знайшлося досить просте та елегантне рішення, яким я і хочу з вами поділитися.

Як відомо, всі Raspberry мають досить потужний відеопроцесор, який відмінно підходить для апаратного декодування відео. Так з'явилася ідея запускати браузер із дашбордом десь ще, а на малинку передавати готовий потік із відрендереною картинкою.

Плюс до всього це мало спростити управління, тому що в даному випадку все налаштування буде виконуватися на одній віртуалці, яку простіше оновлювати і бекапит.

Сказано зроблено.

Серверна частина

Ми скористаємося готовим Cloud Image для Ubuntu. Не вимагаючи установки, він містить все необхідне для швидкого розгортання віртуальної машини, а підтримка Cloud-Init допомагає моментально налаштувати мережу, додати ssh-ключі та швидко ввести її в дію.

Розгортаємо нову віртуалку і насамперед встановимо на ній Корг, nodm и коробка для флюсу:

apt-get update
apt-get install -y xserver-xorg nodm fluxbox
sed -i 's/^NODM_USER=.*/NODM_USER=ubuntu/' /etc/default/nodm

Також скористаємося конфігом для Xorg, люб'язно наданим нам Diego Ongaro, додавши лише новий дозвіл 1920 × 1080, тому що всі наші монітори використовуватимуть саме його:

cat > /etc/X11/xorg.conf <<EOT
Section "Device"
    Identifier      "device"
    Driver          "vesa"
EndSection

Section "Screen"
    Identifier      "screen"
    Device          "device"
    Monitor         "monitor"
    DefaultDepth    16
    SubSection "Display"
        Modes       "1920x1080" "1280x1024" "1024x768" "800x600"
    EndSubSection
EndSection

Section "Monitor"
    Identifier      "monitor"
    HorizSync       20.0 - 50.0
    VertRefresh     40.0 - 80.0
    Option          "DPMS"
EndSection

Section "ServerLayout"
    Identifier      "layout"
    Screen          "screen"
EndSection
EOT

systemctl restart nodm

Тепер встановимо Firefox, запускати ми його як system сервіс, так що за одне і напишемо unit-файл для нього:

apt-get install -y firefox xdotool

cat > /etc/systemd/system/firefox.service <<EOT
[Unit]
Description=Firefox
After=network.target

[Service]
Restart=always
User=ubuntu
Environment="DISPLAY=:0"
Environment="XAUTHORITY=/home/ubuntu/.Xauthority"
ExecStart=/usr/bin/firefox -url 'http://example.org/mydashboard'
ExecStartPost=/usr/bin/xdotool search --sync --onlyvisible --class "Firefox" windowactivate key F11

[Install]
WantedBy=graphical.target
EOT

systemctl enable firefox
systemctl start firefox

Xdotool необхідний нам для того, щоб запускати firefox відразу в повноекранному режимі.
Використовуючи параметр -url можна вказати будь-яку сторінку, щоб вона відкривалася автоматично при запуску браузера.

На цьому етапі наш кіоск вже готовий, але тепер нам потрібно експортувати картинку по мережі на інші монітори та пристрої. Для цього ми скористаємося можливостями Рух JPEG, формату який частіше використовується для стрімінгу відео з більшості веб-камер.

Для цього нам знадобиться дві речі: FFmpeg з модулем x11 grab, для захоплення картинки з іксів та streamEye, який роздаватиме її нашим клієнтам:

apt-get install -y make gcc ffmpeg 

cd /tmp/
wget https://github.com/ccrisan/streameye/archive/master.tar.gz
tar xvf master.tar.gz 
cd streameye-master/
make
make install

cat > /etc/systemd/system/streameye.service <<EOT
[Unit]
Description=streamEye
After=network.target

[Service]
Restart=always
User=ubuntu
Environment="DISPLAY=:0"
Environment="XAUTHORITY=/home/ubuntu/.Xauthority"
ExecStart=/bin/sh -c 'ffmpeg -f x11grab -s 1920x1080 -i :0 -r 1 -f mjpeg -q:v 5 - 2>/dev/null | streameye'

[Install]
WantedBy=graphical.target
EOT

systemctl enable streameye
systemctl start streameye

Оскільки наша картинка не вимагає швидкого оновлення, я вказав частоту оновлення: 1 кадр в секунду (параметр -r 1) та якість стиснення: 5 (параметр -q:v 5)

Тепер пробуємо зайти на http://your-vm:8080/, у відповідь ви побачите скріншот робочого столу, що постійно оновлюється. Чудово! — те, що й було потрібно.

Клієнтська частина

Тут досі простіше, як я вже сказав використати ми будемо Raspberry Pi Model B+.

Насамперед встановимо на неї ArchLinux ARM, для цього слідуємо інструкції на офіційному сайті.

Нам також потрібно виділити більше пам'яті для нашого відеочіпа, для цього відредагуємо в /boot/config.txt

gpu_mem=128

Завантажимо нашу нову систему і не забувши ініціалізувати pacman keyring, встановимо OMXPlayer:

pacman -Sy omxplayer

Що примітно, OMXPlayer може працювати без іксів, тому все що нам потрібно - це написати unit-файл для нього і запустити:

cat > /etc/systemd/system/omxplayer.service <<EOT
[Unit]
Description=OMXPlayer
Wants=network-online.target
After=network-online.target

[Service]
Type=simple
Restart=always
ExecStart=/usr/bin/omxplayer -r --live -b http://your-vm:8080/ --aspect-mode full

[Install]
WantedBy=multi-user.target
EOT

systemctl enable omxplayer
systemctl start omxplayer

Як параметр -b http://your-vm:8080/ ми надаємо URL з нашого сервера.

На цьому все, на підключеному екрані, відразу повинна з'явитися картинка з нашого сервера. У разі виникнення будь-яких проблем, стрим буде автоматично перезапущено, а клієнти перепідключаться до нього.

Як бонус можна встановити отриману картинку як скрінсейвер на всі комп'ютери в офісі. Для цього вам знадобляться MPV и XScreenSaver:

mode:  one
selected: 0
programs:              
     "Monitoring Screen"  mpv --really-quiet --no-audio --fs       
      --loop=inf --no-stop-screensaver       
      --wid=$XSCREENSAVER_WINDOW        
      http://your-vm:8080/      n
    maze -root        n
    electricsheep --root 1       n

Тепер ваші колеги будуть дуже задоволені 🙂

Джерело: habr.com

Додати коментар або відгук