Skip to content

Commit f637e42

Browse files
authored
Merge pull request #16 from GabrielSalla/use-pydantic-dataclass-validation
Use pydantic for dataclass validation
2 parents 9d233d6 + 86acb0c commit f637e42

File tree

16 files changed

+254
-115
lines changed

16 files changed

+254
-115
lines changed

Dockerfile

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -8,13 +8,15 @@ WORKDIR /app
88
RUN apk add curl \
99
&& python3 -m venv $VIRTUAL_ENV \
1010
&& pip install --upgrade pip \
11-
&& pip3 install poetry
11+
&& pip install poetry --no-cache-dir
1212

1313
COPY . /app/
1414

15-
RUN poetry install --no-root --only main
15+
RUN poetry install --no-root --only main \
16+
&& poetry cache clear --no-interaction --all .
1617

1718

1819
FROM sentinela AS sentinela_dev
1920

20-
RUN poetry install --no-root
21+
RUN poetry install --no-root \
22+
&& poetry cache clear --no-interaction --all .

poetry.lock

Lines changed: 144 additions & 12 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

pyproject.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,8 +17,8 @@ alembic = "^1.14.0"
1717
asyncpg = "^0.30.0"
1818
certifi = "*"
1919
croniter = "^5.0.1"
20-
dataclass-type-validator = "^0.1.2"
2120
prometheus-client = "^0.21.1"
21+
pydantic = "^2.10.4"
2222
python = "^3.12"
2323
pytz = "*"
2424
pyyaml = "^6.0.2"

src/components/http_server/monitor_routes.py

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
import logging
22
import traceback
33

4+
import pydantic
45
from aiohttp import web
5-
from dataclass_type_validator import TypeValidationError
66

77
import external_requests as external_requests
88
from components.monitors_loader import MonitorValidationError
@@ -68,6 +68,8 @@ async def monitor_register(request):
6868
monitor_code = request_data.get("monitor_code")
6969
additional_files = request_data.get("additional_files", {})
7070

71+
error_response: dict[str, str | list]
72+
7173
if monitor_code is None:
7274
error_response = {
7375
"status": "error",
@@ -82,11 +84,18 @@ async def monitor_register(request):
8284
monitor = await external_requests.monitor_register(
8385
monitor_name, monitor_code, additional_files
8486
)
85-
except TypeValidationError as e:
87+
except pydantic.ValidationError as e:
8688
error_response = {
8789
"status": "error",
8890
"message": "Type validation error",
89-
"error": e.errors,
91+
"error": [
92+
{
93+
"loc": list(error["loc"]),
94+
"type": error["type"],
95+
"msg": error["msg"],
96+
}
97+
for error in e.errors()
98+
],
9099
}
91100
return web.json_response(error_response, status=400)
92101
except MonitorValidationError as e:

src/components/monitors_loader/monitors_loader.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,12 @@
11
import asyncio
22
import logging
33
import shutil
4-
from dataclasses import dataclass
54
from datetime import datetime
65
from pathlib import Path
76
from typing import Generator, cast
87

8+
from pydantic.dataclasses import dataclass
9+
910
import module_loader as module_loader
1011
import registry as registry
1112
import utils.app as app

src/configs/configs.py

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,10 @@
11
import os
2-
from dataclasses import dataclass
32
from typing import Any
43

54
import yaml
6-
from dataclass_type_validator import dataclass_validate
5+
from pydantic.dataclasses import dataclass
76

87

9-
@dataclass_validate(strict=True)
108
@dataclass
119
class Configs:
1210
load_sample_monitors: bool

src/module_loader/checker.py

Lines changed: 0 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -140,14 +140,6 @@ def _check_reaction_functions(reaction_options: ReactionOptions) -> list[str]:
140140
errors: list[str] = []
141141

142142
for field in ReactionOptions.__dataclass_fields__:
143-
if not isinstance(reaction_options[field], list):
144-
errors.append(
145-
ERROR_FIELD_WRONG_TYPE.format(
146-
display_name=f"reaction_options.{field}", expected_type="list[Coroutine]"
147-
)
148-
)
149-
continue
150-
151143
# Check each item in the reactions list
152144
for item in reaction_options[field]:
153145
try:

src/options/options.py

Lines changed: 2 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,11 @@
1-
from dataclasses import dataclass, field
1+
from dataclasses import field
22
from typing import Any, Callable, Coroutine
33

4-
from dataclass_type_validator import dataclass_validate
4+
from pydantic.dataclasses import dataclass
55

66
from configs import configs
77

88

9-
@dataclass_validate(strict=True)
109
@dataclass
1110
class MonitorOptions:
1211
"""
@@ -24,7 +23,6 @@ class MonitorOptions:
2423
execution_timeout: int = configs.executor_monitor_timeout
2524

2625

27-
@dataclass_validate(strict=True)
2826
@dataclass
2927
class IssueOptions:
3028
"""
@@ -42,7 +40,6 @@ class IssueOptions:
4240
unique: bool = False
4341

4442

45-
@dataclass_validate(strict=True)
4643
@dataclass
4744
class PriorityLevels:
4845
"""
@@ -64,7 +61,6 @@ def __getitem__(self, name: str):
6461
return getattr(self, name)
6562

6663

67-
@dataclass_validate(strict=True)
6864
@dataclass
6965
class AgeRule:
7066
"""
@@ -77,7 +73,6 @@ class AgeRule:
7773
priority_levels: PriorityLevels
7874

7975

80-
@dataclass_validate(strict=True)
8176
@dataclass
8277
class CountRule:
8378
"""
@@ -91,7 +86,6 @@ class CountRule:
9186
priority_levels: PriorityLevels
9287

9388

94-
@dataclass_validate(strict=True)
9589
@dataclass
9690
class ValueRule:
9791
"""
@@ -110,7 +104,6 @@ class ValueRule:
110104
priority_levels: PriorityLevels
111105

112106

113-
@dataclass_validate(strict=True)
114107
@dataclass
115108
class AlertOptions:
116109
"""
@@ -128,7 +121,6 @@ class AlertOptions:
128121
reaction_function_type = Callable[[dict[str, Any]], Coroutine[Any, Any, Any]]
129122

130123

131-
@dataclass_validate(strict=True)
132124
@dataclass
133125
class ReactionOptions:
134126
"""

src/plugins/slack/notifications/slack_notification.py

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,10 @@
11
import json
22
import logging
33
import os
4-
from dataclasses import dataclass
54
from functools import partial
65
from typing import Any, Coroutine
76

8-
from dataclass_type_validator import dataclass_validate
7+
from pydantic.dataclasses import dataclass
98
from pytz import timezone
109
from tabulate import tabulate
1110

@@ -31,7 +30,6 @@
3130
}
3231

3332

34-
@dataclass_validate(strict=True)
3533
@dataclass(kw_only=True)
3634
class SlackNotification:
3735
"""

src/plugins/slack/slack.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import os
2-
from dataclasses import dataclass
32
from typing import Any, cast
43

4+
from pydantic.dataclasses import dataclass
55
from slack_sdk.errors import SlackApiError
66
from slack_sdk.web.async_client import AsyncSlackResponse, AsyncWebClient
77

0 commit comments

Comments
 (0)