Files
claudetools/.claude/skills/rmm-audit/SKILL.md
Mike Swanson 5ead5d4dee sync: auto-sync from DESKTOP-0O8A1RL at 2026-05-19 17:56:56
Author: Mike Swanson
Machine: DESKTOP-0O8A1RL
Timestamp: 2026-05-19 17:56:56
2026-05-19 17:57:02 -07:00

14 KiB

name, description
name description
rmm-audit Periodic end-to-end verification of the GuruRMM codebase. Runs 5 parallel audit passes: (1) API/route inventory cross-reference, (2) UI coverage and gap update, (3) Rust code quality and standards compliance, (4) TypeScript/frontend quality, (5) security and data integrity. Produces a timestamped audit report and updates the living docs (UI_GAPS.md, FEATURE_ROADMAP.md). Takes 10-20 minutes. Invoke explicitly only — no auto-trigger. Use /rmm-audit for a full audit. Optional arg: --pass=<name> to run a single pass (api, ui, rust, ts, security).

GuruRMM End-to-End Audit

Periodic full-stack sanity check. Read-only by default — findings are written to a report file and living docs are updated. No code is changed.


Execution Overview

Phase 0: Context load (coordinator reads key files)
Phase 1: Spawn 4 parallel audit agents
Phase 2: Collect findings, aggregate, score
Phase 3: Write report + update living docs
Phase 4: Present summary to user

The audit is orchestrated here (Claude coordinator). All heavy passes run in parallel subagents. Each agent returns structured findings; the coordinator aggregates and writes the final report.


Phase 0: Context Load (Coordinator Reads These)

Before spawning agents, read these yourself:

  1. projects/msp-tools/guru-rmm/CONTEXT.md — project overview and current state
  2. projects/msp-tools/guru-rmm/docs/UI_GAPS.md — living gap tracker (may be stale)
  3. projects/msp-tools/guru-rmm/docs/FEATURE_ROADMAP.md — planned features
  4. .claude/CODING_GUIDELINES.md — development standards

Capture from server/src/api/mod.rs the complete route list (all .route(...) calls). This becomes the authority route list passed to both the API and UI audit agents.


Phase 1: Parallel Audit Agents

Spawn all four agents simultaneously in a single message. Each agent receives the full context it needs inline — do not assume they share context.


Agent A — API Coverage & Route Inventory

Goal: Find server endpoints with no dashboard UI exposure, and dashboard API client functions calling non-existent or mismatched server routes.

Instructions for agent:

  1. Read server/src/api/mod.rs in full — extract every .route(path, method) into a list grouped by resource (agents, clients, sites, policies, etc.).

  2. Read dashboard/src/api/client.ts — extract every API function and the URL path it calls.

  3. Cross-reference:

    • Server routes with no client.ts function → ORPHANED ROUTE (dead code or intentionally backend-only — distinguish by context)
    • Client.ts functions whose URL doesn't match any server route → BROKEN CALL
    • Server routes that exist but the client uses a different HTTP method → METHOD MISMATCH
  4. Read dashboard/src/App.tsx (or wherever routes are defined) — list all frontend pages and their paths.

  5. For each API resource group, assess whether a UI page exposes the major CRUD operations. Flag any resource that has full CRUD on the server but only partial or no UI.

  6. Return structured findings: [SEVERITY] Description — file:line.


Agent B — Rust Code Quality & Standards

Goal: Find violations of the established Rust coding standards and common quality issues across the server codebase.

Instructions for agent:

Read .claude/CODING_GUIDELINES.md first to know the rules. Then check:

Compliance checks:

  • .unwrap() or .expect() calls outside of #[cfg(test)] blocks — these panic in production. Flag every occurrence with context. Note: .expect("invariant reason") in truly-impossible paths is acceptable if the reason is clear.
  • todo!() or unimplemented!() macros in non-test production code paths.
  • sqlx::query! / sqlx::query_as! macros (banned — project uses SQLX_OFFLINE=true with runtime queries only).
  • format!() used to construct SQL strings (injection risk — parameterize instead).
  • unwrap_or_default() on Option<String> producing empty strings that get used as real values without validation.

Auth coverage:

  • Read server/src/api/mod.rs — identify which route groups use .layer(middleware::from_fn(...)) or similar auth middleware vs. which are public.
  • Any non-public route that doesn't go through JWT auth or agent-key auth middleware is a [CRITICAL] finding.
  • Check that agent-key-authenticated routes cannot be accessed with JWT tokens and vice versa (separation of agent vs. admin plane).

Logging hygiene:

  • Grep for tracing:: / log:: calls that include agent keys, passwords, tokens, or PII (email addresses, user names). These should use redacted representations.

Error handling:

  • HTTP handlers returning 500 with e.to_string() — raw error messages can leak internals to API callers. Should be logged server-side, generic message returned.

Search paths: server/src/ only. Exclude server/src/db/mod.rs re-exports.

Return structured findings with file:line references.


Agent C — TypeScript / Frontend Quality

Goal: Find frontend code quality issues, standards violations, and missing UI patterns.

Instructions for agent:

TypeScript quality:

  • any type annotations in dashboard/src/ — each is a type safety gap.
  • @ts-ignore or @ts-expect-error comments — note reason and whether they're still needed.
  • console.log / console.error left in production code (not in dev-only blocks).
  • Hardcoded API base URLs instead of using import.meta.env.VITE_API_URL.

Component patterns:

  • React components without error boundaries on data-fetching sections — if the query throws, the entire page crashes.
  • useQuery calls with no isLoading or isError handling — silent failures.
  • Forms with no validation on submit (empty strings submitted as values).
  • Missing key prop on mapped elements.

API client completeness:

  • For each resource in client.ts, verify the TypeScript interface matches what the server actually returns. Focus on fields that were added recently: Agent should have is_dc, maintenance_mode_note, agent_version. AgentUsers should have is_dc: boolean, groups: GroupEntry[]. Any missing field means the UI silently shows undefined.

Accessibility basics:

  • Buttons with icon-only content (no text) — need title or aria-label.
  • Form inputs without associated <label> elements.

Search paths: dashboard/src/ only.

Return structured findings with file:line references.


Agent D — Data Integrity & Security

Goal: Verify migration sequencing, wire format consistency between agent and server, policy system end-to-end completeness, and security boundaries.

Instructions for agent:

Migration integrity:

  • List all files in server/migrations/ — verify numbering is sequential with no gaps (001, 002, 003... no 019a or skipped numbers).
  • For each CREATE TABLE in migrations, verify a corresponding db/<table>.rs module exists in the server.
  • For each db/<table>.rs, verify the struct fields match the migration columns. Focus on recently added columns: agent_users.is_dc, agent_users.groups.

Agent ↔ Server wire format:

  • Read agent/src/transport/mod.rs — list all AgentMessage variants and ServerMessage variants.
  • Read server/src/ws/mod.rs — find the dispatch match arm for each incoming AgentMessage. Any AgentMessage variant with no server handler is dead code (or a missing implementation).
  • Read server/src/policy/config_update.rs — list all fields in AgentConfigUpdate. Cross-reference with agent/src/transport/mod.rs ConfigUpdatePayload. Any field the server sends but the agent doesn't handle (or vice versa) is a silent drop.

Policy system completeness:

  • Read server/src/db/policies.rs PolicyData struct — list all sections.
  • Read server/src/policy/merge.rs — verify every section in PolicyData has a corresponding merge function called in merge_policy_data().
  • Read server/src/policy/config_update.rs — verify every section in PolicyData is either mapped to AgentConfigUpdate or intentionally server-side-only (like thresholds). Document which is which.
  • Check server/src/policy/effective.rs — are there assertions/tests for every PolicyData section having a system default value?

Version consistency:

  • agent/Cargo.toml version vs. the version string the server expects in heartbeats. The server should not hard-reject agents on minor version differences.
  • server/Cargo.toml version — is it being bumped on releases?

WebSocket message validation:

  • In server/src/ws/mod.rs, for each AgentMessage variant that carries a payload, is the payload validated before use? (e.g., empty hostnames, negative numbers, excessively large strings that could be a DoS vector).

Return structured findings with file:line references.


Phase 2: Aggregating Findings

Collect all four agents' outputs. Classify each finding:

Severity Meaning
[CRITICAL] Security vulnerability, data loss risk, or production crash path
[HIGH] Functional gap blocking a core workflow, or standards violation with user impact
[MEDIUM] Code quality issue, UI gap, or inconsistency without immediate impact
[LOW] Minor polish, dead code, missing comment
[INFO] Neutral observation, completed item, or context note

Deduplicate: if two agents flag the same issue from different angles, merge into one finding with both references.


Phase 3: Write Report + Update Living Docs

Report Location

Write to: projects/msp-tools/guru-rmm/reports/YYYY-MM-DD-rmm-audit.md (use actual date). If a report from today already exists, append a -2 suffix.

Report Format

# GuruRMM Audit Report — YYYY-MM-DD

**Auditor:** Claude (claude-sonnet-4-6)
**Passes:** API Coverage, UI Gaps, Rust Quality, TypeScript Quality, Data Integrity
**Previous audit:** [link to prior report if one exists, else "First audit"]

---

## Executive Summary

| Pass | Total | Critical | High | Medium | Low |
|------|-------|---------|------|--------|-----|
| API Coverage | N | N | N | N | N |
| UI Gaps | N | N | N | N | N |
| Rust Quality | N | N | N | N | N |
| TypeScript | N | N | N | N | N |
| Data Integrity | N | N | N | N | N |
| **TOTAL** | **N** | **N** | **N** | **N** | **N** |

**Requires immediate action:** [list of CRITICAL findings in one line each]

---

## Pass 1: API Coverage

### [SEVERITY] Finding Title
**File:** path/to/file.rs:LINE
**Detail:** What the problem is, why it matters.
**Recommendation:** What to do.

[repeat for each finding]

---

## Pass 2: UI Gaps

[Same format. Cross-reference against UI_GAPS.md — note which items in that doc
are now COMPLETE vs. still open vs. newly discovered.]

---

## Pass 3: Rust Code Quality

[findings]

---

## Pass 4: TypeScript / Frontend Quality

[findings]

---

## Pass 5: Data Integrity & Security

[findings]

---

## UI_GAPS.md Delta

Items completed since last audit:
- [x] Example completed gap

Items still open:
- [ ] Example open gap — still unimplemented

New gaps discovered this audit:
- [ ] Example new gap

---

## Recommended Action Order

1. [CRITICAL items, sorted by impact]
2. [HIGH items]
3. [MEDIUM items — can be batched]

Update UI_GAPS.md

After writing the report, update docs/UI_GAPS.md:

  • Mark items [x] if the audit confirmed they're fully implemented
  • Update "Last Updated" date
  • Add any newly discovered gaps under the appropriate priority section
  • Do NOT remove completed items — move them to the "Completed Features" section

Phase 4: User Summary

Present a concise summary to the user:

Audit complete. Report: projects/msp-tools/guru-rmm/reports/YYYY-MM-DD-rmm-audit.md

CRITICAL (N): [one-line each]
HIGH (N):     [one-line each]
MEDIUM (N):   Batched in report.

UI_GAPS.md: N items marked complete, N new gaps added.

Recommended first action: [the single highest-priority finding]

Then ask: "Want me to start on any of these findings?"


Conventions

  • Read, don't run. This skill never executes code or makes API calls. It reads files and uses Grep/GrepAI for search.
  • Derive from code, not docs. Treat all .md documentation as potentially stale. The code is truth.
  • Be specific. Every finding needs a file:line reference. Vague findings ("the code could be better") are useless.
  • No false positives. If something looks like a problem but context makes it acceptable, note it as [INFO] with the reason it's OK.
  • Severity is impact, not effort. A two-line fix can be [CRITICAL] if it's a security issue.
  • Commit the report. After writing, delegate to Gitea Agent to commit the report file (not the code changes — those are separate work items).

Reference: Key Files by Area

Server

Area Key Files
Routes server/src/api/mod.rs
DB layer server/src/db/*.rs
WebSocket server/src/ws/mod.rs
Policy system server/src/policy/
Migrations server/migrations/*.sql

Dashboard

Area Key Files
Routes dashboard/src/App.tsx
Pages dashboard/src/pages/*.tsx
API client dashboard/src/api/client.ts
Components dashboard/src/components/*.tsx

Agent

Area Key Files
Wire format agent/src/transport/mod.rs
WS handler agent/src/transport/websocket.rs
Metrics agent/src/metrics/
Users agent/src/users.rs

Docs / Standards

Area Key Files
Coding standards .claude/CODING_GUIDELINES.md
Feature roadmap projects/msp-tools/guru-rmm/docs/FEATURE_ROADMAP.md
UI gaps tracker projects/msp-tools/guru-rmm/docs/UI_GAPS.md
Architecture decisions projects/msp-tools/guru-rmm/docs/ARCHITECTURE_DECISIONS.md
Past audit reports projects/msp-tools/guru-rmm/reports/