refactor: enforce device labels, unify screenshot, remove deprecated commands, session-id-less design
- Device labels: lowercase, no whitespace, only a-z 0-9 - _ (enforced at config time) - Session IDs removed: device label is the sole identifier - Routes changed: /sessions/:id → /devices/:label - Removed commands: click, type, find-window, wait-for-window, label, old version, server-version - Renamed: status → version (compares relay/remote.py/client commits) - Unified screenshot: takes 'screen' or a window label as argument - Windows listed with human-readable labels (same format as device labels) - Single instance enforcement via PID lock file - Removed input.rs (click/type functionality) - All docs and code in English - Protocol: Hello.label is now required (String, not Option<String>) - Client auto-migrates invalid labels on startup
This commit is contained in:
parent
5fd01a423d
commit
0b4a6de8ae
14 changed files with 736 additions and 1180 deletions
130
SKILL.md
130
SKILL.md
|
|
@ -1,110 +1,92 @@
|
|||
# Skill: helios-remote
|
||||
|
||||
> **Hinweis:** Dieses Repo enthält außer diesem Skill noch Rust-Code (Client, Server) und Assets. Die anderen Dateien und Ordner im Repo sind für den Skill nicht relevant - nicht lesen, nicht anfassen.
|
||||
> **Note:** This repo also contains Rust code (client, server) and assets.
|
||||
> Those files are not relevant for using the skill — don't read or modify them.
|
||||
|
||||
Steuere PCs die über den Helios Remote Relay-Server verbunden sind.
|
||||
Control PCs connected to the Helios Remote Relay Server.
|
||||
|
||||
## Wann nutzen
|
||||
## When to use
|
||||
|
||||
Wenn Moritz sagt, dass ich etwas auf einem verbundenen PC tun soll:
|
||||
- "Mach auf meinem PC..."
|
||||
- "Schau mal was auf dem Rechner läuft..."
|
||||
- "Nimm einen Screenshot von..."
|
||||
- "Klick auf X, tippe Y..."
|
||||
- Allgemein: Remote-Zugriff auf einen PC der gerade online ist
|
||||
When Moritz asks to do something on a connected PC:
|
||||
- "Do X on my PC..."
|
||||
- "Check what's running on the computer..."
|
||||
- "Take a screenshot of..."
|
||||
- General: remote access to an online PC
|
||||
|
||||
## Setup
|
||||
|
||||
- **Script:** `skills/helios-remote/remote.py`
|
||||
- **Config:** `skills/helios-remote/config.env` (URL + API-Key, nicht ändern)
|
||||
- **Config:** `skills/helios-remote/config.env` (URL + API key, don't modify)
|
||||
- `SKILL_DIR=/home/moritz/.openclaw/workspace/skills/helios-remote`
|
||||
|
||||
## Wichtige Regeln
|
||||
## Important Rules
|
||||
|
||||
- **Vor destruktiven Aktionen** (Wallpaper, Registry, Systemeinstellungen, Dateien löschen) immer erst den aktuellen Zustand lesen und merken!
|
||||
- Wallpaper auslesen: `(Get-ItemProperty 'HKCU:\Control Panel\Desktop').WallPaper`
|
||||
- **Label-Routing:** `session_id` kann UUID oder Label-Name sein → einfach `"Moritz PC"` verwenden
|
||||
- **Before destructive actions** (wallpaper, registry, system settings, deleting files) always read the current state first!
|
||||
- Wallpaper: `(Get-ItemProperty 'HKCU:\Control Panel\Desktop').WallPaper`
|
||||
- **Device labels are lowercase**, no whitespace, only `a-z 0-9 - _` (e.g. `moritz_pc`)
|
||||
|
||||
## Befehle
|
||||
## Commands
|
||||
|
||||
```bash
|
||||
SKILL_DIR=/home/moritz/.openclaw/workspace/skills/helios-remote
|
||||
|
||||
# Sessions
|
||||
python $SKILL_DIR/remote.py sessions
|
||||
python $SKILL_DIR/remote.py server-version
|
||||
python $SKILL_DIR/remote.py version "Moritz PC"
|
||||
# Devices
|
||||
python $SKILL_DIR/remote.py devices
|
||||
|
||||
# Screenshot → /tmp/helios-remote-screenshot.png
|
||||
# IMMER screenshot-window bevorzugen (spart Bandbreite)!
|
||||
python $SKILL_DIR/remote.py screenshot-window "Moritz PC" "chrome" # aktives Fenster by title
|
||||
python $SKILL_DIR/remote.py screenshot "Moritz PC" # nur wenn kein Fenster bekannt
|
||||
# ALWAYS prefer window screenshots (saves bandwidth)!
|
||||
python $SKILL_DIR/remote.py screenshot moritz_pc google_chrome # window by label
|
||||
python $SKILL_DIR/remote.py screenshot moritz_pc screen # full screen only when no window known
|
||||
|
||||
# Shell-Befehl (PowerShell, kein wrapper nötig)
|
||||
python $SKILL_DIR/remote.py exec "Moritz PC" "Get-Process"
|
||||
python $SKILL_DIR/remote.py exec "Moritz PC" "hostname"
|
||||
# Mit längerer Timeout für Downloads etc. (default: 30s)
|
||||
python $SKILL_DIR/remote.py exec "Moritz PC" --timeout 600 "Invoke-WebRequest -Uri https://... -OutFile C:\file.zip"
|
||||
# Shell command (PowerShell, no wrapper needed)
|
||||
python $SKILL_DIR/remote.py exec moritz_pc "Get-Process"
|
||||
python $SKILL_DIR/remote.py exec moritz_pc "hostname"
|
||||
# With longer timeout for downloads etc. (default: 30s)
|
||||
python $SKILL_DIR/remote.py exec moritz_pc --timeout 600 "Invoke-WebRequest -Uri https://... -OutFile C:\file.zip"
|
||||
|
||||
# Mausklick / Text tippen
|
||||
python $SKILL_DIR/remote.py click "Moritz PC" 960 540
|
||||
python $SKILL_DIR/remote.py type "Moritz PC" "Hello World"
|
||||
# Windows (visible only, shown with human-readable labels)
|
||||
python $SKILL_DIR/remote.py windows moritz_pc
|
||||
python $SKILL_DIR/remote.py focus moritz_pc discord
|
||||
python $SKILL_DIR/remote.py maximize moritz_pc google_chrome
|
||||
python $SKILL_DIR/remote.py minimize-all moritz_pc
|
||||
|
||||
# Fenster (nur sichtbare werden angezeigt)
|
||||
python $SKILL_DIR/remote.py windows "Moritz PC"
|
||||
python $SKILL_DIR/remote.py find-window "Moritz PC" "chrome"
|
||||
python $SKILL_DIR/remote.py focus "Moritz PC" <window_id>
|
||||
python $SKILL_DIR/remote.py maximize "Moritz PC" <window_id>
|
||||
python $SKILL_DIR/remote.py minimize-all "Moritz PC"
|
||||
# Launch program (fire-and-forget)
|
||||
python $SKILL_DIR/remote.py run moritz_pc notepad.exe
|
||||
|
||||
# Programm starten (fire-and-forget)
|
||||
python $SKILL_DIR/remote.py run "Moritz PC" notepad.exe
|
||||
|
||||
# User um etwas bitten (zeigt MessageBox, blockiert bis OK)
|
||||
python $SKILL_DIR/remote.py prompt "Moritz PC" "Bitte klicke auf Speichern, dann OK"
|
||||
python $SKILL_DIR/remote.py prompt "Moritz PC" "UAC-Dialog erscheint gleich - bitte bestätigen" --title "Aktion erforderlich"
|
||||
# Ask user to do something (shows MessageBox, blocks until OK)
|
||||
python $SKILL_DIR/remote.py prompt moritz_pc "Please click Save, then OK"
|
||||
python $SKILL_DIR/remote.py prompt moritz_pc "UAC dialog coming - please confirm" --title "Action required"
|
||||
|
||||
# Clipboard
|
||||
python $SKILL_DIR/remote.py clipboard-get "Moritz PC"
|
||||
python $SKILL_DIR/remote.py clipboard-set "Moritz PC" "Text in Zwischenablage"
|
||||
python $SKILL_DIR/remote.py clipboard-get moritz_pc
|
||||
python $SKILL_DIR/remote.py clipboard-set moritz_pc "Text for clipboard"
|
||||
|
||||
# Dateien hoch-/runterladen
|
||||
python $SKILL_DIR/remote.py upload "Moritz PC" /tmp/local.txt "C:\Users\Moritz\Desktop\remote.txt"
|
||||
python $SKILL_DIR/remote.py download "Moritz PC" "C:\Users\Moritz\file.txt" /tmp/downloaded.txt
|
||||
# File transfer
|
||||
python $SKILL_DIR/remote.py upload moritz_pc /tmp/local.txt "C:\Users\Moritz\Desktop\remote.txt"
|
||||
python $SKILL_DIR/remote.py download moritz_pc "C:\Users\Moritz\file.txt" /tmp/downloaded.txt
|
||||
|
||||
# Label setzen
|
||||
python $SKILL_DIR/remote.py label "Moritz PC" "Neues Label"
|
||||
# Version: compare relay + remote.py + client commits (are they in sync?)
|
||||
python $SKILL_DIR/remote.py version moritz_pc
|
||||
|
||||
# Client log (last 100 lines, --lines for more)
|
||||
python $SKILL_DIR/remote.py logs moritz_pc
|
||||
python $SKILL_DIR/remote.py logs moritz_pc --lines 200
|
||||
```
|
||||
|
||||
## Typischer Workflow: UI-Aufgabe
|
||||
## Typical Workflow: UI Task
|
||||
|
||||
1. `screenshot` → Bildschirm anschauen
|
||||
2. `find-window` → Fenster-ID holen
|
||||
3. `focus` → Fenster in den Vordergrund
|
||||
4. `exec` / `click` / `type` → Aktion ausführen
|
||||
5. `screenshot` → Ergebnis prüfen
|
||||
1. `screenshot <device> screen` → look at the screen
|
||||
2. `windows <device>` → find the window label
|
||||
3. `focus <device> <window_label>` → bring it to front
|
||||
4. `exec` → perform the action
|
||||
5. `screenshot <device> <window_label>` → verify result
|
||||
|
||||
# Warten bis ein Fenster erscheint (z.B. nach Programmstart)
|
||||
python $SKILL_DIR/remote.py wait-for-window "Moritz PC" "notepad" --timeout 10
|
||||
## ⚠️ Prompt Rule (important!)
|
||||
|
||||
# Status: Relay + remote.py + Client-Commit vergleichen (sind alle in sync?)
|
||||
python $SKILL_DIR/remote.py status "Moritz PC"
|
||||
|
||||
# Client-Log (letzte 100 Zeilen, --lines für mehr)
|
||||
python $SKILL_DIR/remote.py logs "Moritz PC"
|
||||
python $SKILL_DIR/remote.py logs "Moritz PC" --lines 200
|
||||
```
|
||||
|
||||
## ⚠️ Klick-Regel (wichtig!)
|
||||
|
||||
**Niemals blind klicken.** Pixel-Koordinaten aus Screenshots sind unzuverlässig.
|
||||
|
||||
Wenn ich auf einen Button oder UI-Element klicken muss:
|
||||
1. Erst `prompt` benutzen um Moritz zu bitten es selbst zu klicken
|
||||
2. Dann weitermachen sobald er OK drückt
|
||||
**Never interact with UI blindly.** When you need the user to click something:
|
||||
|
||||
```bash
|
||||
python $SKILL_DIR/remote.py prompt "Moritz PC" "Bitte klicke auf [Speichern], dann OK drücken"
|
||||
python $SKILL_DIR/remote.py prompt moritz_pc "Please click [Save], then press OK"
|
||||
```
|
||||
|
||||
Ausnahme: wenn ich die exakten Koordinaten eines Elements kenne (z.B. durch wiederholte Nutzung desselben UIs).
|
||||
This blocks until the user confirms. Use it whenever manual interaction is needed.
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue