diff --git a/prowler/providers/m365/exceptions/exceptions.py b/prowler/providers/m365/exceptions/exceptions.py index 2b5840dd10..7d599386f9 100644 --- a/prowler/providers/m365/exceptions/exceptions.py +++ b/prowler/providers/m365/exceptions/exceptions.py @@ -98,21 +98,21 @@ class M365BaseException(ProwlerException): "message": "User and Password environment variables are needed to use Credentials authentication method.", "remediation": "Ensure your environment variables are properly set up.", }, - (6023, "M365EnvironmentUserCredentialsError"): { - "message": "User or Password environment variables are not correct.", - "remediation": "Ensure you are using the right credentials.", + (6023, "M365UserCredentialsError"): { + "message": "The provided User credentials are not valid.", + "remediation": "Check the User credentials and ensure they are valid.", }, (6024, "M365NotValidUserError"): { - "message": "The provided M365 User is not valid.", - "remediation": "Check the M365 User and ensure it is a valid user.", + "message": "The provided User is not valid.", + "remediation": "Check the User and ensure it is a valid user.", }, (6025, "M365NotValidEncryptedPasswordError"): { - "message": "The provided M365 Encrypted Password is not valid.", - "remediation": "Check the M365 Encrypted Password and ensure it is a valid password.", + "message": "The provided Encrypted Password is not valid.", + "remediation": "Check the Encrypted Password and ensure it is a valid password.", }, (6026, "M365UserNotBelongingToTenantError"): { - "message": "The provided M365 User does not belong to the specified tenant.", - "remediation": "Check the M365 User email domain and ensure it belongs to the specified tenant.", + "message": "The provided User does not belong to the specified tenant.", + "remediation": "Check the User email domain and ensure it belongs to the specified tenant.", }, } @@ -298,7 +298,7 @@ class M365MissingEnvironmentCredentialsError(M365CredentialsError): ) -class M365EnvironmentUserCredentialsError(M365CredentialsError): +class M365UserCredentialsError(M365CredentialsError): def __init__(self, file=None, original_exception=None, message=None): super().__init__( 6023, file=file, original_exception=original_exception, message=message diff --git a/prowler/providers/m365/m365_provider.py b/prowler/providers/m365/m365_provider.py index a8e4ce4ec2..f5011c9c27 100644 --- a/prowler/providers/m365/m365_provider.py +++ b/prowler/providers/m365/m365_provider.py @@ -33,7 +33,6 @@ from prowler.providers.m365.exceptions.exceptions import ( M365ConfigCredentialsError, M365CredentialsUnavailableError, M365DefaultAzureCredentialError, - M365EnvironmentUserCredentialsError, M365EnvironmentVariableError, M365GetTokenIdentityError, M365HTTPResponseError, @@ -51,6 +50,7 @@ from prowler.providers.m365.exceptions.exceptions import ( M365SetUpSessionError, M365TenantIdAndClientIdNotBelongingToClientSecretError, M365TenantIdAndClientSecretNotBelongingToClientIdError, + M365UserCredentialsError, ) from prowler.providers.m365.lib.mutelist.mutelist import M365Mutelist from prowler.providers.m365.lib.powershell.m365_powershell import ( @@ -434,9 +434,9 @@ class M365Provider(Provider): if init_modules: initialize_m365_powershell_modules() return credentials - raise M365EnvironmentUserCredentialsError( + raise M365UserCredentialsError( file=os.path.basename(__file__), - message="M365_USER or M365_ENCRYPTED_PASSWORD environment variables are not correct. Please ensure you are using the right credentials.", + message="The provided User credentials are not valid.", ) finally: test_session.close() @@ -994,7 +994,7 @@ class M365Provider(Provider): except ValueError: raise M365NotValidTenantIdError( file=os.path.basename(__file__), - message="The provided M365 Tenant ID is not valid.", + message="The provided Tenant ID is not valid.", ) # Validate the Client ID @@ -1003,28 +1003,28 @@ class M365Provider(Provider): except ValueError: raise M365NotValidClientIdError( file=os.path.basename(__file__), - message="The provided M365 Client ID is not valid.", + message="The provided Client ID is not valid.", ) # Validate the Client Secret if not client_secret: raise M365NotValidClientSecretError( file=os.path.basename(__file__), - message="The provided M365 Client Secret is not valid.", + message="The provided Client Secret is not valid.", ) # Validate the User if not user: raise M365NotValidUserError( file=os.path.basename(__file__), - message="The provided M365 User is not valid.", + message="The provided User is not valid.", ) # Validate the Encrypted Password if not encrypted_password: raise M365NotValidEncryptedPasswordError( file=os.path.basename(__file__), - message="The provided M365 Encrypted Password is not valid.", + message="The provided Encrypted Password is not valid.", ) try: @@ -1042,7 +1042,7 @@ class M365Provider(Provider): ) raise M365ClientIdAndClientSecretNotBelongingToTenantIdError( file=os.path.basename(__file__), - message="The provided M365 Client ID and Client Secret do not belong to the specified Tenant ID.", + message="The provided Client ID and Client Secret do not belong to the specified Tenant ID.", ) except M365NotValidClientIdError as client_id_error: logger.error( @@ -1050,7 +1050,7 @@ class M365Provider(Provider): ) raise M365TenantIdAndClientSecretNotBelongingToClientIdError( file=os.path.basename(__file__), - message="The provided M365 Tenant ID and Client Secret do not belong to the specified Client ID.", + message="The provided Tenant ID and Client Secret do not belong to the specified Client ID.", ) except M365NotValidClientSecretError as client_secret_error: logger.error( @@ -1058,7 +1058,7 @@ class M365Provider(Provider): ) raise M365TenantIdAndClientIdNotBelongingToClientSecretError( file=os.path.basename(__file__), - message="The provided M365 Tenant ID and Client ID do not belong to the specified Client Secret.", + message="The provided Tenant ID and Client ID do not belong to the specified Client Secret.", ) @staticmethod @@ -1100,19 +1100,25 @@ class M365Provider(Provider): if f"Tenant '{tenant_id}'" in error_description: raise M365NotValidTenantIdError( file=os.path.basename(__file__), - message="The provided Microsoft 365 Tenant ID is not valid for the specified Client ID and Client Secret.", + message="The provided Tenant ID is not valid for the specified Client ID and Client Secret.", ) if f"Application with identifier '{client_id}'" in error_description: raise M365NotValidClientIdError( file=os.path.basename(__file__), - message="The provided Microsoft 365 Client ID is not valid for the specified Tenant ID and Client Secret.", + message="The provided Client ID is not valid for the specified Tenant ID and Client Secret.", ) if "Invalid client secret provided" in error_description: raise M365NotValidClientSecretError( file=os.path.basename(__file__), - message="The provided Microsoft 365 Client Secret is not valid for the specified Tenant ID and Client ID.", + message="The provided Client Secret is not valid for the specified Tenant ID and Client ID.", ) - - except Exception as e: - # Generic exception handling (if needed) - raise RuntimeError(f"An unexpected error occurred: {str(e)}") + except ( + M365NotValidTenantIdError, + M365NotValidClientIdError, + M365NotValidClientSecretError, + ) as m365_error: + # M365 specific errors already raised + raise RuntimeError(f"{m365_error}") + except Exception as error: + # Generic exception handling for unexpected errors + raise RuntimeError(f"An unexpected error occurred: {str(error)}") diff --git a/tests/providers/m365/m365_provider_test.py b/tests/providers/m365/m365_provider_test.py index c891ab2d45..1d8c0759e6 100644 --- a/tests/providers/m365/m365_provider_test.py +++ b/tests/providers/m365/m365_provider_test.py @@ -522,7 +522,7 @@ class TestM365Provider: user="test@example.com", encrypted_password="test_password", ) - assert "The provided M365 Tenant ID is not valid." in str(exception.value) + assert "The provided Tenant ID is not valid." in str(exception.value) def test_validate_static_credentials_missing_client_id(self): with pytest.raises(M365NotValidClientIdError) as exception: @@ -533,7 +533,7 @@ class TestM365Provider: user="test@example.com", encrypted_password="test_password", ) - assert "The provided M365 Client ID is not valid." in str(exception.value) + assert "The provided Client ID is not valid." in str(exception.value) def test_validate_static_credentials_missing_client_secret(self): with pytest.raises(M365NotValidClientSecretError) as exception: @@ -544,7 +544,7 @@ class TestM365Provider: user="test@example.com", encrypted_password="test_password", ) - assert "The provided M365 Client Secret is not valid." in str(exception.value) + assert "The provided Client Secret is not valid." in str(exception.value) def test_validate_static_credentials_missing_user(self): with pytest.raises(M365NotValidUserError) as exception: @@ -555,7 +555,7 @@ class TestM365Provider: user="", encrypted_password="test_password", ) - assert "The provided M365 User is not valid." in str(exception.value) + assert "The provided User is not valid." in str(exception.value) def test_validate_static_credentials_missing_encrypted_password(self): with pytest.raises(M365NotValidEncryptedPasswordError) as exception: @@ -566,9 +566,7 @@ class TestM365Provider: user="test@example.com", encrypted_password="", ) - assert "The provided M365 Encrypted Password is not valid." in str( - exception.value - ) + assert "The provided Encrypted Password is not valid." in str(exception.value) def test_validate_arguments_missing_env_credentials(self): with pytest.raises(M365MissingEnvironmentCredentialsError) as exception: @@ -583,6 +581,7 @@ class TestM365Provider: user=None, encrypted_password=None, ) + assert ( "M365 provider requires AZURE_CLIENT_ID, AZURE_CLIENT_SECRET, AZURE_TENANT_ID, M365_USER and M365_ENCRYPTED_PASSWORD environment variables to be set when using --env-auth" in str(exception.value)