feat(azure): Defender checks related to security contacts and notifications (#3344)

This commit is contained in:
Rubén De la Torre Vico
2024-02-05 13:51:56 +01:00
committed by GitHub
parent c6e8a0b6d3
commit c795d76fe9
14 changed files with 728 additions and 0 deletions

View File

@@ -0,0 +1,30 @@
{
"Provider": "azure",
"CheckID": "defender_additional_email_configured_with_a_security_contact",
"CheckTitle": "Ensure 'Additional email addresses' is Configured with a Security Contact Email",
"CheckType": [],
"ServiceName": "defender",
"SubServiceName": "",
"ResourceIdTemplate": "",
"Severity": "medium",
"ResourceType": "AzureEmailNotifications",
"Description": "Microsoft Defender for Cloud emails the subscription owners whenever a high-severity alert is triggered for their subscription. You should provide a security contact email address as an additional email address.",
"Risk": "Microsoft Defender for Cloud emails the Subscription Owner to notify them about security alerts. Adding your Security Contact's email address to the 'Additional email addresses' field ensures that your organization's Security Team is included in these alerts. This ensures that the proper people are aware of any potential compromise in order to mitigate the risk in a timely fashion.",
"RelatedUrl": "https://docs.microsoft.com/en-us/azure/security-center/security-center-provide-security-contact-details",
"Remediation": {
"Code": {
"CLI": "",
"NativeIaC": "",
"Other": "https://www.trendmicro.com/cloudoneconformity/knowledge-base/azure/SecurityCenter/security-contact-email.html",
"Terraform": ""
},
"Recommendation": {
"Text": "1. From Azure Home select the Portal Menu 2. Select Microsoft Defender for Cloud 3. Click on Environment Settings 4. Click on the appropriate Management Group, Subscription, or Workspace 5. Click on Email notifications 6. Enter a valid security contact email address (or multiple addresses separated by commas) in the Additional email addresses field 7. Click Save",
"Url": "https://learn.microsoft.com/en-us/rest/api/defenderforcloud/security-contacts/list?view=rest-defenderforcloud-2020-01-01-preview&tabs=HTTP"
}
},
"Categories": [],
"DependsOn": [],
"RelatedTo": [],
"Notes": ""
}

View File

@@ -0,0 +1,36 @@
import re
from prowler.lib.check.models import Check, Check_Report_Azure
from prowler.providers.azure.services.defender.defender_client import defender_client
class defender_additional_email_configured_with_a_security_contact(Check):
def execute(self) -> Check_Report_Azure:
findings = []
for (
subscription_name,
security_contacts,
) in defender_client.security_contacts.items():
for contact_name, contact_info in security_contacts.items():
report = Check_Report_Azure(self.metadata())
report.status = "PASS"
report.subscription = subscription_name
report.resource_name = contact_name
report.resource_id = contact_info.resource_id
report.status_extended = f"There is another correct email configured for susbscription {subscription_name}."
emails = contact_info.emails.split(";")
for email in emails:
if re.fullmatch(
r"\b[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Z|a-z]{2,}\b", email
):
break
else:
report.status = "FAIL"
report.status_extended = f"There is not another correct email configured for susbscription {subscription_name}."
findings.append(report)
return findings

View File

@@ -0,0 +1,30 @@
{
"Provider": "azure",
"CheckID": "defender_ensure_notify_alerts_severity_is_high",
"CheckTitle": "Ensure That 'Notify about alerts with the following severity' is Set to 'High'",
"CheckType": [],
"ServiceName": "defender",
"SubServiceName": "",
"ResourceIdTemplate": "",
"Severity": "high",
"ResourceType": "AzureEmailNotifications",
"Description": "Microsoft Defender for Cloud emails the subscription owners whenever a high-severity alert is triggered for their subscription. You should provide a security contact email address as an additional email address.",
"Risk": "Microsoft Defender for Cloud emails the Subscription Owner to notify them about security alerts. Adding your Security Contact's email address to the 'Additional email addresses' field ensures that your organization's Security Team is included in these alerts. This ensures that the proper people are aware of any potential compromise in order to mitigate the risk in a timely fashion.",
"RelatedUrl": "https://docs.microsoft.com/en-us/azure/security-center/security-center-provide-security-contact-details",
"Remediation": {
"Code": {
"CLI": "",
"NativeIaC": "",
"Other": "https://www.trendmicro.com/cloudoneconformity/knowledge-base/azure/SecurityCenter/enable-high-severity-email-notifications.html",
"Terraform": ""
},
"Recommendation": {
"Text": "1. From Azure Home select the Portal Menu 2. Select Microsoft Defender for Cloud 3. Click on Environment Settings 4. Click on the appropriate Management Group, Subscription, or Workspace 5. Click on Email notifications 6. Enter a valid security contact email address (or multiple addresses separated by commas) in the Additional email addresses field 7. Click Save",
"Url": "https://docs.microsoft.com/en-us/rest/api/securitycenter/securitycontacts/list"
}
},
"Categories": [],
"DependsOn": [],
"RelatedTo": [],
"Notes": ""
}

View File

@@ -0,0 +1,27 @@
from prowler.lib.check.models import Check, Check_Report_Azure
from prowler.providers.azure.services.defender.defender_client import defender_client
class defender_ensure_notify_alerts_severity_is_high(Check):
def execute(self) -> Check_Report_Azure:
findings = []
for (
subscription_name,
security_contacts,
) in defender_client.security_contacts.items():
for contact_name, contact_info in security_contacts.items():
report = Check_Report_Azure(self.metadata())
report.status = "PASS"
report.subscription = subscription_name
report.resource_name = contact_name
report.resource_id = contact_info.resource_id
report.status_extended = f"Notifiy alerts are enabled for severity high in susbscription {subscription_name}."
if contact_info.alert_notifications_minimal_severity != "High":
report.status = "FAIL"
report.status_extended = f"Notifiy alerts are not enabled for severity high in susbscription {subscription_name}."
findings.append(report)
return findings

View File

@@ -0,0 +1,30 @@
{
"Provider": "azure",
"CheckID": "defender_ensure_notify_emails_to_owners",
"CheckTitle": "Ensure That 'All users with the following roles' is set to 'Owner'",
"CheckType": [],
"ServiceName": "defender",
"SubServiceName": "",
"ResourceIdTemplate": "",
"Severity": "medium",
"ResourceType": "AzureEmailNotifications",
"Description": "Enable security alert emails to subscription owners.",
"Risk": "Enabling security alert emails to subscription owners ensures that they receive security alert emails from Microsoft. This ensures that they are aware of any potential security issues and can mitigate the risk in a timely fashion.",
"RelatedUrl": "https://docs.microsoft.com/en-us/azure/security-center/security-center-provide-security-contact-details",
"Remediation": {
"Code": {
"CLI": "",
"NativeIaC": "",
"Other": "https://www.trendmicro.com/cloudoneconformity/knowledge-base/azure/SecurityCenter/email-to-subscription-owners.html",
"Terraform": ""
},
"Recommendation": {
"Text": "1. From Azure Home select the Portal Menu 2. Select Microsoft Defender for Cloud 3. Click on Environment Settings 4. Click on the appropriate Management Group, Subscription, or Workspace 5. Click on Email notifications 6. In the drop down of the All users with the following roles field select Owner 7. Click Save",
"Url": "https://docs.microsoft.com/en-us/rest/api/securitycenter/securitycontacts/list"
}
},
"Categories": [],
"DependsOn": [],
"RelatedTo": [],
"Notes": ""
}

View File

@@ -0,0 +1,34 @@
from prowler.lib.check.models import Check, Check_Report_Azure
from prowler.providers.azure.services.defender.defender_client import defender_client
class defender_ensure_notify_emails_to_owners(Check):
def execute(self) -> Check_Report_Azure:
findings = []
for (
subscription_name,
security_contacts,
) in defender_client.security_contacts.items():
for contact_name, contact_info in security_contacts.items():
report = Check_Report_Azure(self.metadata())
report.status = "PASS"
report.subscription = subscription_name
report.resource_name = contact_name
report.resource_id = contact_info.resource_id
report.status_extended = (
f"The Owner role is notified for subscription {subscription_name}."
)
if (
contact_info.notified_roles_state != "On"
or "Owner" not in contact_info.notified_roles
):
report.status = "FAIL"
report.status_extended = f"The Owner role is not notified for subscription {subscription_name}."
findings.append(report)
return findings

View File

@@ -15,6 +15,7 @@ class Defender(AzureService):
self.pricings = self.__get_pricings__()
self.auto_provisioning_settings = self.__get_auto_provisioning_settings__()
self.assessments = self.__get_assessments__()
self.security_contacts = self.__get_security_contacts__()
def __get_pricings__(self):
logger.info("Defender - Getting pricings...")
@@ -89,6 +90,33 @@ class Defender(AzureService):
)
return assessments
def __get_security_contacts__(self):
logger.info("Defender - Getting security contacts...")
security_contacts = {}
for subscription_name, client in self.clients.items():
try:
# TODO: List all security contacts. For now, the list method is not working.
security_contact_default = client.security_contacts.get("default")
security_contacts.update({subscription_name: {}})
security_contacts[subscription_name].update(
{
security_contact_default.name: Defender_Security_Contacts(
resource_id=security_contact_default.id,
emails=security_contact_default.emails,
phone=security_contact_default.phone,
alert_notifications_minimal_severity=security_contact_default.alert_notifications.minimal_severity,
alert_notifications_state=security_contact_default.alert_notifications.state,
notified_roles=security_contact_default.notifications_by_role.roles,
notified_roles_state=security_contact_default.notifications_by_role.state,
)
}
)
except Exception as error:
logger.error(
f"Subscription name: {subscription_name} -- {error.__class__.__name__}[{error.__traceback__.tb_lineno}]: {error}"
)
return security_contacts
class Defender_Pricing(BaseModel):
resource_id: str
@@ -107,3 +135,13 @@ class Defender_Assessments(BaseModel):
resource_id: str
resource_name: str
status: str
class Defender_Security_Contacts(BaseModel):
resource_id: str
emails: str
phone: str
alert_notifications_minimal_severity: str
alert_notifications_state: str
notified_roles: list[str]
notified_roles_state: str

View File

@@ -0,0 +1,210 @@
from unittest import mock
from uuid import uuid4
from prowler.providers.azure.services.defender.defender_service import (
Defender_Security_Contacts,
)
from tests.providers.azure.azure_fixtures import AZURE_SUSCRIPTION
class Test_defender_additional_email_configured_with_a_security_contact:
def test_defender_no_notify_emails(self):
defender_client = mock.MagicMock
defender_client.security_contacts = {}
with mock.patch(
"prowler.providers.azure.services.defender.defender_additional_email_configured_with_a_security_contact.defender_additional_email_configured_with_a_security_contact.defender_client",
new=defender_client,
):
from prowler.providers.azure.services.defender.defender_additional_email_configured_with_a_security_contact.defender_additional_email_configured_with_a_security_contact import (
defender_additional_email_configured_with_a_security_contact,
)
check = defender_additional_email_configured_with_a_security_contact()
result = check.execute()
assert len(result) == 0
def test_defender_no_additional_emails(self):
resource_id = str(uuid4())
defender_client = mock.MagicMock
defender_client.security_contacts = {
AZURE_SUSCRIPTION: {
"default": Defender_Security_Contacts(
resource_id=resource_id,
emails="",
phone="",
alert_notifications_minimal_severity="High",
alert_notifications_state="On",
notified_roles=["Contributor"],
notified_roles_state="On",
)
}
}
with mock.patch(
"prowler.providers.azure.services.defender.defender_additional_email_configured_with_a_security_contact.defender_additional_email_configured_with_a_security_contact.defender_client",
new=defender_client,
):
from prowler.providers.azure.services.defender.defender_additional_email_configured_with_a_security_contact.defender_additional_email_configured_with_a_security_contact import (
defender_additional_email_configured_with_a_security_contact,
)
check = defender_additional_email_configured_with_a_security_contact()
result = check.execute()
assert len(result) == 1
assert result[0].status == "FAIL"
assert (
result[0].status_extended
== f"There is not another correct email configured for susbscription {AZURE_SUSCRIPTION}."
)
assert result[0].subscription == AZURE_SUSCRIPTION
assert result[0].resource_name == "default"
assert result[0].resource_id == resource_id
def test_defender_additional_email_bad_format(self):
resource_id = str(uuid4())
defender_client = mock.MagicMock
defender_client.security_contacts = {
AZURE_SUSCRIPTION: {
"default": Defender_Security_Contacts(
resource_id=resource_id,
emails="bad_email",
phone="",
alert_notifications_minimal_severity="High",
alert_notifications_state="On",
notified_roles=["Contributor"],
notified_roles_state="On",
)
}
}
with mock.patch(
"prowler.providers.azure.services.defender.defender_additional_email_configured_with_a_security_contact.defender_additional_email_configured_with_a_security_contact.defender_client",
new=defender_client,
):
from prowler.providers.azure.services.defender.defender_additional_email_configured_with_a_security_contact.defender_additional_email_configured_with_a_security_contact import (
defender_additional_email_configured_with_a_security_contact,
)
check = defender_additional_email_configured_with_a_security_contact()
result = check.execute()
assert len(result) == 1
assert result[0].status == "FAIL"
assert (
result[0].status_extended
== f"There is not another correct email configured for susbscription {AZURE_SUSCRIPTION}."
)
assert result[0].subscription == AZURE_SUSCRIPTION
assert result[0].resource_name == "default"
assert result[0].resource_id == resource_id
def test_defender_additional_email_bad_separator(self):
resource_id = str(uuid4())
defender_client = mock.MagicMock
defender_client.security_contacts = {
AZURE_SUSCRIPTION: {
"default": Defender_Security_Contacts(
resource_id=resource_id,
emails="test@test.es, test@test.email.com",
phone="",
alert_notifications_minimal_severity="High",
alert_notifications_state="On",
notified_roles=["Contributor"],
notified_roles_state="On",
)
}
}
with mock.patch(
"prowler.providers.azure.services.defender.defender_additional_email_configured_with_a_security_contact.defender_additional_email_configured_with_a_security_contact.defender_client",
new=defender_client,
):
from prowler.providers.azure.services.defender.defender_additional_email_configured_with_a_security_contact.defender_additional_email_configured_with_a_security_contact import (
defender_additional_email_configured_with_a_security_contact,
)
check = defender_additional_email_configured_with_a_security_contact()
result = check.execute()
assert len(result) == 1
assert result[0].status == "FAIL"
assert (
result[0].status_extended
== f"There is not another correct email configured for susbscription {AZURE_SUSCRIPTION}."
)
assert result[0].subscription == AZURE_SUSCRIPTION
assert result[0].resource_name == "default"
assert result[0].resource_id == resource_id
def test_defender_additional_email_good_format(self):
resource_id = str(uuid4())
defender_client = mock.MagicMock
defender_client.security_contacts = {
AZURE_SUSCRIPTION: {
"default": Defender_Security_Contacts(
resource_id=resource_id,
emails="test@test.com",
phone="",
alert_notifications_minimal_severity="High",
alert_notifications_state="On",
notified_roles=["Contributor"],
notified_roles_state="On",
)
}
}
with mock.patch(
"prowler.providers.azure.services.defender.defender_additional_email_configured_with_a_security_contact.defender_additional_email_configured_with_a_security_contact.defender_client",
new=defender_client,
):
from prowler.providers.azure.services.defender.defender_additional_email_configured_with_a_security_contact.defender_additional_email_configured_with_a_security_contact import (
defender_additional_email_configured_with_a_security_contact,
)
check = defender_additional_email_configured_with_a_security_contact()
result = check.execute()
assert len(result) == 1
assert result[0].status == "PASS"
assert (
result[0].status_extended
== f"There is another correct email configured for susbscription {AZURE_SUSCRIPTION}."
)
assert result[0].subscription == AZURE_SUSCRIPTION
assert result[0].resource_name == "default"
assert result[0].resource_id == resource_id
def test_defender_additional_email_good_format_multiple_subdomains(self):
resource_id = str(uuid4())
defender_client = mock.MagicMock
defender_client.security_contacts = {
AZURE_SUSCRIPTION: {
"default": Defender_Security_Contacts(
resource_id=resource_id,
emails="test@test.mail.es; bad_mail",
phone="",
alert_notifications_minimal_severity="High",
alert_notifications_state="On",
notified_roles=["Contributor"],
notified_roles_state="On",
)
}
}
with mock.patch(
"prowler.providers.azure.services.defender.defender_additional_email_configured_with_a_security_contact.defender_additional_email_configured_with_a_security_contact.defender_client",
new=defender_client,
):
from prowler.providers.azure.services.defender.defender_additional_email_configured_with_a_security_contact.defender_additional_email_configured_with_a_security_contact import (
defender_additional_email_configured_with_a_security_contact,
)
check = defender_additional_email_configured_with_a_security_contact()
result = check.execute()
assert len(result) == 1
assert result[0].status == "PASS"
assert (
result[0].status_extended
== f"There is another correct email configured for susbscription {AZURE_SUSCRIPTION}."
)
assert result[0].subscription == AZURE_SUSCRIPTION
assert result[0].resource_name == "default"
assert result[0].resource_id == resource_id

View File

@@ -0,0 +1,99 @@
from unittest import mock
from uuid import uuid4
from prowler.providers.azure.services.defender.defender_service import (
Defender_Security_Contacts,
)
from tests.providers.azure.azure_fixtures import AZURE_SUSCRIPTION
class Test_defender_ensure_notify_alerts_severity_is_high:
def test_defender_no_severity_alerts(self):
defender_client = mock.MagicMock
defender_client.security_contacts = {}
with mock.patch(
"prowler.providers.azure.services.defender.defender_ensure_notify_alerts_severity_is_high.defender_ensure_notify_alerts_severity_is_high.defender_client",
new=defender_client,
):
from prowler.providers.azure.services.defender.defender_ensure_notify_alerts_severity_is_high.defender_ensure_notify_alerts_severity_is_high import (
defender_ensure_notify_alerts_severity_is_high,
)
check = defender_ensure_notify_alerts_severity_is_high()
result = check.execute()
assert len(result) == 0
def test_defender_severity_alerts_low(self):
resource_id = str(uuid4())
defender_client = mock.MagicMock
defender_client.security_contacts = {
AZURE_SUSCRIPTION: {
"default": Defender_Security_Contacts(
resource_id=resource_id,
emails="",
phone="",
alert_notifications_minimal_severity="Low",
alert_notifications_state="On",
notified_roles=["Contributor"],
notified_roles_state="On",
)
}
}
with mock.patch(
"prowler.providers.azure.services.defender.defender_ensure_notify_alerts_severity_is_high.defender_ensure_notify_alerts_severity_is_high.defender_client",
new=defender_client,
):
from prowler.providers.azure.services.defender.defender_ensure_notify_alerts_severity_is_high.defender_ensure_notify_alerts_severity_is_high import (
defender_ensure_notify_alerts_severity_is_high,
)
check = defender_ensure_notify_alerts_severity_is_high()
result = check.execute()
assert len(result) == 1
assert result[0].status == "FAIL"
assert (
result[0].status_extended
== f"Notifiy alerts are not enabled for severity high in susbscription {AZURE_SUSCRIPTION}."
)
assert result[0].subscription == AZURE_SUSCRIPTION
assert result[0].resource_name == "default"
assert result[0].resource_id == resource_id
def test_defender_severity_alerts_high(self):
resource_id = str(uuid4())
defender_client = mock.MagicMock
defender_client.security_contacts = {
AZURE_SUSCRIPTION: {
"default": Defender_Security_Contacts(
resource_id=resource_id,
emails="",
phone="",
alert_notifications_minimal_severity="High",
alert_notifications_state="On",
notified_roles=["Contributor"],
notified_roles_state="On",
)
}
}
with mock.patch(
"prowler.providers.azure.services.defender.defender_ensure_notify_alerts_severity_is_high.defender_ensure_notify_alerts_severity_is_high.defender_client",
new=defender_client,
):
from prowler.providers.azure.services.defender.defender_ensure_notify_alerts_severity_is_high.defender_ensure_notify_alerts_severity_is_high import (
defender_ensure_notify_alerts_severity_is_high,
)
check = defender_ensure_notify_alerts_severity_is_high()
result = check.execute()
assert len(result) == 1
assert result[0].status == "PASS"
assert (
result[0].status_extended
== f"Notifiy alerts are enabled for severity high in susbscription {AZURE_SUSCRIPTION}."
)
assert result[0].subscription == AZURE_SUSCRIPTION
assert result[0].resource_name == "default"
assert result[0].resource_id == resource_id

View File

@@ -0,0 +1,136 @@
from unittest import mock
from uuid import uuid4
from prowler.providers.azure.services.defender.defender_service import (
Defender_Security_Contacts,
)
from tests.providers.azure.azure_fixtures import AZURE_SUSCRIPTION
class Test_defender_ensure_notify_emails_to_owners:
def test_defender_no_notify_emails(self):
defender_client = mock.MagicMock
defender_client.security_contacts = {}
with mock.patch(
"prowler.providers.azure.services.defender.defender_ensure_notify_emails_to_owners.defender_ensure_notify_emails_to_owners.defender_client",
new=defender_client,
):
from prowler.providers.azure.services.defender.defender_ensure_notify_emails_to_owners.defender_ensure_notify_emails_to_owners import (
defender_ensure_notify_emails_to_owners,
)
check = defender_ensure_notify_emails_to_owners()
result = check.execute()
assert len(result) == 0
def test_defender_no_notify_emails_to_owners(self):
resource_id = str(uuid4())
defender_client = mock.MagicMock
defender_client.security_contacts = {
AZURE_SUSCRIPTION: {
"default": Defender_Security_Contacts(
resource_id=resource_id,
emails="",
phone="",
alert_notifications_minimal_severity="High",
alert_notifications_state="On",
notified_roles=["Contributor"],
notified_roles_state="On",
)
}
}
with mock.patch(
"prowler.providers.azure.services.defender.defender_ensure_notify_emails_to_owners.defender_ensure_notify_emails_to_owners.defender_client",
new=defender_client,
):
from prowler.providers.azure.services.defender.defender_ensure_notify_emails_to_owners.defender_ensure_notify_emails_to_owners import (
defender_ensure_notify_emails_to_owners,
)
check = defender_ensure_notify_emails_to_owners()
result = check.execute()
assert len(result) == 1
assert result[0].status == "FAIL"
assert (
result[0].status_extended
== f"The Owner role is not notified for subscription {AZURE_SUSCRIPTION}."
)
assert result[0].subscription == AZURE_SUSCRIPTION
assert result[0].resource_name == "default"
assert result[0].resource_id == resource_id
def test_defender_notify_emails_to_owners_off(self):
resource_id = str(uuid4())
defender_client = mock.MagicMock
defender_client.security_contacts = {
AZURE_SUSCRIPTION: {
"default": Defender_Security_Contacts(
resource_id=resource_id,
emails="",
phone="",
alert_notifications_minimal_severity="High",
alert_notifications_state="On",
notified_roles=["Owner", "Contributor"],
notified_roles_state="Off",
)
}
}
with mock.patch(
"prowler.providers.azure.services.defender.defender_ensure_notify_emails_to_owners.defender_ensure_notify_emails_to_owners.defender_client",
new=defender_client,
):
from prowler.providers.azure.services.defender.defender_ensure_notify_emails_to_owners.defender_ensure_notify_emails_to_owners import (
defender_ensure_notify_emails_to_owners,
)
check = defender_ensure_notify_emails_to_owners()
result = check.execute()
assert len(result) == 1
assert result[0].status == "FAIL"
assert (
result[0].status_extended
== f"The Owner role is not notified for subscription {AZURE_SUSCRIPTION}."
)
assert result[0].subscription == AZURE_SUSCRIPTION
assert result[0].resource_name == "default"
assert result[0].resource_id == resource_id
def test_defender_notify_emails_to_owners(self):
resource_id = str(uuid4())
defender_client = mock.MagicMock
defender_client.security_contacts = {
AZURE_SUSCRIPTION: {
"default": Defender_Security_Contacts(
resource_id=resource_id,
emails="test@test.es",
phone="",
alert_notifications_minimal_severity="High",
alert_notifications_state="On",
notified_roles=["Owner", "Contributor"],
notified_roles_state="On",
)
}
}
with mock.patch(
"prowler.providers.azure.services.defender.defender_ensure_notify_emails_to_owners.defender_ensure_notify_emails_to_owners.defender_client",
new=defender_client,
):
from prowler.providers.azure.services.defender.defender_ensure_notify_emails_to_owners.defender_ensure_notify_emails_to_owners import (
defender_ensure_notify_emails_to_owners,
)
check = defender_ensure_notify_emails_to_owners()
result = check.execute()
assert len(result) == 1
assert result[0].status == "PASS"
assert (
result[0].status_extended
== f"The Owner role is notified for subscription {AZURE_SUSCRIPTION}."
)
assert result[0].subscription == AZURE_SUSCRIPTION
assert result[0].resource_name == "default"
assert result[0].resource_id == resource_id

View File

@@ -6,6 +6,7 @@ from prowler.providers.azure.services.defender.defender_service import (
Defender,
Defender_Assessments,
Defender_Pricing,
Defender_Security_Contacts,
)
from tests.providers.azure.azure_fixtures import (
AZURE_SUSCRIPTION,
@@ -50,6 +51,22 @@ def mock_defender_get_assessments(_):
}
def mock_defender_get_security_contacts(_):
return {
AZURE_SUSCRIPTION: {
"default": Defender_Security_Contacts(
resource_id="/subscriptions/resource_id",
emails="user@user.com, test@test.es",
phone="666666666",
alert_notifications_minimal_severity="High",
alert_notifications_state="On",
notified_roles=["Owner", "Contributor"],
notified_roles_state="On",
)
}
}
@patch(
"prowler.providers.azure.services.defender.defender_service.Defender.__get_pricings__",
new=mock_defender_get_pricings,
@@ -62,6 +79,10 @@ def mock_defender_get_assessments(_):
"prowler.providers.azure.services.defender.defender_service.Defender.__get_assessments__",
new=mock_defender_get_assessments,
)
@patch(
"prowler.providers.azure.services.defender.defender_service.Defender.__get_security_contacts__",
new=mock_defender_get_security_contacts,
)
class Test_Defender_Service:
def test__get_client__(self):
defender = Defender(set_mocked_azure_audit_info())
@@ -129,3 +150,40 @@ class Test_Defender_Service:
== "default"
)
assert defender.assessments[AZURE_SUSCRIPTION]["default"].status == "Healthy"
def test__get_security_contacts__(self):
defender = Defender(set_mocked_azure_audit_info())
assert len(defender.security_contacts) == 1
assert (
defender.security_contacts[AZURE_SUSCRIPTION]["default"].resource_id
== "/subscriptions/resource_id"
)
assert (
defender.security_contacts[AZURE_SUSCRIPTION]["default"].emails
== "user@user.com, test@test.es"
)
assert (
defender.security_contacts[AZURE_SUSCRIPTION]["default"].phone
== "666666666"
)
assert (
defender.security_contacts[AZURE_SUSCRIPTION][
"default"
].alert_notifications_minimal_severity
== "High"
)
assert (
defender.security_contacts[AZURE_SUSCRIPTION][
"default"
].alert_notifications_state
== "On"
)
assert defender.security_contacts[AZURE_SUSCRIPTION][
"default"
].notified_roles == ["Owner", "Contributor"]
assert (
defender.security_contacts[AZURE_SUSCRIPTION][
"default"
].notified_roles_state
== "On"
)