Open Stream Deck

Исполнение

Где и как работает плагин: изолированная среда, жизненный цикл, сторожевой таймер, перезапуск и лимиты.

Каждый плагин получает отдельную изолированную среду:

  • iframe с sandbox="allow-scripts" и собственным непрозрачным origin;
  • политика безопасности default-src 'none', script-src 'unsafe-inline' blob: 'wasm-unsafe-eval', worker-src blob: и connect-src только для разрешённых адресов из network;
  • выделенный воркер, в котором исполняется код плагина.

Встроенный скрипт в политике нужен только загрузчику самой среды. Код плагина загружается в воркер из blob: и не имеет DOM, поэтому вставить свой скрипт на страницу он не может.

Из воркера недоступны: окно и DOM приложения, eval и new Function, importScripts и import() по сети, IndexedDB, Cache Storage, cookies, localStorage, сеть вне объявленных адресов. Доступны: таймеры, TextEncoder, TextDecoder, URL, structuredClone, WebAssembly и прочее стандартное окружение воркера.

Жизненный цикл

  1. Приложение создаёт среду, загружает код и отправляет init.
  2. Для каждого действия на видимой странице приходит appear, при уходе со страницы disappear.
  3. Нажатия, сообщения из настроек, ответы брокеров и таймеры приходят событиями.
  4. При остановке плагина среда уничтожается целиком: воркер, таймеры, соединения брокеров.

Сторожевой таймер и перезапуск

Хост раз в 5 секунд проверяет, отвечает ли воркер. Если ответа нет 10 секунд, воркер считается зависшим и уничтожается. Экземпляр также останавливают ошибка при загрузке кода и трап WASM, в том числе паника в Rust.

После сбоя хост перезапускает плагин с паузами 1, 2, 5, 10 и 30 секунд. Если экземпляр проработал дольше минуты, счётчик сбрасывается. Шестой сбой подряд переводит плагин в состояние crashed, дальше его перезапускает только пользователь.

Ошибка в обработчике (Err в Rust, исключение или отклонённый Promise в JavaScript) записывается в журнал и не останавливает плагин.

Лимиты

РесурсОграничение
Одно сообщение в любую сторону2 МиБ
Картинка setImage1 МиБ
Подпись512 символов
Команд от плагина600 подряд, затем 300 в секунду
Активных контекстов256
Таймеров WASM64 одновременно, шаг от 16 мс
Соединений WebSocket через брокер8
HTTP-запросов в полёте через брокер16
Текст в буфер обмена64 КиБ

Плагин, который превысил лимит команд, получает предупреждение в журнал. Лишние команды отбрасываются.