mirror of
https://github.com/apache/superset.git
synced 2026-04-19 16:14:52 +00:00
refactor: use exception status for logging (#21971)
This commit is contained in:
committed by
GitHub
parent
c3f1873c43
commit
ce145c676c
@@ -18,7 +18,7 @@ import json
|
||||
from contextlib import contextmanager
|
||||
from datetime import datetime, timedelta, timezone
|
||||
from typing import List, Optional
|
||||
from unittest.mock import Mock, patch
|
||||
from unittest.mock import call, Mock, patch
|
||||
from uuid import uuid4
|
||||
|
||||
import pytest
|
||||
@@ -29,6 +29,7 @@ from freezegun import freeze_time
|
||||
from sqlalchemy.sql import func
|
||||
|
||||
from superset import db
|
||||
from superset.exceptions import SupersetException
|
||||
from superset.models.core import Database
|
||||
from superset.models.dashboard import Dashboard
|
||||
from superset.models.slice import Slice
|
||||
@@ -37,16 +38,22 @@ from superset.reports.commands.exceptions import (
|
||||
AlertQueryInvalidTypeError,
|
||||
AlertQueryMultipleColumnsError,
|
||||
AlertQueryMultipleRowsError,
|
||||
ReportScheduleClientErrorsException,
|
||||
ReportScheduleCsvFailedError,
|
||||
ReportScheduleCsvTimeout,
|
||||
ReportScheduleForbiddenError,
|
||||
ReportScheduleNotFoundError,
|
||||
ReportSchedulePreviousWorkingError,
|
||||
ReportScheduleScreenshotFailedError,
|
||||
ReportScheduleScreenshotTimeout,
|
||||
ReportScheduleSystemErrorsException,
|
||||
ReportScheduleUnexpectedError,
|
||||
ReportScheduleWorkingTimeoutError,
|
||||
)
|
||||
from superset.reports.commands.execute import AsyncExecuteReportScheduleCommand
|
||||
from superset.reports.commands.execute import (
|
||||
AsyncExecuteReportScheduleCommand,
|
||||
BaseReportState,
|
||||
)
|
||||
from superset.reports.commands.log_prune import AsyncPruneReportScheduleLogCommand
|
||||
from superset.reports.models import (
|
||||
ReportDataFormat,
|
||||
@@ -56,6 +63,10 @@ from superset.reports.models import (
|
||||
ReportScheduleValidatorType,
|
||||
ReportState,
|
||||
)
|
||||
from superset.reports.notifications.exceptions import (
|
||||
NotificationError,
|
||||
NotificationParamException,
|
||||
)
|
||||
from superset.reports.types import ReportScheduleExecutor
|
||||
from superset.utils.database import get_example_database
|
||||
from tests.integration_tests.fixtures.birth_names_dashboard import (
|
||||
@@ -115,7 +126,6 @@ def assert_log(state: str, error_message: Optional[str] = None):
|
||||
|
||||
if state == ReportState.ERROR:
|
||||
# On error we send an email
|
||||
print(logs)
|
||||
assert len(logs) == 3
|
||||
else:
|
||||
assert len(logs) == 2
|
||||
@@ -1392,7 +1402,7 @@ def test_email_dashboard_report_fails(
|
||||
screenshot_mock.return_value = SCREENSHOT_FILE
|
||||
email_mock.side_effect = SMTPException("Could not connect to SMTP XPTO")
|
||||
|
||||
with pytest.raises(ReportScheduleUnexpectedError):
|
||||
with pytest.raises(ReportScheduleSystemErrorsException):
|
||||
AsyncExecuteReportScheduleCommand(
|
||||
TEST_ID, create_report_email_dashboard.id, datetime.utcnow()
|
||||
).run()
|
||||
@@ -1886,3 +1896,66 @@ def test_prune_log_soft_time_out(bulk_delete_logs, create_report_email_dashboard
|
||||
with pytest.raises(SoftTimeLimitExceeded) as excinfo:
|
||||
AsyncPruneReportScheduleLogCommand().run()
|
||||
assert str(excinfo.value) == "SoftTimeLimitExceeded()"
|
||||
|
||||
|
||||
@patch("superset.reports.commands.execute.logger")
|
||||
@patch("superset.reports.commands.execute.create_notification")
|
||||
def test__send_with_client_errors(notification_mock, logger_mock):
|
||||
notification_content = "I am some content"
|
||||
recipients = ["test@foo.com"]
|
||||
notification_mock.return_value.send.side_effect = NotificationParamException()
|
||||
with pytest.raises(ReportScheduleClientErrorsException) as excinfo:
|
||||
BaseReportState._send(BaseReportState, notification_content, recipients)
|
||||
|
||||
assert excinfo.errisinstance(SupersetException)
|
||||
logger_mock.warning.assert_called_with(
|
||||
(
|
||||
"SupersetError(message='', error_type=<SupersetErrorType.REPORT_NOTIFICATION_ERROR: 'REPORT_NOTIFICATION_ERROR'>, level=<ErrorLevel.WARNING: 'warning'>, extra=None)"
|
||||
)
|
||||
)
|
||||
|
||||
|
||||
@patch("superset.reports.commands.execute.logger")
|
||||
@patch("superset.reports.commands.execute.create_notification")
|
||||
def test__send_with_multiple_errors(notification_mock, logger_mock):
|
||||
notification_content = "I am some content"
|
||||
recipients = ["test@foo.com", "test2@bar.com"]
|
||||
notification_mock.return_value.send.side_effect = [
|
||||
NotificationParamException(),
|
||||
NotificationError(),
|
||||
]
|
||||
# it raises the error with a 500 status if present
|
||||
with pytest.raises(ReportScheduleSystemErrorsException) as excinfo:
|
||||
BaseReportState._send(BaseReportState, notification_content, recipients)
|
||||
|
||||
assert excinfo.errisinstance(SupersetException)
|
||||
# it logs both errors as warnings
|
||||
logger_mock.warning.assert_has_calls(
|
||||
[
|
||||
call(
|
||||
"SupersetError(message='', error_type=<SupersetErrorType.REPORT_NOTIFICATION_ERROR: 'REPORT_NOTIFICATION_ERROR'>, level=<ErrorLevel.WARNING: 'warning'>, extra=None)"
|
||||
),
|
||||
call(
|
||||
"SupersetError(message='', error_type=<SupersetErrorType.REPORT_NOTIFICATION_ERROR: 'REPORT_NOTIFICATION_ERROR'>, level=<ErrorLevel.ERROR: 'error'>, extra=None)"
|
||||
),
|
||||
]
|
||||
)
|
||||
|
||||
|
||||
@patch("superset.reports.commands.execute.logger")
|
||||
@patch("superset.reports.commands.execute.create_notification")
|
||||
def test__send_with_server_errors(notification_mock, logger_mock):
|
||||
|
||||
notification_content = "I am some content"
|
||||
recipients = ["test@foo.com"]
|
||||
notification_mock.return_value.send.side_effect = NotificationError()
|
||||
with pytest.raises(ReportScheduleSystemErrorsException) as excinfo:
|
||||
BaseReportState._send(BaseReportState, notification_content, recipients)
|
||||
|
||||
assert excinfo.errisinstance(SupersetException)
|
||||
# it logs the error
|
||||
logger_mock.warning.assert_called_with(
|
||||
(
|
||||
"SupersetError(message='', error_type=<SupersetErrorType.REPORT_NOTIFICATION_ERROR: 'REPORT_NOTIFICATION_ERROR'>, level=<ErrorLevel.ERROR: 'error'>, extra=None)"
|
||||
)
|
||||
)
|
||||
|
||||
37
tests/unit_tests/utils/log_tests.py
Normal file
37
tests/unit_tests/utils/log_tests.py
Normal file
@@ -0,0 +1,37 @@
|
||||
# Licensed to the Apache Software Foundation (ASF) under one
|
||||
# or more contributor license agreements. See the NOTICE file
|
||||
# distributed with this work for additional information
|
||||
# regarding copyright ownership. The ASF licenses this file
|
||||
# to you under the Apache License, Version 2.0 (the
|
||||
# "License"); you may not use this file except in compliance
|
||||
# with the License. You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing,
|
||||
# software distributed under the License is distributed on an
|
||||
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
# KIND, either express or implied. See the License for the
|
||||
# specific language governing permissions and limitations
|
||||
# under the License.
|
||||
|
||||
|
||||
from superset.utils.log import get_logger_from_status
|
||||
|
||||
|
||||
def test_log_from_status_exception() -> None:
|
||||
(func, log_level) = get_logger_from_status(500)
|
||||
assert func.__name__ == "exception"
|
||||
assert log_level == "exception"
|
||||
|
||||
|
||||
def test_log_from_status_warning() -> None:
|
||||
(func, log_level) = get_logger_from_status(422)
|
||||
assert func.__name__ == "warning"
|
||||
assert log_level == "warning"
|
||||
|
||||
|
||||
def test_log_from_status_info() -> None:
|
||||
(func, log_level) = get_logger_from_status(300)
|
||||
assert func.__name__ == "info"
|
||||
assert log_level == "info"
|
||||
Reference in New Issue
Block a user