The tenant contact address had no server-side validation, so a direct API caller could store any string in the field service notices are sent to. UpdateTenantConfiguration now rejects non-addresses, recipient lists (a comma would silently widen who receives those notices), display-name forms and control characters (mail-header injection), and normalizes what it stores. Empty stays valid - having no contact address is a legitimate state. The seed path had a worse problem than missing validation. It was a read-modify-write of the whole model through SaveTenantConfigurationAsync, which upserts with TableUpdateMode.Replace and no ETag: a concurrent portal save was clobbered by the seeder's stale snapshot of EVERY field, not just ContactEmail. It also wrote straight through IConfigRepository, bypassing the TenantConfigurationService cache, so a seeded address stayed invisible for the full 5-minute TTL. TrySeedTenantContactEmailAsync now writes ETag-conditionally in Merge mode - one property, and a 412 means someone else wrote the row so the seed abandons rather than overwriting the winner. A lost seed is recoverable on the next maintenance run; a lost admin edit is not. The same seed logic existed twice (preview notification-email save and the maintenance backfill). Both now call a single owner on TenantConfigurationService, which holds the never-overwrite invariant, the cache eviction and the fail-soft guarantee. Fail-soft lives in the service rather than the repository so it holds for any implementation. Tests cover the validator, the service contract, and the repository against a mocked TableClient: Merge mode, the ETag actually passed, only ContactEmail in the patch, the 412 race, 404, storage faults. Plus a regression pin that SaveTenantConfigurationAsync is never called from the seed path. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
AutopilotMonitor
Advanced monitoring and troubleshooting solution for Windows Autopilot deployments. Gain full visibility into every enrollment session with a detailed event timeline, fleet health dashboards, and session reporting. Define custom analysis rules to automatically detect issues and gather rules to collect targeted evidence. Retrieve diagnostics packages on demand, configure agent settings like auto-reboot behavior and automatic timezone adjustment — all managed centrally from the web dashboard.
Private Preview
Autopilot Monitor is currently running as a Private Preview. Visit autopilotmonitor.com to request access and learn more.
Overview
Autopilot Monitor provides real-time tracking, intelligent diagnostics, and automated troubleshooting for Windows Autopilot enrollment processes. It consists of:
- Bootstrap Script — PowerShell script deployed via Intune that starts monitoring early in the enrollment process
- Monitoring Agent — Lightweight .NET application that collects telemetry and evidence during enrollment
- Backend API — Azure Functions-based ingestion and processing pipeline
- Web Dashboard — Next.js application for real-time monitoring and fleet analytics
Architecture
For detailed information about the system architecture, components, and data flow, see Architecture Documentation.
Documentation
Full admin documentation is available at docs.autopilotmonitor.com
License
This project uses a split licensing model:
- MIT License — Agent (
src/Agent/) and Shared library (src/Shared/) — unrestricted use on end-user devices - AGPL-3.0 — Backend (
src/Backend/), Web Dashboard (src/Web/), and MCP Server (src/McpServer/) — server-side components remain open source
See LICENSE for full details.



