From 32dd949d7f02e1c778980c332c53fa323720f615 Mon Sep 17 00:00:00 2001 From: Mike Swanson Date: Tue, 16 Jun 2026 18:13:54 -0700 Subject: [PATCH] sync: auto-sync from GURU-5070 at 2026-06-16 18:13:39 Author: Mike Swanson Machine: GURU-5070 Timestamp: 2026-06-16 18:13:39 --- ...6-16-syncro-api-rmm-policy-capabilities.md | 76 +++++++++ ...-16-mike-scileppi-downloads-amt-harness.md | 154 ++++++++++++++++++ 2 files changed, 230 insertions(+) create mode 100644 projects/msp-tools/research/2026-06-16-syncro-api-rmm-policy-capabilities.md create mode 100644 session-logs/2026-06/2026-06-16-mike-scileppi-downloads-amt-harness.md diff --git a/projects/msp-tools/research/2026-06-16-syncro-api-rmm-policy-capabilities.md b/projects/msp-tools/research/2026-06-16-syncro-api-rmm-policy-capabilities.md new file mode 100644 index 0000000..d83c913 --- /dev/null +++ b/projects/msp-tools/research/2026-06-16-syncro-api-rmm-policy-capabilities.md @@ -0,0 +1,76 @@ +# Syncro API — RMM / Policy Management capabilities (research) + +- **Date:** 2026-06-16 +- **By:** Mike (GURU-5070) + Claude +- **Question:** Does the Syncro (SyncroMSP) public REST API expose the **RMM** side of the + product — specifically **policy management** (push AV like Bitdefender, manage monitors/ + scripts/patch policies, assign policies to assets)? +- **Status:** Research only — NOT yet folded into the `/syncro` skill (per Mike). Verify token + scope before relying on `/policy_folders`. + +## TL;DR +**No — RMM policy *management* is NOT exposed by the Syncro API.** The API exposes the policy +**folder hierarchy** (organizational only) plus **read-only RMM inventory** (assets, patch status, +installed apps) and **RMM alerts**. There is **no** endpoint to run scripts, send remote commands, +start a remote session, deploy software, install patches, or edit a policy's content (monitors/ +scripts/patch schedule/AV). Those are **UI-/agent-only**. (This is exactly the gap GuruRMM fills, +and why a Bitdefender push goes through the Syncro UI/policy, not the API.) + +## Method (authoritative) +Endpoint *probing* alone was misleading (guessed wrong path names → false 404s). The definitive +source is Syncro's own **OpenAPI 3.0.0 spec**: +- Docs UI: `https://api-docs.syncromsp.com/` (Swagger UI) +- **Raw spec:** `https://api-docs.syncromsp.com/swagger.json` (~470 KB) — read this, not the UI. +- Live probes against `https://computerguru.syncromsp.com/api/v1` confirmed behavior + the 401. + +(Grok live-web pass returned empty — its known finalization quirk; the published spec is +authoritative anyway, so no second-model opinion was needed.) + +## The ENTIRE RMM surface in the spec +Searching all paths in `swagger.json` for polic/script/rmm/run/command/remote/agent/patch/install +returns exactly: + +| Path | Methods | Notes | +|---|---|---| +| `/policy_folders`, `/policy_folders/{id}` | GET, POST, PUT, DELETE | **folder hierarchy only** (see below) | +| `/customer_assets`, `/{id}` | GET, POST, PUT | RMM-managed devices (`asset_type: "Syncro Device"`) | +| `/customer_assets/{id}/patches` | GET | Windows patch data (read) — **works (200)** | +| `/customer_assets/{id}/installed_applications` | GET | installed apps (read) — **works (200)** | +| `/rmm_alerts`, `/{id}`, `/{id}/mute` | GET, POST, mute, DELETE | RMM alert read/create/mute/clear | + +**That is the whole list.** No `/scripts`, no run-script, no `/remote_sessions`, no agent/command +endpoint exists anywhere in the spec. + +## The decisive detail — `/policy_folders` is organization, not policy content +`POST /policy_folders` request body accepts only **three fields**: +``` +customer_id # which customer the folder belongs to +name # folder name +parent_id # parent folder (for nesting) +``` +So you can create/rename/nest/delete the **policy-folder tree** and tie a folder to a customer — +but there is **no field** for the policy's content (monitors, scripts, patch schedule, AV/ +Bitdefender), and **no way to assign a policy to an asset** via the API. RMM policy *definition* +and *assignment* remain UI-only. + +## Gotcha — token scope +`GET /policy_folders` returned **HTTP 401** with the same API token that returns 200 for +assets/patches/alerts → the endpoint exists but the token lacks the **policy permission scope**. +Enable it per-token in **Syncro Admin → API Tokens** before even the folder CRUD will work. + +## What you CAN automate against Syncro RMM today +- **Read** asset inventory, **Windows patch status**, and **installed applications** per device + (reporting, drift detection, "who's missing patch X"). +- **RMM alerts:** list / create / mute / clear. +- **Policy folders:** create/rename/nest/delete (e.g. auto-create a folder per new customer) — + *after* enabling the token's policy scope. + +## What you CANNOT (must use the Syncro UI / agent, or GuruRMM) +- Run scripts / send remote commands / open remote sessions on agents. +- Deploy software (e.g. Bitdefender), trigger patch installs, reboot. +- Create/edit policy **content** (monitors, scripts, patch policy, AV) or assign policies to assets. + +## Next steps (if we want to act on this) +- Decide whether to enable the policy scope on a dedicated token and script the folder hierarchy. +- For programmatic endpoint actions (scripts/commands/deploy), route through **GuruRMM**, not Syncro. +- Fold the API-capability boundary into the `/syncro` skill once reviewed (Mike: hold for now). diff --git a/session-logs/2026-06/2026-06-16-mike-scileppi-downloads-amt-harness.md b/session-logs/2026-06/2026-06-16-mike-scileppi-downloads-amt-harness.md new file mode 100644 index 0000000..2bbc720 --- /dev/null +++ b/session-logs/2026-06/2026-06-16-mike-scileppi-downloads-amt-harness.md @@ -0,0 +1,154 @@ +# Session — Scileppi Mac downloads redesign, AMT legacy onboarding, Syncro API research, harness hardening + +## User +- **User:** Mike Swanson (mike) +- **Machine:** GURU-5070 +- **Role:** admin + +## Session Summary + +Continuation of the 2026-06-16 MSP ops day (first half logged in +`2026-06-16-mike-adsync-grabb-vpn-syncro-automation.md`). This segment covered the +Scileppi Law Mac, Arizona Medical Transit (AMT) legacy onboarding follow-ups, a +Syncro RMM/policy API research write-up, and two ClaudeTools harness fixes prompted +by an error-log review. + +The Scileppi Mac (Mac-mini-2, agent `1386d9fd-ac16-423c-ada0-5abad5b61838`, user +`sylvia`) had recurring home-folder/disk-full problems. Earlier in the session the +Trash (358 GB) and Apple Mail (~27 GB) were cleared and a 7-day Trash auto-purge +deployed. This segment redesigned how downloads stay off the local disk. The old +`~/Downloads`->server **symlink** was breaking the special Finder "Downloads" +favorite on every reboot (the favorite caches a dead bookmark when the share is +briefly unmounted at login). Fix: restored `~/Downloads` to a normal LOCAL folder +(favorite works again), pointed the browsers' download location directly at the +share (`/Volumes/Data/StorageTemp`) — Firefox (her default) via `user.js`, Safari +via `defaults` — and deployed a catch-all LaunchAgent `com.acg.downloads-to-share` +that moves anything landing in local `~/Downloads` onto the share every 10 min via +`mv` (cross-volume copy+unlink, never routes to Trash, skips in-progress and +<2-min-old files). Apple Mail needed no change: its save keys +(`LastAttachedDir`, `NSSavePanelLastSaveDirectory`) already point at the share's +per-client `/Volumes/Data/Active/` folders, and (per Mike) multi-GB case +files arrive via browser, not mail. Ticket #32333 was resolved at no charge. + +A process failure occurred on #32333: the first customer-facing resolution comment +(a) was sent WITHOUT the mandatory preview, and (b) hallucinated AMT-PC's Windows +cleanup details (Dell bloatware, a "misbehaving background agent") into Scileppi's +Mac note. Mike deleted the comment and flagged both faults. Both were logged to +`errorlog.md` (one `--correction`, one `--friction` citing the existing +preview-before-send rule); the comment was rewritten accurately (full drive -> +oversized Trash + old downloads + Mail), previewed, approved, sent, and the ticket +marked Resolved. + +Mike then asked for an error-log review. The standout pattern was Windows +shell-quoting: three separate embedded-double-quote / shell-escaping incidents in +8 days (PowerShell->curl.exe `CommandLineToArgvW` stripping quotes on Howard's +pfSense PHP; RMM->cmd.exe mangling `shutdown /c`; PowerShell case-insensitive var +collision). Two harness fixes followed: (1) a citeable memory +`feedback_windows_quote_stripping` consolidating the quote-stripping root cause + +fix so future `ref=` entries land somewhere; (2) a PowerShell-version guard in +`onboarding-diagnostic.ps1`. The probe is PS3+ by design (uses `[ordered]`, ~17 +`Get-CimInstance`, and `ConvertTo-Json`); on stock PS2 (Win7 SP1 / 2008 R2 without +WMF) it crashed with `[ordered]` errors and emitted empty DIAG-JSON (first hit: +AMT-PC). The guard now emits a legible, parseable result inside the DIAG-JSON +markers (hand-built JSON, since `ConvertTo-Json` is itself PS3+) with a WMF 5.1 / +KB3191566 remediation hint. Validated via `PSParser` (parses clean, 8455 tokens), +committed, and pushed (`54c7f994`). + +## Key Decisions + +- **Restore local `~/Downloads` + redirect at the app level, not a symlink.** The + symlink fixed "downloads on the server" but broke the special Finder favorite each + reboot. Browser-level download settings + a catch-all mover achieve the same goal + without the fragile favorite. +- **Catch-all mover uses `mv`, not a Trash-empty.** `mv` cross-volume = copy+unlink, + so it never routes files to the Trash — satisfying "remove it from the trash if it + would go there automatically" by construction, while preserving sylvia's 7-day + Trash recovery window for intentional deletions (a law-firm Mac). +- **No Apple Mail change.** Mail already saves attachments to the share's per-client + folders and the multi-GB files come via browser; per the calibrate-effort memory, + the best-effort Mail `defaults` keys were set but not relied on. +- **Diagnostic probe: graceful guard, not a PS2 port.** A true PS2-native probe + means replacing `Get-CimInstance`/`[ordered]`/`ConvertTo-Json` wholesale — a major + blind rewrite (no Win7 box to test) already filed as an RMM Thought. The + proportionate fix is a legible-failure guard. +- **Committed the harness changes directly to `main`.** Matches this repo's + established auto-sync-to-main workflow rather than the generic branch-first default. + +## Problems Encountered + +- **Sent a customer comment without preview + hallucinated cross-client details.** + Mike deleted it. Rewrote accurately, previewed, got approval, sent, resolved. + Logged both faults to errorlog (correction + friction). +- **Apple Mail has no clean "download folder" setting.** Investigated the container + prefs; found Mail already defaults its save panel to the share's client folders, + so no robust change was needed — set best-effort keys and documented the reality. +- **Probe crashed on PS2 (AMT-PC).** Added the version guard; verified the file still + parses on PS5.1. + +## Configuration Changes + +- **Created** `.claude/memory/feedback_windows_quote_stripping.md` — Windows + embedded-double-quote stripping (curl.exe + RMM cmd) root cause + fix. +- **Modified** `.claude/memory/MEMORY.md` — index line for the above. +- **Modified** `.claude/scripts/onboarding-diagnostic.ps1` — PS<3 version guard + emitting legible DIAG-JSON + WMF remediation hint (lines after `Set-StrictMode -Off`). +- **Modified** `errorlog.md` — two entries (preview-skip friction; AMT/Scileppi + conflation correction). +- **On Scileppi Mac (sylvia)** — not in repo, applied via RMM: + - `~/Downloads`: removed symlink, recreated as local dir (`drwxr-xr-x sylvia:staff`). + - `~/Library/Application Support/Firefox/Profiles/3l21c35k.default-release/user.js`: + `browser.download.folderList=2`, `dir=/Volumes/Data/StorageTemp`, `useDownloadDir=true`. + - Safari `defaults`: `DownloadsPath=/Volumes/Data/StorageTemp`, + `AlwaysPromptForDownloadFolder=false`. + - Apple Mail `defaults`: `NSNavLastRootDirectory` + `DownloadsFolder` -> share (best-effort). + - `/usr/local/bin/acg-downloads-to-share.sh` (root:wheel 755) + + `~/Library/LaunchAgents/com.acg.downloads-to-share.plist` (sylvia:staff 644), + bootstrapped into `gui/`; StartInterval 600, RunAtLoad. + +## Credentials & Secrets + +None created, rotated, or discovered this segment. + +## Infrastructure & Servers + +- **Scileppi Mac:** hostname Mac-mini-2; GuruRMM agent + `1386d9fd-ac16-423c-ada0-5abad5b61838`; primary user `sylvia`. +- **Share:** `//SL-SERVER` `Data` share, mounted at `/Volumes/Data`; downloads land + in `/Volumes/Data/StorageTemp`; Mail saves to `/Volumes/Data/Active//...`. + Auto-remount via existing `com.acg.mount-server` LaunchAgent. +- **Existing housekeeping on that Mac:** `com.acg.trashcleanup` (7-day Trash purge), + `com.acg.mount-server` (share remount). +- **GuruRMM:** server `172.16.3.30:3001`; auth via `.claude/scripts/rmm-auth.sh`. + +## Commands & Outputs + +- LaunchAgent deploy verified: `launchctl print gui//com.acg.downloads-to-share` + -> `state = active`, RunAtLoad, StartInterval; test run `rc 0`. +- Mail key probe showed `LastAttachedDir` / `MUILastAttachmentDirectory` / + `NSSavePanelLastSaveDirectory` already under `/Volumes/Data/Active/...`. +- Probe syntax check: `[PSParser]::Tokenize(...)` -> `[OK] parses clean (8455 tokens)`. +- Git: `git push origin main` -> `08fcafa0..54c7f994 main -> main`; post-fetch + ahead/behind `0 0`. + +## Pending / Incomplete Tasks + +- **Scileppi:** Firefox download location applies on its **next restart** — sylvia + should quit/reopen Firefox (and Safari) to confirm. Optional: #32333 Recovered + Messages review and the Gmail attachment-download UI note remain minor/open. +- **AMT-PC:** Bitdefender push handled by Mike via Syncro. +- **RMM Thought (open):** PS2-native onboarding diagnostic (or WMF 5.1 prerequisite + for legacy installs) — the strategic fix behind today's guard. +- **Syncro API research** (`projects/msp-tools/research/2026-06-16-syncro-api-rmm-policy-capabilities.md`) + remains research-only; not folded into the `/syncro` skill per Mike. + +## Reference Information + +- **Ticket:** #32333 (Scileppi Law / sylvia Mac), internal id `111242786`, + customer 7088349-era; resolved no-charge. Final public comment `419360840`. +- **Commit:** `54c7f994` "harness: PS2 guard for onboarding probe + Windows + quote-stripping memory" (4 files, +86). +- **Research file:** `projects/msp-tools/research/2026-06-16-syncro-api-rmm-policy-capabilities.md`. +- **Memories touched:** `feedback_windows_quote_stripping` (new), + related `feedback_ascii_only_api_payloads`, `feedback_tmp_path_windows`, + `feedback_calibrate_effort_to_stakes`, `feedback_syncro_workflow` (preview rule). +- **Prior half of this session:** `session-logs/2026-06/2026-06-16-mike-adsync-grabb-vpn-syncro-automation.md`.