Back to blog
AzureBest PracticesCloud SecurityMonitoring & LoggingOperations & Compliance

Security Contact Has No Email: Fixing Silent Defender for Cloud Alerts

Defender for Cloud alerts are useless if no one is notified. Learn why a missing security contact email matters and how to fix it with CLI, Bicep, and policy.

TL;DR

This check flags Defender for Cloud security contacts that have no email address set, which means high severity alerts get raised but never reach a human. Fix it by adding at least one monitored email to your security contact configuration, ideally a shared distribution list rather than a single person.

Microsoft Defender for Cloud spends its day scanning your subscriptions for threats: brute force attempts on a VM, a crypto miner spinning up on a container, a suspicious sign-in to a storage account. When it finds something, it generates a security alert. The question this check answers is simple but important: when that alert fires, does anyone actually find out?

If your security contact has no email address configured, the answer is no. Alerts pile up inside the portal, waiting for someone to log in and notice them. That is rarely how breaches get caught in time.


What this check detects

The securitycenter_noemail check inspects the security contact configuration in Microsoft Defender for Cloud (formerly Azure Security Center) for a given subscription. It fails when a security contact exists but has no email address attached to it.

A security contact in Defender for Cloud is the destination for two kinds of notifications:

  • Security alerts: emails sent when Defender detects active threats, typically filtered by severity.
  • Attack path and recommendation notifications: periodic summaries of high risk findings affecting your environment.

Without an email address, neither of these reaches anyone. The configuration exists in name only.

Note: Defender for Cloud notification settings are configured per subscription, not per tenant. A clean configuration on one subscription tells you nothing about the others. This is a common blind spot in multi-subscription environments.


Why it matters

Detection without notification is barely detection at all. The whole value of a tool like Defender for Cloud rests on shrinking the gap between when something bad happens and when your team responds. An empty email field stretches that gap from minutes to days, or until the next time someone happens to open the portal.

Consider how this plays out in practice:

  • Off-hours attacks go unanswered. Most intrusions do not respect business hours. A brute force alert at 2 AM Saturday is useless if it sits in a portal nobody is watching until Monday.
  • Lateral movement gets a head start. An attacker who lands on one compromised VM uses the quiet time to pivot. Every hour without a response widens the blast radius.
  • Compliance findings. Frameworks like the Microsoft Cloud Security Benchmark, CIS Azure, and SOC 2 explicitly expect security alerts to reach a responsible party. An unconfigured contact is a documented gap during an audit.

A security alert that nobody reads is an incident report you are writing for the breach you have not noticed yet.

This is one of those misconfigurations that costs nothing to fix and quietly undermines everything else you have invested in. You can have Defender for Cloud running at the highest plan tier, with every recommendation green, and still miss a live intrusion because the alert went nowhere.


How to fix it

The fix is to configure at least one valid email address on the security contact. Below are three ways to do it: the portal, the Azure CLI, and infrastructure as code.

Option 1: Azure portal

  1. Open Microsoft Defender for Cloud in the Azure portal.
  2. In the left menu, go to Environment settings.
  3. Select the subscription you want to configure.
  4. Choose Email notifications.
  5. Under Email recipients, enter one or more email addresses. You can also enable notifications to subscription owners and contributors by role.
  6. Set the alert severity threshold (High is the sensible default for direct emails).
  7. Click Save.

Tip: Use a shared distribution list or a security team alias rather than a single engineer's address. People change teams, go on leave, and leave the company. A mailbox like [email protected] survives all of that.

Option 2: Azure CLI

You can set the security contact email with the az security contact commands. List the current contacts first to see what you are working with:

az security contact list --output table

Then create or update the contact with an email address. On recent CLI versions, contacts are named (the default is default):

az security contact create \
  --name "default" \
  --emails "[email protected]" \
  --notifications-by-role-roles "Owner" \
  --alert-notifications-state "On" \
  --alert-notifications-minimal-severity "High"

Warning: The az security contact command syntax has changed across CLI versions and the security extension. If a flag is rejected, run az security contact create --help to confirm the exact parameters your version expects. Older versions used a single --email flag and a --phone argument.

Verify the change took effect:

az security contact show --name "default" --output json

Option 3: Infrastructure as code (Bicep)

If you manage subscriptions with Bicep, declare the security contact so it is enforced as part of your deployment:

resource securityContact 'Microsoft.Security/securityContacts@2023-12-01-preview' = {
  name: 'default'
  properties: {
    emails: '[email protected]'
    isEnabled: true
    notificationsByRole: {
      state: 'On'
      roles: [
        'Owner'
      ]
    }
    alertNotifications: {
      state: 'On'
      minimalSeverity: 'High'
    }
  }
}

The Terraform equivalent uses the azurerm_security_center_contact resource:

resource "azurerm_security_center_contact" "default" {
  name                = "default"
  email               = "[email protected]"
  alert_notifications = true
  alerts_to_admins    = true
}

Note: A comma-separated string in the emails field lets you list multiple recipients, but a distribution list is cleaner to maintain. Manage the membership in your identity provider, not in your IaC.


How to prevent it from happening again

Fixing one subscription is easy. Keeping every subscription configured as your estate grows is the real challenge. Bake the requirement into your guardrails so it is never a manual step.

Enforce with Azure Policy

Microsoft ships built-in policy definitions that audit this exact condition. Look for the policy titled "Subscriptions should have a contact email address for security issues" and assign it at the management group level so it covers every subscription, current and future.

# Find the built-in policy definition
az policy definition list \
  --query "[?contains(displayName, 'contact email address for security issues')].{name:name, displayName:displayName}" \
  --output table

Assign it across a management group:

az policy assignment create \
  --name "require-security-contact-email" \
  --display-name "Require security contact email" \
  --scope "/providers/Microsoft.Management/managementGroups/your-mg-id" \
  --policy ""

This policy is audit-only, so it reports non-compliant subscriptions rather than blocking anything. Pair it with a remediation step so newly onboarded subscriptions get flagged the moment they drift.

Gate it in CI/CD

If subscription setup runs through a pipeline, add a check that fails the build when the security contact has no email. A short script in your deployment stage closes the loop:

CONTACT_EMAIL=$(az security contact show --name "default" \
  --query "emails" --output tsv 2>/dev/null)

if [ -z "$CONTACT_EMAIL" ]; then
  echo "FAIL: No security contact email configured for this subscription."
  exit 1
fi
echo "OK: Security contact email set to $CONTACT_EMAIL"

Tip: Lensix runs the securitycenter_noemail check continuously across all your subscriptions, so you catch a missing contact email without writing or maintaining any of this glue yourself. Continuous monitoring beats a one-time pipeline check that only runs at deploy time.


Best practices

Setting an email is the floor, not the ceiling. A few habits make the notification path genuinely reliable:

  • Send to a shared mailbox or alias. Avoid tying critical alerts to one person's account.
  • Route to a system, not just an inbox. Forward the security alias into your SIEM, ticketing system, or on-call tool so alerts become tracked work, not just unread mail.
  • Set the severity threshold deliberately. High severity to direct email keeps signal high. Pull medium and low findings into a dashboard or scheduled digest instead of flooding the inbox.
  • Test the path. Trigger a sample alert and confirm it actually arrives. A configured email that lands in a spam filter is no better than an empty field.
  • Cover every subscription. Apply the configuration at the management group level through policy so new subscriptions inherit it automatically.
  • Review contacts during offboarding. When someone leaves, make sure their address has not become the sole recipient on any subscription.

None of this is expensive or complicated. It is the kind of small, boring control that separates teams who hear about an incident in minutes from teams who read about it in the breach report. Set the email, route it somewhere a human will act on it, and enforce it everywhere by default.