This is an automated email from the ASF dual-hosted git repository.
potiuk pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/airflow.git
The following commit(s) were added to refs/heads/main by this push:
new 83e83e272f Replace to broad exceptions into the Core (#38344)
83e83e272f is described below
commit 83e83e272fdd359e7b3fd7ef368681c10d825220
Author: Andrey Anshin <[email protected]>
AuthorDate: Thu Mar 21 12:53:43 2024 +0400
Replace to broad exceptions into the Core (#38344)
---
airflow/api_connexion/schemas/common_schema.py | 2 +-
airflow/configuration.py | 2 +-
airflow/hooks/package_index.py | 2 +-
airflow/jobs/base_job_runner.py | 3 ++-
airflow/models/taskinstance.py | 2 +-
airflow/providers_manager.py | 2 +-
airflow/utils/dates.py | 6 +++---
airflow/utils/email.py | 2 +-
airflow/utils/log/logging_mixin.py | 2 +-
airflow/utils/python_virtualenv.py | 2 +-
airflow/www/extensions/init_auth_manager.py | 2 +-
tests/always/test_providers_manager.py | 6 +++---
tests/api_connexion/schemas/test_common_schema.py | 2 +-
tests/hooks/test_package_index.py | 2 +-
tests/models/test_taskinstance.py | 22 +++++++++++++---------
tests/operators/test_python.py | 18 +++++++++---------
tests/utils/test_dates.py | 6 +++---
17 files changed, 44 insertions(+), 39 deletions(-)
diff --git a/airflow/api_connexion/schemas/common_schema.py
b/airflow/api_connexion/schemas/common_schema.py
index aaaf0812c6..e91c7b23d8 100644
--- a/airflow/api_connexion/schemas/common_schema.py
+++ b/airflow/api_connexion/schemas/common_schema.py
@@ -123,7 +123,7 @@ class ScheduleIntervalSchema(OneOfSchema):
elif isinstance(obj, CronExpression):
return "CronExpression"
else:
- raise Exception(f"Unknown object type: {obj.__class__.__name__}")
+ raise TypeError(f"Unknown object type: {obj.__class__.__name__}")
class ColorField(fields.String):
diff --git a/airflow/configuration.py b/airflow/configuration.py
index db94ee14ed..7c1cac1576 100644
--- a/airflow/configuration.py
+++ b/airflow/configuration.py
@@ -264,7 +264,7 @@ class AirflowConfigParser(ConfigParser):
)
self._default_values.set(section, key, value)
if errors:
- raise Exception(
+ raise AirflowConfigException(
f"The string config passed as default contains variables. "
f"This is not supported. String config: {config_string}"
)
diff --git a/airflow/hooks/package_index.py b/airflow/hooks/package_index.py
index e6d169d65e..8475a09369 100644
--- a/airflow/hooks/package_index.py
+++ b/airflow/hooks/package_index.py
@@ -73,7 +73,7 @@ class PackageIndexHook(BaseHook):
conn = self.get_connection(self.pi_conn_id)
index_url = conn.host
if not index_url:
- raise Exception("Please provide an index URL.")
+ raise ValueError("Please provide an index URL.")
return self._get_basic_auth_conn_url(index_url, conn.login,
conn.password)
def test_connection(self) -> tuple[bool, str]:
diff --git a/airflow/jobs/base_job_runner.py b/airflow/jobs/base_job_runner.py
index e26c100ea8..df6fcc67ab 100644
--- a/airflow/jobs/base_job_runner.py
+++ b/airflow/jobs/base_job_runner.py
@@ -19,6 +19,7 @@ from __future__ import annotations
from typing import TYPE_CHECKING
+from airflow.exceptions import AirflowException
from airflow.utils.session import NEW_SESSION, provide_session
if TYPE_CHECKING:
@@ -35,7 +36,7 @@ class BaseJobRunner:
def __init__(self, job: Job) -> None:
if job.job_type and job.job_type != self.job_type:
- raise Exception(
+ raise AirflowException(
f"The job is already assigned a different job_type:
{job.job_type}."
f"This is a bug and should be reported."
)
diff --git a/airflow/models/taskinstance.py b/airflow/models/taskinstance.py
index ad956e68b4..696ee98d6f 100644
--- a/airflow/models/taskinstance.py
+++ b/airflow/models/taskinstance.py
@@ -2518,7 +2518,7 @@ class TaskInstance(Base, LoggingMixin):
msg = f"Task failed due to SystemExit({e.code})"
self.handle_failure(msg, test_mode, context, session=session)
session.commit()
- raise Exception(msg)
+ raise AirflowException(msg)
except BaseException as e:
self.handle_failure(e, test_mode, context, session=session)
session.commit()
diff --git a/airflow/providers_manager.py b/airflow/providers_manager.py
index 9552a8a526..5263be4f5f 100644
--- a/airflow/providers_manager.py
+++ b/airflow/providers_manager.py
@@ -619,7 +619,7 @@ class ProvidersManager(LoggingMixin, metaclass=Singleton):
self._provider_schema_validator.validate(provider_info)
provider_info_package_name = provider_info["package-name"]
if package_name != provider_info_package_name:
- raise Exception(
+ raise ValueError(
f"The package '{package_name}' from setuptools and "
f"{provider_info_package_name} do not match. Please make
sure they are aligned"
)
diff --git a/airflow/utils/dates.py b/airflow/utils/dates.py
index b4eecdcb56..89bc29195a 100644
--- a/airflow/utils/dates.py
+++ b/airflow/utils/dates.py
@@ -79,9 +79,9 @@ def date_range(
return []
if end_date:
if start_date > end_date:
- raise Exception("Wait. start_date needs to be before end_date")
+ raise ValueError("Wait. start_date needs to be before end_date")
if num:
- raise Exception("Wait. Either specify end_date OR num")
+ raise ValueError("Wait. Either specify end_date OR num")
if not end_date and not num:
end_date = timezone.utcnow()
@@ -99,7 +99,7 @@ def date_range(
elif isinstance(delta, relativedelta):
abs_delta = abs(delta)
else:
- raise Exception("Wait. delta must be either datetime.timedelta or cron
expression as str")
+ raise TypeError("Wait. delta must be either datetime.timedelta or cron
expression as str")
dates = []
if end_date:
diff --git a/airflow/utils/email.py b/airflow/utils/email.py
index b4cd313359..aebc2a6e09 100644
--- a/airflow/utils/email.py
+++ b/airflow/utils/email.py
@@ -133,7 +133,7 @@ def send_email_smtp(
mail_from = smtp_mail_from
else:
if from_email is None:
- raise Exception(
+ raise ValueError(
"You should set from email - either by smtp/smtp_mail_from
config or `from_email` parameter"
)
mail_from = from_email
diff --git a/airflow/utils/log/logging_mixin.py
b/airflow/utils/log/logging_mixin.py
index 0f18b9da8d..0ea08af5f1 100644
--- a/airflow/utils/log/logging_mixin.py
+++ b/airflow/utils/log/logging_mixin.py
@@ -227,7 +227,7 @@ class RedirectStdHandler(StreamHandler):
def __init__(self, stream):
if not isinstance(stream, str):
- raise Exception(
+ raise TypeError(
"Cannot use file like objects. Use 'stdout' or 'stderr' as a
str and without 'ext://'."
)
diff --git a/airflow/utils/python_virtualenv.py
b/airflow/utils/python_virtualenv.py
index 4a03c2d18e..3fa0077a96 100644
--- a/airflow/utils/python_virtualenv.py
+++ b/airflow/utils/python_virtualenv.py
@@ -105,7 +105,7 @@ def prepare_virtualenv(
execute_in_subprocess(virtualenv_cmd)
if requirements is not None and requirements_file_path is not None:
- raise Exception("Either requirements OR requirements_file_path has to
be passed, but not both")
+ raise ValueError("Either requirements OR requirements_file_path has to
be passed, but not both")
pip_cmd = None
if requirements is not None and len(requirements) != 0:
diff --git a/airflow/www/extensions/init_auth_manager.py
b/airflow/www/extensions/init_auth_manager.py
index d29fb6944e..1c3d399647 100644
--- a/airflow/www/extensions/init_auth_manager.py
+++ b/airflow/www/extensions/init_auth_manager.py
@@ -60,7 +60,7 @@ def init_auth_manager(appbuilder: AirflowAppBuilder) ->
BaseAuthManager:
def get_auth_manager() -> BaseAuthManager:
"""Return the auth manager, provided it's been initialized before."""
if auth_manager is None:
- raise Exception(
+ raise RuntimeError(
"Auth Manager has not been initialized yet. "
"The `init_auth_manager` method needs to be called first."
)
diff --git a/tests/always/test_providers_manager.py
b/tests/always/test_providers_manager.py
index f6c508ed34..4294da4cfe 100644
--- a/tests/always/test_providers_manager.py
+++ b/tests/always/test_providers_manager.py
@@ -268,7 +268,7 @@ class TestProviderManager:
widgets["extra__test__my_param"] = widget_field
widgets["my_param"] = dummy_field
else:
- raise Exception("unexpected")
+ raise ValueError("unexpected")
provider_manager._add_widgets(
package_name="abc",
@@ -456,9 +456,9 @@ def test_lazy_cache_dict_resolving(value, expected_outputs):
def test_lazy_cache_dict_raises_error():
def raise_method():
- raise Exception("test")
+ raise RuntimeError("test")
lazy_cache_dict = LazyDictWithCache()
lazy_cache_dict["key"] = raise_method
- with pytest.raises(Exception, match="test"):
+ with pytest.raises(RuntimeError, match="test"):
_ = lazy_cache_dict["key"]
diff --git a/tests/api_connexion/schemas/test_common_schema.py
b/tests/api_connexion/schemas/test_common_schema.py
index 9259aad683..fc9ab3fff4 100644
--- a/tests/api_connexion/schemas/test_common_schema.py
+++ b/tests/api_connexion/schemas/test_common_schema.py
@@ -140,5 +140,5 @@ class TestScheduleIntervalSchema:
def test_should_error_unknown_obj_type(self):
instance = 342
schema_instance = ScheduleIntervalSchema()
- with pytest.raises(Exception, match="Unknown object type: int"):
+ with pytest.raises(TypeError, match="Unknown object type: int"):
schema_instance.dump(instance)
diff --git a/tests/hooks/test_package_index.py
b/tests/hooks/test_package_index.py
index 34a2182904..7d40bda32c 100644
--- a/tests/hooks/test_package_index.py
+++ b/tests/hooks/test_package_index.py
@@ -87,7 +87,7 @@ def test_get_connection_url(mock_get_connection: str | None):
connection_url = hook_instance.get_connection_url()
assert connection_url == expected_result
else:
- with pytest.raises(Exception):
+ with pytest.raises(ValueError, match="Please provide an index URL."):
hook_instance.get_connection_url()
diff --git a/tests/models/test_taskinstance.py
b/tests/models/test_taskinstance.py
index 457d311923..72284c5c69 100644
--- a/tests/models/test_taskinstance.py
+++ b/tests/models/test_taskinstance.py
@@ -3039,14 +3039,14 @@ class TestTaskInstance:
@pytest.mark.parametrize(
"code, expected_state",
[
- (1, State.FAILED),
- (-1, State.FAILED),
- ("error", State.FAILED),
- (0, State.SUCCESS),
- (None, State.SUCCESS),
+ pytest.param(1, State.FAILED, id="code-positive-number"),
+ pytest.param(-1, State.FAILED, id="code-negative-number"),
+ pytest.param("error", State.FAILED, id="code-text"),
+ pytest.param(0, State.SUCCESS, id="code-zero"),
+ pytest.param(None, State.SUCCESS, id="code-none"),
],
)
- def test_handle_system_exit(self, dag_maker, code, expected_state):
+ def test_handle_system_exit_failed(self, dag_maker, code, expected_state):
with dag_maker():
def f(*args, **kwargs):
@@ -3060,10 +3060,14 @@ class TestTaskInstance:
session = settings.Session()
session.merge(ti)
session.commit()
- try:
+
+ if expected_state == State.SUCCESS:
+ ctx = contextlib.nullcontext()
+ else:
+ ctx = pytest.raises(AirflowException, match=rf"Task failed due to
SystemExit\({code}\)")
+
+ with ctx:
ti._run_raw_task()
- except Exception:
- ...
ti.refresh_from_db()
assert ti.state == expected_state
diff --git a/tests/operators/test_python.py b/tests/operators/test_python.py
index 3e6f5a8b9a..036ea9e938 100644
--- a/tests/operators/test_python.py
+++ b/tests/operators/test_python.py
@@ -748,14 +748,14 @@ class BaseTestPythonVirtualenvOperator(BasePythonTest):
def test_fail(self):
def f():
- raise Exception
+ raise RuntimeError
with pytest.raises(CalledProcessError):
self.run_as_task(f)
def test_fail_with_message(self):
def f():
- raise Exception("Custom error message")
+ raise RuntimeError("Custom error message")
with pytest.raises(AirflowException, match="Custom error message"):
self.run_as_task(f)
@@ -765,7 +765,7 @@ class BaseTestPythonVirtualenvOperator(BasePythonTest):
global virtualenv_string_args
print(virtualenv_string_args)
if virtualenv_string_args[0] != virtualenv_string_args[2]:
- raise Exception
+ raise RuntimeError
self.run_as_task(f, string_args=[1, 2, 1])
@@ -774,7 +774,7 @@ class BaseTestPythonVirtualenvOperator(BasePythonTest):
if a == 0 and b == 1 and c and not d:
return True
else:
- raise Exception
+ raise RuntimeError
self.run_as_task(f, op_args=[0, 1], op_kwargs={"c": True})
@@ -940,7 +940,7 @@ class
TestPythonVirtualenvOperator(BaseTestPythonVirtualenvOperator):
import funcsigs # noqa: F401
except ImportError:
return True
- raise Exception
+ raise RuntimeError
self.run_as_task(f, system_site_packages=False, requirements=["dill"])
@@ -955,7 +955,7 @@ class
TestPythonVirtualenvOperator(BaseTestPythonVirtualenvOperator):
import funcsigs
if funcsigs.__version__ != "0.4":
- raise Exception
+ raise RuntimeError
self.run_as_task(f, requirements=["funcsigs==0.4"])
@@ -971,7 +971,7 @@ class
TestPythonVirtualenvOperator(BaseTestPythonVirtualenvOperator):
import funcsigs
if funcsigs.__version__ != "0.4":
- raise Exception
+ raise RuntimeError
self.run_as_task(f, requirements=["funcsigs==0.4"],
do_not_use_caching=True)
@@ -1038,7 +1038,7 @@ class
TestPythonVirtualenvOperator(BaseTestPythonVirtualenvOperator):
{}.iteritems()
except AttributeError:
return
- raise Exception
+ raise RuntimeError
self.run_as_task(f, python_version="3", use_dill=False,
requirements=["dill"])
@@ -1274,7 +1274,7 @@ class
BaseTestBranchPythonVirtualenvOperator(BaseTestPythonVirtualenvOperator):
if a == 0 and b == 1 and c and not d:
return True
else:
- raise Exception
+ raise RuntimeError
with pytest.raises(AirflowException, match="but got 'bool'"):
self.run_as_task(f, op_args=[0, 1], op_kwargs={"c": True})
diff --git a/tests/utils/test_dates.py b/tests/utils/test_dates.py
index 2b73bd3d13..689df2f9d6 100644
--- a/tests/utils/test_dates.py
+++ b/tests/utils/test_dates.py
@@ -109,16 +109,16 @@ class TestUtilsDatesDateRange:
assert dates.date_range(datetime(2016, 1, 1), datetime(2016, 1, 3)) ==
[]
def test_end_date_before_start_date(self):
- with pytest.raises(Exception, match="Wait. start_date needs to be
before end_date"):
+ with pytest.raises(ValueError, match="Wait. start_date needs to be
before end_date"):
dates.date_range(datetime(2016, 2, 1), datetime(2016, 1, 1),
delta=timedelta(seconds=1))
def test_both_end_date_and_num_given(self):
- with pytest.raises(Exception, match="Wait. Either specify end_date OR
num"):
+ with pytest.raises(ValueError, match="Wait. Either specify end_date OR
num"):
dates.date_range(datetime(2016, 1, 1), datetime(2016, 1, 3),
num=2, delta=timedelta(seconds=1))
def test_invalid_delta(self):
exception_msg = "Wait. delta must be either datetime.timedelta or cron
expression as str"
- with pytest.raises(Exception, match=exception_msg):
+ with pytest.raises(TypeError, match=exception_msg):
dates.date_range(datetime(2016, 1, 1), datetime(2016, 1, 3),
delta=1)
def test_positive_num_given(self):