diff options
| -rw-r--r-- | backend/helpers.py | 18 | ||||
| -rw-r--r-- | backend/main.py | 10 | ||||
| -rw-r--r-- | backend/utilities.py | 18 | ||||
| -rw-r--r-- | frontend/src/components/settings/pages/general/RemoteDebugging.tsx | 34 | ||||
| -rw-r--r-- | frontend/src/components/settings/pages/general/index.tsx | 2 |
5 files changed, 79 insertions, 3 deletions
diff --git a/backend/helpers.py b/backend/helpers.py index 8d329560..5e26f163 100644 --- a/backend/helpers.py +++ b/backend/helpers.py @@ -2,11 +2,15 @@ import certifi import ssl import uuid import re +import subprocess from aiohttp.web import middleware, Response from subprocess import check_output from time import sleep + +REMOTE_DEBUGGER_UNIT = "steam-web-debug-portforward.service" + # global vars csrf_token = str(uuid.uuid4()) ssl_ctx = ssl.create_default_context(cafile=certifi.where()) @@ -63,3 +67,17 @@ def get_user_group() -> str: if group == None: raise ValueError("helpers.get_user_group method called before group variable was set. Run helpers.set_user_group first.") return group + +async def is_systemd_unit_active(unit_name: str) -> bool: + res = subprocess.run(["systemctl", "is-active", unit_name], stdout=subprocess.DEVNULL, stderr=subprocess.DEVNULL) + return res.returncode == 0 + +async def stop_systemd_unit(unit_name: str) -> subprocess.CompletedProcess: + cmd = ["systemctl", "stop", unit_name] + + return subprocess.run(cmd, stdout=subprocess.DEVNULL, stderr=subprocess.DEVNULL) + +async def start_systemd_unit(unit_name: str) -> subprocess.CompletedProcess: + cmd = ["systemctl", "start", unit_name] + + return subprocess.run(cmd, stdout=subprocess.DEVNULL, stderr=subprocess.DEVNULL) diff --git a/backend/main.py b/backend/main.py index 07b086e4..07e82d92 100644 --- a/backend/main.py +++ b/backend/main.py @@ -13,7 +13,7 @@ from subprocess import call # local modules from browser import PluginBrowser -from helpers import csrf_middleware, get_csrf_token, get_user, get_user_group, set_user, set_user_group +from helpers import csrf_middleware, get_csrf_token, get_user, get_user_group, set_user, set_user_group, stop_systemd_unit, REMOTE_DEBUGGER_UNIT from injector import inject_to_tab, tab_has_global_var from loader import Loader from updater import Updater @@ -28,8 +28,9 @@ set_user_group() USER = get_user() GROUP = get_user_group() HOME_PATH = "/home/"+USER +HOMEBREW_PATH = HOME_PATH+"/homebrew" CONFIG = { - "plugin_path": getenv("PLUGIN_PATH", HOME_PATH+"/homebrew/plugins"), + "plugin_path": getenv("PLUGIN_PATH", HOMEBREW_PATH+"/plugins"), "chown_plugin_path": getenv("CHOWN_PLUGIN_PATH", "1") == "1", "server_host": getenv("SERVER_HOST", "127.0.0.1"), "server_port": int(getenv("SERVER_PORT", "1337")), @@ -47,6 +48,9 @@ async def chown_plugin_dir(_): if code_chown != 0 or code_chmod != 0: logger.error(f"chown/chmod exited with a non-zero exit code (chown: {code_chown}, chmod: {code_chmod})") +def remote_debugging_allowed(): + return path.exists(HOMEBREW_PATH + "/allow_remote_debugging") + class PluginManager: def __init__(self) -> None: self.loop = get_event_loop() @@ -66,6 +70,8 @@ class PluginManager: self.web_app.on_startup.append(chown_plugin_dir) self.loop.create_task(self.loader_reinjector()) self.loop.create_task(self.load_plugins()) + if not remote_debugging_allowed(): + self.loop.create_task(stop_systemd_unit(REMOTE_DEBUGGER_UNIT)) self.loop.set_exception_handler(self.exception_handler) self.web_app.add_routes([get("/auth/token", self.get_auth_token)]) diff --git a/backend/utilities.py b/backend/utilities.py index 834faeb2..9c0c6388 100644 --- a/backend/utilities.py +++ b/backend/utilities.py @@ -5,6 +5,7 @@ from aiohttp import ClientSession, web from injector import inject_to_tab import helpers +import subprocess class Utilities: def __init__(self, context) -> None: @@ -16,7 +17,10 @@ class Utilities: "confirm_plugin_install": self.confirm_plugin_install, "execute_in_tab": self.execute_in_tab, "inject_css_into_tab": self.inject_css_into_tab, - "remove_css_from_tab": self.remove_css_from_tab + "remove_css_from_tab": self.remove_css_from_tab, + "allow_remote_debugging": self.allow_remote_debugging, + "disallow_remote_debugging": self.disallow_remote_debugging, + "remote_debugging_allowed": self.remote_debugging_allowed } if context: @@ -133,3 +137,15 @@ class Utilities: "success": False, "result": e } + + + async def remote_debugging_allowed(self): + return await helpers.is_systemd_unit_active(helpers.REMOTE_DEBUGGER_UNIT) + + async def allow_remote_debugging(self): + await helpers.start_systemd_unit(helpers.REMOTE_DEBUGGER_UNIT) + return True + + async def disallow_remote_debugging(self): + await helpers.stop_systemd_unit(helpers.REMOTE_DEBUGGER_UNIT) + return True diff --git a/frontend/src/components/settings/pages/general/RemoteDebugging.tsx b/frontend/src/components/settings/pages/general/RemoteDebugging.tsx new file mode 100644 index 00000000..1310263f --- /dev/null +++ b/frontend/src/components/settings/pages/general/RemoteDebugging.tsx @@ -0,0 +1,34 @@ +import { Field, ToggleField } from 'decky-frontend-lib'; +import { useEffect, useState } from 'react'; +import { FaBug } from 'react-icons/fa'; + +export default function RemoteDebuggingSettings() { + const [allowRemoteDebugging, setAllowRemoteDebugging] = useState<boolean>(false); + useEffect(() => { + (async () => { + const res = (await window.DeckyPluginLoader.callServerMethod('remote_debugging_allowed')) as { result: boolean }; + setAllowRemoteDebugging(res.result); + })(); + }, []); + + return ( + <Field + label="Allow Remote CEF Debugging" + description={ + <span style={{ whiteSpace: 'pre-line' }}> + Allow unauthenticated access to the CEF debugger to anyone in your network + </span> + } + icon={<FaBug style={{ display: 'block' }} />} + > + <ToggleField + checked={allowRemoteDebugging} + onChange={(toggleValue) => { + setAllowRemoteDebugging(toggleValue); + if (toggleValue) window.DeckyPluginLoader.callServerMethod('allow_remote_debugging'); + else window.DeckyPluginLoader.callServerMethod('disallow_remote_debugging'); + }} + /> + </Field> + ); +} diff --git a/frontend/src/components/settings/pages/general/index.tsx b/frontend/src/components/settings/pages/general/index.tsx index 7dc5cfa4..16add6bc 100644 --- a/frontend/src/components/settings/pages/general/index.tsx +++ b/frontend/src/components/settings/pages/general/index.tsx @@ -3,6 +3,7 @@ import { useState } from 'react'; import { FaShapes } from 'react-icons/fa'; import { installFromURL } from '../../../store/Store'; +import RemoteDebuggingSettings from './RemoteDebugging'; import UpdaterSettings from './Updater'; export default function GeneralSettings() { @@ -20,6 +21,7 @@ export default function GeneralSettings() { /> </Field> */} <UpdaterSettings /> + <RemoteDebuggingSettings /> <Field label="Manual plugin install" description={<TextField label={'URL'} value={pluginURL} onChange={(e) => setPluginURL(e?.target.value)} />} |
