← Blog

How to Use Your Steam Machine as a Dev Machine

Your Steam Machine is a full Linux PC. It is also the exact hardware your Decky plugins run on. This guide makes it an always-on dev box that you reach from your laptop. Then it shows how to build and test a Decky plugin on it.

Other guides build plugins on a second computer, often a virtual machine. Then a script copies the plugin to the device with your sudo password. Here you build on the Steam Machine itself, and Decky Loader installs the plugin for you. You test on the real Gaming Mode and the real Steam client.

You need the Steam Machine, a keyboard for the first few minutes, and a laptop with a terminal. Do the four steps in order.

Step 1: Remote access and an always-on machine

Set a password and turn on SSH

On the Steam Machine, go to Desktop Mode (Steam button → Power → Switch to Desktop). Open Konsole.

  1. Set a password for the deck user. Every sudo command needs it:

    passwd
    
  2. Turn on the SSH server:

    sudo systemctl enable --now sshd
    
  3. On your laptop, copy your SSH key to the machine. The user is always deck:

    ssh-copy-id deck@<steam-machine-ip>
    
  4. Allow key logins only. On the Steam Machine, create /etc/ssh/sshd_config.d/10-keys-only.conf:

    PasswordAuthentication no
    KbdInteractiveAuthentication no
    PermitRootLogin no
    

    Keep the 10- prefix. SSH uses the first value it reads, so your file must sort before the system's 99-archlinux.conf. Then run sudo systemctl restart sshd.

Settings in /etc stay after SteamOS updates.

Reach it from anywhere with Tailscale

Tailscale puts your devices on a private network, so SSH also works away from home. Its official SteamOS installer puts Tailscale in /opt/tailscale, which stays after system updates:

git clone https://github.com/tailscale-dev/deck-tailscale.git ~/deck-tailscale
sudo -i
cd ~deck/deck-tailscale
bash tailscale.sh
source /etc/profile.d/tailscale.sh
tailscale up --qr --operator=deck --hostname=steam-machine
exit

Scan the QR code with your phone to add the machine to your account. Now connect with ssh deck@steam-machine. Logins still use your SSH key; Tailscale only carries the connection. Turn on automatic updates with sudo /opt/tailscale/tailscale set --auto-update.

Keep it awake

When SteamOS sleeps, it turns off the network, and the machine stops answering. On a machine that is always plugged in, turn off sleep in two places:

  1. In Gaming Mode, open Settings → Power. Set the sleep timer to Never.

  2. Mask the system's sleep targets, so nothing can start a sleep:

    sudo systemctl mask sleep.target suspend.target hibernate.target hybrid-sleep.target
    

If the machine ever powers down, Wake-on-LAN wakes it from your home network. Turn it on for the wired connection:

nmcli connection modify "Wired connection 1" 802-3-ethernet.wake-on-lan magic

To wake it, run wakeonlan -i <broadcast-address> <mac-address> on another computer at home. ip link shows the MAC address.

Keep a terminal session open

tmux keeps your terminal running on the machine between connections. Run it as a user service. Create ~/.config/systemd/user/tmux.service:

[Service]
Type=forking
ExecStart=/usr/bin/tmux new-session -d -s main

[Install]
WantedBy=default.target

Enable it, and let your user services run without a login:

systemctl --user enable --now tmux
loginctl enable-linger deck

Now ssh in and run tmux attach -t main. Do the rest of this guide there.

Step 2: Install Decky Loader

Decky Loader adds plugins to Gaming Mode. They show in the Quick Access Menu (the … button).

  1. In Konsole, run the official installer. Type your deck password when it asks:

    curl -L https://github.com/SteamDeckHomebrew/decky-installer/releases/latest/download/install_release.sh | sh
    
  2. Go to Gaming Mode and press the … button. A plug icon in the Quick Access Menu shows that Decky runs.

  3. Open Decky's gear icon → General, and turn on Developer mode. Step 4 uses the Developer section it adds.

Update Decky from the gear icon → General → Updates. Do this after each SteamOS update. A new SteamOS brings a new Steam client, and Decky updates follow it.

Step 3: Dev environment

SteamOS keeps its system files read-only, and each update replaces them. Your home folder stays as it is. So your tools go in your home folder. Anything that SteamOS does not include runs in a container.

  1. Add your bin folders to PATH:

    mkdir -p ~/.local/bin
    echo 'export PATH=~/.local/bin:~/.local/node/bin:$PATH' >> ~/.bashrc
    source ~/.bashrc
    
  2. Install Node.js and pnpm. Copy the link to the Linux x64 .tar.xz from nodejs.org. Then:

    mkdir -p ~/.local/node
    curl -L <link> | tar -xJ -C ~/.local/node --strip-components=1
    corepack enable
    

    Check with node -v and pnpm -v.

  3. Use Podman for everything else. Podman comes with SteamOS and runs without root:

    podman run --rm -it -v "$PWD:/work:z" -w /work python:3.12-slim bash
    
  4. Set your git identity. Use the email that your GitHub account knows:

    git config --global user.name "Your Name"
    git config --global user.email "you@example.com"
    

Step 4: Build and test a plugin

With Decky installed, Steam's debugger listens on localhost:8080. Its SharedJSContext page is where Decky and its plugins run.

Decky also has an Allow Remote CEF Debugging setting. It opens the debugger to everyone on your network, with no login. You do not need it: the SSH tunnel below reaches localhost:8080 securely. Keep it off.

The loop

  1. Start from the template.

    git clone https://github.com/SteamDeckHomebrew/decky-plugin-template my-plugin
    cd my-plugin
    

    In package.json, set "packageManager": "pnpm@9.15.9". This is the version that the store's builder uses.

  2. Build with the store's own builder image, so you get the same build as your users:

    podman run --rm -e CI=true -v "$PWD:/plugin:z" -v "$PWD/out:/out:z" \
      ghcr.io/steamdeckhomebrew/builder:latest
    

    The built plugin goes to out/. If your Python backend needs more packages, put them in py_modules/ yourself.

  3. Zip it. Decky expects one folder with the plugin's name at the top of the zip:

    mkdir -p pkg/my-plugin
    cp -r out/plugin.json out/package.json out/main.py out/LICENSE out/dist pkg/my-plugin/
    (cd pkg && zip -r ../my-plugin.zip my-plugin)
    
  4. Serve the zip on the machine, so Decky can download it:

    systemd-run --user --unit=zipserve python3 -m http.server 47815
    
  5. Install. Decky downloads the zip, installs it as root and loads it. A running game keeps running.

    • From the menu: Decky gear → Developer → Install Plugin from URL, with http://127.0.0.1:47815/my-plugin.zip.

    • From your laptop: open a tunnel with ssh -L 8080:localhost:8080 deck@steam-machine. In Chrome, open chrome://inspect, add localhost:8080, and open SharedJSContext. Then run:

      DeckyBackend.call("utilities/install_plugin",
        "http://127.0.0.1:47815/my-plugin.zip", "My Plugin", "1.0.0", false)
      
  6. Test. Open your plugin from the Quick Access Menu. Backend logs are in ~/homebrew/logs/<plugin>/. gamescopectl screenshot shot.png captures the real screen.

Put steps 2 to 5 in a script. Then each change is one command away from the TV.

Best practices

  • Check an install by its file. Compare the sha256sum of ~/homebrew/plugins/<name>/dist/index.js with the one in your zip.
  • Read the screen size at runtime with window.innerWidth and window.innerHeight. The interface is 854×534 on a Deck and 1348×758 on a 4K TV.
  • Test buttons with the controller. Components that use Focusable with onActivate respond only to the controller.
  • Reload the whole UI for a clean start. Run SteamClient.Browser.RestartJSContext() in SharedJSContext. Steam's interface and all plugins come back in about 5 seconds.

Ship it

  1. Add a CI job that runs the same builder image and tsc --noEmit.
  2. Attach the zip to each GitHub release, so people can test before the store accepts it.
  3. Open a PR to decky-plugin-database that adds your repo as a submodule. Reviews are slow. A short comment each week keeps the PR open.

Next steps

Your Steam Machine is now an always-on box that you can reach and build on. Some things to try next:

  • Work from anywhere. Install Tailscale on your laptop and phone, with the same account. Then ssh deck@steam-machine works outside your home network, with no ports to open on your router.
  • Stream your games. The machine is always awake, so it is a good Remote Play host. On another device, open Steam or the free Steam Link app. Log in to the same account, and press Stream on a game that is installed on the Steam Machine.
  • Let an AI agent help. Run an AI coding agent in your tmux session. It can write and test plugins, read logs, and manage this machine. Over SSH and Tailscale, it can also manage your other devices, like Steam Decks.
  • Mod your games. With Decky installed, the Nexus Mods plugin lets you find, install and turn mods on and off from the Quick Access Menu. It needs a Nexus Mods Premium account and your API key.