network/cnmaestro/README.md
2026-05-09 16:54:28 -05:00

2.6 KiB

cnmaestro CLI

Cleanup offline devices and bulk-upgrade firmware on a cnMaestro Cloud instance (cloud.cambiumnetworks.com).

Setup

1. Find your tenant's API base URL

Each cnMaestro Cloud tenant lives on a regional subdomain. Log in to your tenant in a browser and copy the scheme + host portion of the URL — everything before the first /#/. Example:

https://us-e1-s1-cmjbcvncy6.cloud.cambiumnetworks.com/#/VERONA_NETWORKS/home-view/home
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
this is your CNMAESTRO_BASE_URL

2. Create an API client

  1. While logged in, go to the menu (top-right gear/avatar) → Application (or Services) → API Clients.
  2. Click Add New (or Add API Client).
  3. Give it a name (e.g. cnmaestro-cli). Grant a role that has at minimum:
    • Read access to devices and firmware.
    • Delete access to devices.
    • Permission to create firmware-update jobs. The built-in Administrator role covers all three.
  4. Save and copy the Client ID and Client Secret. The secret is shown only once.

3. Install

cd /Users/graham/dev/network/cnmaestro
uv sync
cp .env.example .env
# edit .env with your client id + secret

4. Smoke-test

uv run cnmaestro cleanup --dry-run

This authenticates, lists devices, and prints what would be removed without actually removing anything.

Usage

Remove devices offline > 24h

uv run cnmaestro cleanup                       # interactive, asks before deleting
uv run cnmaestro cleanup --threshold-hours 48  # custom threshold
uv run cnmaestro cleanup --yes                 # non-interactive (cron)
uv run cnmaestro cleanup --dry-run             # just print, never delete

Bulk-upgrade online devices to latest firmware per model

uv run cnmaestro upgrade                       # interactive
uv run cnmaestro upgrade --product ePMP,PMP    # only these products
uv run cnmaestro upgrade --yes                 # non-interactive
uv run cnmaestro upgrade --dry-run             # show planned jobs only

The upgrade command groups devices by (product, target_version) and submits one bulk firmware job per group (cnMaestro caps each job at 100 devices, so larger groups are chunked).

Safety

  • Both commands default to interactive confirmation.
  • cleanup refuses to run if more than 50 % of the fleet would be removed; pass --force to override.
  • Every destructive call (delete, job-submit) is appended to ./cnmaestro.log for audit.
  • The OAuth2 token is held in memory only.

Tests

uv run pytest

All HTTP is mocked with respx; tests never touch the live API.