419 lines
13 KiB
Markdown
419 lines
13 KiB
Markdown
# MacBook Pro Node - OpenClaw Gateway Integration
|
|
|
|
## Overview
|
|
|
|
This repository documents the OpenClaw gateway integration for the satware AG MacBook Pro, configured as a remote tool node controlled by the agent-zero Docker container running on the Manjaro PC.
|
|
|
|
## System Information
|
|
|
|
| Property | Value |
|
|
|----------|-------|
|
|
| **Hostname** | satware-AG-MacBook-Pro.local |
|
|
| **OS** | macOS 26.3.1 (Tahoe) |
|
|
| **Kernel** | Darwin 25.3.0 (x86_64) |
|
|
| **User** | MWsatwareAG |
|
|
| **Local IP** | 10.11.206.26 (en0) |
|
|
| **Tailscale IP** | 100.64.0.12 |
|
|
| **OpenClaw Version** | core v2026.3.8 |
|
|
|
|
## Node Configuration
|
|
|
|
### Node ID
|
|
```
|
|
77b912f45a10c92e2970574186426b16f898488c9cd201335235be27d076cdf0
|
|
```
|
|
|
|
### Connection Architecture
|
|
|
|
```text
|
|
┌─────────────────────┐ Tailscale ┌─────────────────────┐
|
|
│ MacBook Pro │ 100.64.0.x │ Manjaro PC │
|
|
│ (Tool Node) │◄──────────────────►│ (Gateway Host) │
|
|
│ │ │ │
|
|
│ OpenClaw Node │ WebSocket │ OpenClaw Gateway │
|
|
│ (remote mode) │◄──────────────────►│ (100.64.0.39) │
|
|
│ v2026.3.8 │ Port 18789 │ Port 18789 │
|
|
│ │ │ │
|
|
│ SSH Client │ SSH Tunnel │ SSH Server │
|
|
│ │──────────────────►│ Port 2222 │
|
|
└─────────────────────┘ └─────────────────────┘
|
|
```
|
|
|
|
### MacBook OpenClaw Config (`~/.openclaw/openclaw.json`)
|
|
```json
|
|
{
|
|
"meta": {
|
|
"lastTouchedVersion": "2026.3.8"
|
|
},
|
|
"gateway": {
|
|
"mode": "remote",
|
|
"remote": {
|
|
"url": "ws://100.64.0.39:18789",
|
|
"token": "skt3_W8A5AVp...",
|
|
"sshTarget": "root@100.64.0.39:2222",
|
|
"sshIdentity": "/Users/MWsatwareAG/.ssh/id_ed25519"
|
|
}
|
|
}
|
|
}
|
|
```
|
|
|
|
### Security Policy (`~/.openclaw/exec-approvals.json`)
|
|
```json
|
|
{
|
|
"version": 1,
|
|
"defaults": {
|
|
"security": "full"
|
|
},
|
|
"agents": {},
|
|
"nodes": {
|
|
"77b912f45a10c92e2970574186426b16f898488c9cd201335235be27d076cdf0": {
|
|
"displayName": "satware AG MacBook Pro",
|
|
"security": "full",
|
|
"allowlist": [
|
|
"system.run",
|
|
"system.run.prepare",
|
|
"system.which",
|
|
"browser.proxy"
|
|
]
|
|
}
|
|
}
|
|
}
|
|
```
|
|
|
|
## Node Capabilities
|
|
|
|
| Capability | Commands | Status |
|
|
|------------|----------|--------|
|
|
| **system** | `system.run`, `system.run.prepare`, `system.which` | ✅ Working |
|
|
| **browser** | `browser.proxy` | ⚠️ Requires browser session |
|
|
| **peekaboo**| `see`, `image`, `app.list`, `clipboard.get/set` | ✅ Active (Vision ready) |
|
|
| **imsg** | `chats`, `history`, `send` | ✅ Active (Full Disk Access) |
|
|
| **apple-notes** | `memo` integrations | ✅ Ready |
|
|
| **apple-reminders** | `remindctl` integrations | ✅ Ready |
|
|
| **camera** | `camera.list`, `camera.snap`, `camera.clip` | ❌ Not supported on darwin |
|
|
| **screen** | `screen.record` | ❌ Not in allowlist for darwin |
|
|
| **canvas** | `canvas.snapshot`, `canvas.present`, etc. | ❌ Not supported on darwin |
|
|
|
|
> **Note**: Vision features in `peekaboo` require **Screen Recording** permissions granted to the Node.js binary (`/usr/local/Cellar/node/25.8.0/bin/node`). UI automation (clicks/typing) requires **Accessibility** permissions granted to the same binary.
|
|
|
|
## Tested Commands
|
|
|
|
### peekaboo
|
|
Advanced UI automation and system introspection.
|
|
|
|
| Command | Status | Notes |
|
|
|---------|--------|-------|
|
|
| `peekaboo image` | ✅ | Screenshot capture (Vision) |
|
|
| `peekaboo app list` | ✅ | Lists running applications |
|
|
| `peekaboo clipboard` | ✅ | Read/write system clipboard |
|
|
| `peekaboo dock list` | ✅ | Lists items in macOS Dock |
|
|
| `peekaboo permissions` | ✅ | Diagnostic for TCC permissions |
|
|
|
|
### imsg
|
|
CLI-based iMessage/SMS integration.
|
|
|
|
| Command | Status | Notes |
|
|
|---------|--------|-------|
|
|
| `imsg chats` | ✅ | Lists recent conversations |
|
|
| `imsg history` | ✅ | Retrieves message history |
|
|
| `imsg send` | ✅ | Sends messages via Messages.app |
|
|
|
|
### system.run
|
|
Execute shell commands on the MacBook node.
|
|
|
|
```bash
|
|
# Basic invocation pattern
|
|
docker exec agent-zero openclaw nodes invoke \
|
|
--node "77b912f45a10c92e2970574186426b16f898488c9cd201335235be27d076cdf0" \
|
|
--command "system.run" \
|
|
--params '{"command":["<cmd>","<args>"]}'
|
|
```
|
|
|
|
#### Working Commands
|
|
|
|
| Command | Result | Notes |
|
|
|---------|--------|-------|
|
|
| `hostname` | ✅ | Returns `satware-AG-MacBook-Pro.local` |
|
|
| `uname -a` | ✅ | Darwin 25.3.0 x86_64 |
|
|
| `sw_vers` | ✅ | macOS 26.3 (Build 25D125) |
|
|
| `ls -la /Users/MWsatwareAG` | ✅ | Full filesystem access |
|
|
| `/sbin/ifconfig en0` | ✅ | Network interface info |
|
|
| `/usr/bin/curl -s https://httpbin.org/ip` | ✅ | External network access |
|
|
| `node --version` | ✅ | Node.js v25.8.0 at `/usr/local/bin/node` |
|
|
| `python3 --version` | ✅ | Python3 at `/usr/bin/python3` |
|
|
| `git --version` | ✅ | Git at `/usr/local/bin/git` |
|
|
| `peekaboo --version` | ✅ | v3.0.0-beta3 (Universal) |
|
|
| `imsg --version` | ✅ | v0.5.0 (Universal, locally built) |
|
|
|
|
#### Known Issues
|
|
|
|
| Issue | Cause | Solution |
|
|
|-------|-------|----------|
|
|
| `spawn ENOENT` errors | Command not in PATH | Use full path (e.g., `/sbin/ifconfig`) |
|
|
| Tailscale CLI timeout | GUI app requires interaction | Use alternative network commands |
|
|
| `browser.proxy` Not Found | No browser session running | Start browser first |
|
|
|
|
### system.which
|
|
Find binary locations on the node.
|
|
|
|
```bash
|
|
docker exec agent-zero openclaw nodes invoke \
|
|
--node "77b912f45a10c92e2970574186426b16f898488c9cd201335235be27d076cdf0" \
|
|
--command "system.which" \
|
|
--params '{"bins":["node","python3","git"]}'
|
|
```
|
|
|
|
Returns:
|
|
```json
|
|
{"bins":{"node":"/usr/local/bin/node","python3":"/usr/bin/python3","git":"/usr/local/bin/git"}}
|
|
```
|
|
|
|
## Quick Reference Commands
|
|
|
|
### Check Node Status
|
|
```bash
|
|
docker exec agent-zero openclaw nodes status
|
|
```
|
|
|
|
### Describe Node Capabilities
|
|
```bash
|
|
docker exec agent-zero openclaw nodes describe --node "77b912f45a10c92e2970574186426b16f898488c9cd201335235be27d076cdf0"
|
|
```
|
|
|
|
### Run Shell Command
|
|
```bash
|
|
docker exec agent-zero openclaw nodes run --node "77b912f45a10c92e2970574186426b16f898488c9cd201335235be27d076cdf0" --raw "uname -a"
|
|
```
|
|
|
|
## Gateway Configuration
|
|
|
|
The OpenClaw gateway runs inside the `agent-zero` Docker container on the Manjaro PC.
|
|
|
|
### Gateway Access URLs
|
|
|
|
| URL | Description |
|
|
|-----|-------------|
|
|
| `http://127.0.0.1:18789/` | Localhost access (Control UI) |
|
|
| `http://localhost:18789/` | Localhost access (Control UI) |
|
|
| `http://100.64.0.39:18789/` | Tailscale LAN access |
|
|
| `ws://100.64.0.39:18789` | WebSocket endpoint for nodes |
|
|
|
|
### Gateway Configuration (`/home/ja/internal/luca/openclaw-data/openclaw.json`)
|
|
|
|
Key gateway settings:
|
|
```json
|
|
{
|
|
"gateway": {
|
|
"port": 18789,
|
|
"mode": "local",
|
|
"bind": "lan",
|
|
"controlUi": {
|
|
"allowedOrigins": [
|
|
"http://localhost:18789",
|
|
"http://127.0.0.1:18789",
|
|
"https://localhost:18789",
|
|
"http://100.64.0.39:18789"
|
|
],
|
|
"allowInsecureAuth": true
|
|
}
|
|
}
|
|
}
|
|
```
|
|
|
|
### Exec Approvals Configuration (`/home/ja/internal/luca/openclaw-data/exec-approvals.json`)
|
|
|
|
Node-specific security policy:
|
|
```json
|
|
{
|
|
"version": 1,
|
|
"defaults": { "security": "full" },
|
|
"nodes": {
|
|
"77b912f45a10c92e2970574186426b16f898488c9cd201335235be27d076cdf0": {
|
|
"displayName": "satware AG MacBook Pro",
|
|
"security": "full",
|
|
"allowlist": ["system.run", "system.run.prepare", "system.which", "browser.proxy"]
|
|
}
|
|
}
|
|
}
|
|
```
|
|
|
|
## Network Configuration
|
|
|
|
### Gateway (Manjaro PC)
|
|
- **Tailscale IP**: 100.64.0.39
|
|
- **WebSocket Port**: 18789
|
|
- **SSH Port**: 2222
|
|
|
|
### MacBook Pro
|
|
- **Tailscale IP**: 100.64.0.12
|
|
- **Local IP**: 10.11.206.26
|
|
- **External IP**: 77.24.181.185 (via curl httpbin.org/ip)
|
|
|
|
## Security Considerations
|
|
|
|
1. **exec-approvals.json**: Currently set to `"security": "full"` for testing
|
|
- Consider `"allowlist"` mode for production
|
|
- Define specific allowed commands in allowlist
|
|
|
|
2. **SSH Access**: MacBook has SSH key-based access to gateway container
|
|
- Key: `~/.ssh/id_ed25519`
|
|
- Target: `root@100.64.0.39:2222`
|
|
|
|
3. **WebSocket Connection**: Unencrypted (ws:// not wss://)
|
|
- Traffic stays within Tailscale mesh network
|
|
- Consider TLS termination for external access
|
|
|
|
## Files
|
|
|
|
| File | Location | Purpose |
|
|
|------|----------|---------|
|
|
| `openclaw.json` | `~/.openclaw/openclaw.json` | Node configuration |
|
|
| `exec-approvals.json` | `~/.openclaw/exec-approvals.json` | Security policy |
|
|
| `paired.json` | Gateway: `openclaw-data/devices/paired.json` | Paired devices registry |
|
|
| `authorized_keys` | Gateway: `ssh-keys/authorized_keys` | SSH access keys |
|
|
|
|
## Developer CLI Tools
|
|
|
|
The MacBook has the following version control CLI tools installed via Homebrew (Intel x86, `/usr/local/bin/`).
|
|
|
|
| Tool | Version | Auth | Host |
|
|
|------|---------|------|------|
|
|
| `tea` | 0.12.0 | `ja` | `https://git.satware.ai` |
|
|
| `gh` | 2.87.3 | `jane-alesi` | `github.com` |
|
|
| `glab` | 1.87.0 | `ja` | `gitlab.satware.com` |
|
|
| `git` | 2.50.1 | n/a | (Apple Git-155, system) |
|
|
|
|
### Auth Configuration Paths
|
|
|
|
| Tool | Config File |
|
|
|------|------------|
|
|
| `tea` | `~/.config/tea/config.yml` |
|
|
| `gh` | `~/.config/gh/hosts.yml` |
|
|
| `glab` | `~/.config/glab-cli/config.yml` |
|
|
|
|
### Verify Auth (SSH-safe)
|
|
|
|
```bash
|
|
export PATH="/usr/local/bin:/usr/bin:/bin:$PATH"
|
|
|
|
# tea - Gitea (git.satware.ai)
|
|
tea logins list
|
|
|
|
# gh - GitHub
|
|
gh auth status
|
|
|
|
# glab - GitLab (gitlab.satware.com)
|
|
glab auth status
|
|
|
|
# git fetch from this repo (bypasses macOS keychain)
|
|
cd ~/infrastructure/mw-macbook-pro
|
|
git -c credential.helper="" fetch origin
|
|
```
|
|
|
|
### Re-run Setup
|
|
|
|
If tokens expire or tools need to be reconfigured:
|
|
|
|
```bash
|
|
# tea
|
|
tea logins add --name git-satware --url https://git.satware.ai --token <TOKEN>
|
|
|
|
# gh
|
|
echo "<GITHUB_TOKEN>" | gh auth login --with-token
|
|
|
|
# glab
|
|
glab auth login --hostname gitlab.satware.com --token <TOKEN>
|
|
```
|
|
|
|
> **Note**: The macOS keychain error `fatal: failed to store: -25308` during non-interactive SSH sessions is cosmetic - use `git -c credential.helper=""` to suppress it. Credentials are stored in the config files above.
|
|
|
|
---
|
|
|
|
## Related Documentation
|
|
|
|
- OpenClaw Docs: https://docs.openclaw.ai/cli/nodes
|
|
- Gateway Setup: `/home/ja/internal/luca/docker-compose.yml`
|
|
- Tailscale: https://tailscale.com
|
|
|
|
## Verification Status
|
|
|
|
**Last Verified**: 2026-03-11 23:15 CET
|
|
|
|
| Component | Status |
|
|
|-----------|--------|
|
|
| **Node Connection** | ✅ Paired & Connected |
|
|
| **Gateway Health** | ✅ OK (158ms via Tailscale) |
|
|
| **system.run** | ✅ Working |
|
|
| **Vision (Peekaboo)**| ✅ Active |
|
|
| **iMessage (imsg)** | ✅ Active |
|
|
| **Capabilities** | `browser`, `system`, `peekaboo`, `imsg`, `apple-notes` |
|
|
|
|
### MacBook launchd Services
|
|
|
|
| Service | Status | Purpose |
|
|
|---------|--------|---------|
|
|
| `ai.openclaw.node` | Running | Primary Node service (v2026.3.8) |
|
|
| `ai.openclaw.gateway` | Unloaded | Disabled (remote node role) |
|
|
| `com.satware.openclaw-tunnel` | Running | SSH tunnel to gateway |
|
|
|
|
### Management Commands (on MacBook)
|
|
|
|
```bash
|
|
# Check service status
|
|
launchctl list | grep openclaw
|
|
|
|
# Restart SSH tunnel
|
|
launchctl unload ~/Library/LaunchAgents/com.satware.openclaw-tunnel.plist
|
|
launchctl load ~/Library/LaunchAgents/com.satware.openclaw-tunnel.plist
|
|
```
|
|
|
|
### Verify from Gateway
|
|
|
|
```bash
|
|
# Check node status
|
|
docker exec agent-zero openclaw nodes status
|
|
|
|
# Test command execution
|
|
docker exec agent-zero openclaw nodes invoke \
|
|
--node "77b912f45a10c92e2970574186426b16f898488c9cd201335235be27d076cdf0" \
|
|
--command "system.run" \
|
|
--params '{"command":["hostname"]}'
|
|
```
|
|
|
|
---
|
|
## SSH system health check (2026-03-04 05:12 CET)
|
|
|
|
Target checked: `MWsatwareAG@100.64.0.12`
|
|
|
|
### Snapshot
|
|
|
|
| Area | Result | Notes |
|
|
|------|--------|-------|
|
|
| Reachability | ✅ OK | SSH login successful |
|
|
| OS | ✅ OK | macOS 26.3, Darwin 25.3.0 |
|
|
| Uptime/Load | ✅ OK | Uptime ~12h; load avg ~3.0 on 16 logical CPUs |
|
|
| CPU | ⚠️ Watch | Short-term spikes from `openclaw-gateway`, `RustDesk`, Weather widget |
|
|
| Memory | ✅ OK | 16 GB total (`hw.memsize: 17179869184`) |
|
|
| Disk | ✅ OK | APFS main container ~18% used; high free capacity |
|
|
| Recent errors | ✅ None critical in sample | No critical/fatal lines surfaced in 2h sample |
|
|
| Listening ports | ⚠️ Review | `22`, `5900`, `3283`, Tailscale/RustDesk-related listeners |
|
|
|
|
### Key commands used
|
|
|
|
```bash
|
|
ssh -o BatchMode=yes -o ConnectTimeout=10 MWsatwareAG@100.64.0.12 'sw_vers; uname -a; uptime; sysctl vm.loadavg'
|
|
ssh -o BatchMode=yes -o ConnectTimeout=10 MWsatwareAG@100.64.0.12 'sysctl hw.memsize; df -h; diskutil apfs list | head -n 80'
|
|
ssh -o BatchMode=yes -o ConnectTimeout=10 MWsatwareAG@100.64.0.12 'ps -Ao pid,pcpu,pmem,comm | sort -k2 -nr | head -n 10'
|
|
ssh -o BatchMode=yes -o ConnectTimeout=10 MWsatwareAG@100.64.0.12 'netstat -anv -p tcp | grep LISTEN | head -n 20'
|
|
```
|
|
|
|
## Next steps
|
|
|
|
1. Run a 5-10 minute process sample to confirm whether high CPU from `openclaw-gateway` is transient.
|
|
2. Validate which externally reachable services are required (`22`, `5900`, `3283`, RustDesk/Tailscale).
|
|
3. If hardening is required, disable unneeded listeners and re-test remote workflows.
|
|
4. Add an automated daily health snapshot job and keep results in this repository.
|
|
|
|
---
|
|
*Last updated: 2026-03-11*
|