Skip to content

Commit 59aed51

Browse files
committed
rest-api: convert remaining models to api_model
Change-Id: Ib846ed650d701f16857343ca0146a4df5e34aa49
1 parent 74c4b39 commit 59aed51

13 files changed

Lines changed: 64 additions & 73 deletions

File tree

cmk/gui/inventory/_openapi/_get_inventory_trees.py

Lines changed: 6 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -4,25 +4,24 @@
44
# conditions defined in the file COPYING, which is part of this source code package.
55

66
from collections.abc import Mapping, Sequence
7-
from dataclasses import dataclass
87
from typing import Annotated, Literal
98

109
from cmk.ccc.hostaddress import HostName
1110
from cmk.gui.openapi.framework import QueryParam
12-
from cmk.gui.openapi.framework.model import api_field
11+
from cmk.gui.openapi.framework.model import api_field, api_model
1312
from cmk.gui.openapi.framework.model.base_models import DomainObjectCollectionModel, LinkModel
1413
from cmk.gui.openapi.restful_objects.constructors import collection_href
1514
from cmk.utils.structured_data import ImmutableTree
1615

1716
from .._tree import inventory_of_host
1817

1918

20-
@dataclass(kw_only=True, slots=True)
19+
@api_model
2120
class Attributes:
2221
pairs: dict[str, int | float | str | bool | None] = api_field(description="Key-value pairs")
2322

2423

25-
@dataclass(kw_only=True, slots=True)
24+
@api_model
2625
class Table:
2726
key_columns: Sequence[str] = api_field(
2827
description="The key columns which are used to identify a row"
@@ -32,7 +31,7 @@ class Table:
3231
)
3332

3433

35-
@dataclass(kw_only=True, slots=True)
34+
@api_model
3635
class Tree:
3736
attributes: "Attributes" = api_field(description="A collection of key-value pairs")
3837
table: "Table" = api_field(description="A collection of rows")
@@ -55,7 +54,7 @@ def _transform_inventory_tree(tree: ImmutableTree) -> Tree:
5554
)
5655

5756

58-
@dataclass(kw_only=True, slots=True)
57+
@api_model
5958
class HostInventoryTree:
6059
host_name: str = api_field(
6160
description="The HW/SW Inventory tree of the host",
@@ -65,7 +64,7 @@ class HostInventoryTree:
6564
)
6665

6766

68-
@dataclass(kw_only=True, slots=True)
67+
@api_model
6968
class InventoryTreesCollectionModel(DomainObjectCollectionModel):
7069
domainType: Literal["inventory"] = api_field(
7170
description="The domain type of the objects in the collection",

cmk/gui/openapi/api_endpoints/host_config/create_host.py

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,6 @@
22
# Copyright (C) 2025 Checkmk GmbH - License: GNU General Public License v2
33
# This file is part of Checkmk (https://checkmk.com). It is subject to the terms and
44
# conditions defined in the file COPYING, which is part of this source code package.
5-
from dataclasses import dataclass
65
from typing import Annotated
76

87
from cmk.ccc.hostaddress import HostName
@@ -13,7 +12,7 @@
1312
from cmk.gui.openapi.api_endpoints.models.host_attribute_models import HostUpdateAttributeModel
1413
from cmk.gui.openapi.framework import EndpointBehavior, QueryParam
1514
from cmk.gui.openapi.framework.api_config import APIVersion
16-
from cmk.gui.openapi.framework.model import api_field
15+
from cmk.gui.openapi.framework.model import api_field, api_model
1716
from cmk.gui.openapi.framework.model.common_fields import AnnotatedFolder
1817
from cmk.gui.openapi.framework.model.converter import HostConverter, TypedPlainValidator
1918
from cmk.gui.openapi.framework.versioned_endpoint import (
@@ -30,7 +29,7 @@
3029
from cmk.gui.watolib.hosts_and_folders import Host
3130

3231

33-
@dataclass(kw_only=True, slots=True)
32+
@api_model
3433
class CreateHostModel:
3534
host_name: Annotated[HostName, TypedPlainValidator(str, HostConverter.not_exists)] = api_field(
3635
description="The hostname or IP address of the host to be created.",

cmk/gui/openapi/api_endpoints/host_config/list_hosts.py

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,6 @@
33
# This file is part of Checkmk (https://checkmk.com). It is subject to the terms and
44
# conditions defined in the file COPYING, which is part of this source code package.
55
from collections.abc import Iterable, Sequence
6-
from dataclasses import dataclass
76
from typing import Annotated, Literal
87

98
from cmk import trace
@@ -14,7 +13,7 @@
1413
from cmk.gui.openapi.api_endpoints.host_config.utils import serialize_host
1514
from cmk.gui.openapi.framework import QueryParam
1615
from cmk.gui.openapi.framework.api_config import APIVersion
17-
from cmk.gui.openapi.framework.model import api_field, ApiOmitted
16+
from cmk.gui.openapi.framework.model import api_field, api_model, ApiOmitted
1817
from cmk.gui.openapi.framework.model.base_models import DomainObjectCollectionModel, LinkModel
1918
from cmk.gui.openapi.framework.model.common_fields import FieldsFilterType
2019
from cmk.gui.openapi.framework.versioned_endpoint import (
@@ -32,7 +31,7 @@
3231
tracer = trace.get_tracer()
3332

3433

35-
@dataclass(kw_only=True, slots=True)
34+
@api_model
3635
class HostConfigCollectionModel(DomainObjectCollectionModel):
3736
domainType: Literal["host_config"] = api_field(
3837
description="The domain type of the objects in the collection",

cmk/gui/openapi/api_endpoints/host_config/models/response_models.py

Lines changed: 8 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -3,14 +3,13 @@
33
# This file is part of Checkmk (https://checkmk.com). It is subject to the terms and
44
# conditions defined in the file COPYING, which is part of this source code package.
55
from collections.abc import Sequence
6-
from dataclasses import dataclass
76
from typing import Annotated, Literal
87

98
from pydantic import AfterValidator
109

1110
from cmk.gui.openapi.api_endpoints.models.folder_attribute_models import FolderViewAttributeModel
1211
from cmk.gui.openapi.api_endpoints.models.host_attribute_models import HostViewAttributeModel
13-
from cmk.gui.openapi.framework.model import api_field, ApiOmitted
12+
from cmk.gui.openapi.framework.model import api_field, api_model, ApiOmitted
1413
from cmk.gui.openapi.framework.model.base_models import (
1514
DomainObjectCollectionModel,
1615
DomainObjectModel,
@@ -22,7 +21,7 @@
2221
from cmk.gui.openapi.framework.model.converter import HostConverter
2322

2423

25-
@dataclass(kw_only=True, slots=True)
24+
@api_model
2625
class HostExtensionsModel:
2726
folder: AnnotatedFolder = api_field(description="The folder, in which this host resides.")
2827
attributes: HostViewAttributeModel = api_field(description="Attributes of this host.")
@@ -41,7 +40,7 @@ class HostExtensionsModel:
4140
)
4241

4342

44-
@dataclass(kw_only=True, slots=True)
43+
@api_model
4544
class FolderMembersModel:
4645
hosts: ObjectCollectionMemberModel = api_field(
4746
description="A list of links pointing to the actual host-resources."
@@ -51,15 +50,15 @@ class FolderMembersModel:
5150
)
5251

5352

54-
@dataclass(kw_only=True, slots=True)
53+
@api_model
5554
class FolderExtensionsModel:
5655
path: str = api_field(description="The full path of this folder, slash delimited.")
5756
attributes: FolderViewAttributeModel = api_field(
5857
description="The folder's attributes. Hosts placed in this folder will inherit these attributes."
5958
)
6059

6160

62-
@dataclass(kw_only=True, slots=True)
61+
@api_model
6362
class FolderModel(LinkableModel):
6463
domainType: Literal["folder_config"] = api_field(
6564
description="The domain type of the object.",
@@ -72,7 +71,7 @@ class FolderModel(LinkableModel):
7271
extensions: FolderExtensionsModel = api_field(description="Data and Meta-Data of this object.")
7372

7473

75-
@dataclass(kw_only=True, slots=True)
74+
@api_model
7675
class HostMembersModel(DomainObjectModel):
7776
folder_config: FolderModel = api_field(
7877
description="The folder in which this host resides. It is represented by a hexadecimal "
@@ -81,7 +80,7 @@ class HostMembersModel(DomainObjectModel):
8180
)
8281

8382

84-
@dataclass(kw_only=True, slots=True)
83+
@api_model
8584
class HostConfigModel(DomainObjectModel):
8685
domainType: Literal["host_config"] = api_field(description="The domain type of the object.")
8786
members: HostMembersModel | None = api_field(
@@ -92,7 +91,7 @@ class HostConfigModel(DomainObjectModel):
9291
)
9392

9493

95-
@dataclass(kw_only=True, slots=True)
94+
@api_model
9695
class HostConfigCollectionModel(DomainObjectCollectionModel):
9796
domainType: Literal["host_config"] = api_field(
9897
description="The domain type of the objects in the collection",

cmk/gui/openapi/api_endpoints/models/attributes.py

Lines changed: 20 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@
2222
PrivacyProtocolType,
2323
)
2424
from cmk.gui.logged_in import user
25-
from cmk.gui.openapi.framework.model import api_field, ApiOmitted
25+
from cmk.gui.openapi.framework.model import api_field, api_model, ApiOmitted
2626
from cmk.gui.openapi.framework.model.common_fields import IPv4String, RegexString
2727
from cmk.gui.openapi.framework.model.converter import (
2828
GroupConverter,
@@ -43,7 +43,7 @@
4343
from cmk.utils.translations import TranslationOptionsSpec
4444

4545

46-
@dataclass(kw_only=True, slots=True)
46+
@api_model
4747
class HostContactGroupModel:
4848
groups: list[Annotated[str, AfterValidator(GroupConverter(group_type="host").exists)]] = (
4949
api_field(description="A list of contact groups.", example="all")
@@ -79,13 +79,13 @@ def to_internal(self) -> HostContactGroupSpec:
7979
}
8080

8181

82-
@dataclass(kw_only=True, slots=True)
82+
@api_model
8383
class SNMPCommunityModel:
8484
type: Literal["v1_v2_community"] = api_field(description="SNMP v1 or v2 with community")
8585
community: str = api_field(description="SNMP community (SNMP Versions 1 and 2c)")
8686

8787

88-
@dataclass(kw_only=True, slots=True)
88+
@api_model
8989
class SNMPv3NoAuthNoPrivacyModel:
9090
type: Literal["noAuthNoPriv"] = api_field(
9191
description="SNMPv3 without authentication or privacy"
@@ -103,7 +103,7 @@ def to_internal(self) -> tuple[Literal["noAuthNoPriv"], str]:
103103
return self.type, self.security_name
104104

105105

106-
@dataclass(kw_only=True, slots=True)
106+
@api_model
107107
class SNMPv3AuthNoPrivacyModel:
108108
type: Literal["authNoPriv"] = api_field(
109109
description="SNMPv3 with authentication, but without privacy"
@@ -132,7 +132,7 @@ def to_internal(self) -> tuple[Literal["authNoPriv"], str, str, str]:
132132
)
133133

134134

135-
@dataclass(kw_only=True, slots=True)
135+
@api_model
136136
class SNMPv3AuthPrivacyModel:
137137
type: Literal["authPriv"] = api_field(description="SNMPv3 with authentication and privacy")
138138
auth_protocol: AuthProtocolType = api_field(description="Authentication protocol.")
@@ -211,7 +211,7 @@ def to_internal(field: SNMPCredentialsModel) -> str | tuple:
211211
raise ValueError(f"Unknown SNMP credentials type: {field.type!r}")
212212

213213

214-
@dataclass(kw_only=True, slots=True)
214+
@api_model
215215
class IPAddressRangeModel:
216216
type: Literal["ip_range"] = api_field(description="Select a range of IP addresses")
217217
from_address: IPv4String = api_field(description="The first IPv4 address of this range.")
@@ -229,7 +229,7 @@ def to_internal(self) -> tuple[Literal["ip_range"], tuple[str, str]]:
229229
return self.type, (str(self.from_address), str(self.to_address))
230230

231231

232-
@dataclass(kw_only=True, slots=True)
232+
@api_model
233233
class IPNetworkModel:
234234
type: Literal["ip_network"] = api_field(description="Select an entire network")
235235
network: IPv4Network = api_field(
@@ -248,7 +248,7 @@ def to_internal(self) -> tuple[Literal["ip_network"], tuple[str, int]]:
248248
return self.type, (str(self.network.network_address), self.network.prefixlen)
249249

250250

251-
@dataclass(kw_only=True, slots=True)
251+
@api_model
252252
class IPAddressesModel:
253253
type: Literal["ip_list"] = api_field(description="Select multiple explicit IP addresses")
254254
addresses: list[IPv4String] = api_field(description="List of IPv4 addresses")
@@ -264,7 +264,7 @@ def to_internal(self) -> tuple[Literal["ip_list"], Sequence[HostAddress]]:
264264
return self.type, [HostAddress(x) for x in self.addresses]
265265

266266

267-
@dataclass(kw_only=True, slots=True)
267+
@api_model
268268
class IPRegexpModel:
269269
type: Literal["ip_regex_list"] = api_field(description="Deselect IP addresses with regexes")
270270
regexp_list: list[RegexString] = api_field(
@@ -306,7 +306,7 @@ def from_internal_exclude(value: ExcludeIPRange) -> IPRangeWithRegexpModel:
306306
return IPRangeConverter.from_internal(value)
307307

308308

309-
@dataclass(kw_only=True, slots=True)
309+
@api_model
310310
class TimeAllowedRangeModel:
311311
start: dt.time = api_field(
312312
description="The start time of day. Inclusive. Use ISO8601 format. Seconds are stripped."
@@ -334,7 +334,7 @@ def to_internal(self) -> tuple[_CheckmkTime, _CheckmkTime]:
334334
return (self.start.hour, self.start.minute), (self.end.hour, self.end.minute)
335335

336336

337-
@dataclass(kw_only=True, slots=True)
337+
@api_model
338338
class RegexpRewritesModel:
339339
search: Annotated[RegexString, MaxLen(30)] = api_field(
340340
description="The search regexp. May contain match-groups, conditional matches, etc. This follows the Python regular expression syntax.\n\nFor details see:\n\n * https://docs.python.org/3/library/re.html"
@@ -373,7 +373,7 @@ def to_internal(self) -> tuple[str, str]:
373373
return str(self.search), self.replace_with
374374

375375

376-
@dataclass(kw_only=True, slots=True)
376+
@api_model
377377
class DirectMappingModel:
378378
hostname: str = api_field(description="The host name to be replaced.")
379379
replace_with: str = api_field(description="The replacement string.")
@@ -389,7 +389,7 @@ def to_internal(self) -> tuple[str, str]:
389389
return self.hostname, self.replace_with
390390

391391

392-
@dataclass(kw_only=True, slots=True)
392+
@api_model
393393
class TranslateNamesModel:
394394
case: Literal["nop", "lower", "upper"] = api_field(
395395
serialization_alias="convert_case",
@@ -480,7 +480,7 @@ def to_internal(self) -> TranslationOptionsSpec:
480480
return spec
481481

482482

483-
@dataclass(kw_only=True, slots=True)
483+
@api_model
484484
class NetworkScanModel:
485485
ip_ranges: list[IPRangeModel] = api_field(
486486
serialization_alias="addresses", description="IPv4 addresses to include."
@@ -584,7 +584,7 @@ def to_internal(self) -> NetworkScanSpec:
584584
return spec
585585

586586

587-
@dataclass(kw_only=True, slots=True)
587+
@api_model
588588
class IPMIParametersModel: # TODO: this is dumb (or at least the IPMICredentials are)
589589
username: str | ApiOmitted = api_field(description="IPMI username", default_factory=ApiOmitted)
590590
password: str | ApiOmitted = api_field(description="IPMI password", default_factory=ApiOmitted)
@@ -605,7 +605,7 @@ def to_internal(self) -> IPMICredentials:
605605
return spec
606606

607607

608-
@dataclass(kw_only=True, slots=True)
608+
@api_model
609609
class NetworkScanResultModel:
610610
start: dt.datetime | None = api_field(
611611
description="When the scan started",
@@ -640,7 +640,7 @@ def from_internal(cls, value: NetworkScanResult) -> "NetworkScanResultModel":
640640
)
641641

642642

643-
@dataclass(kw_only=True, slots=True)
643+
@api_model
644644
class MetaDataModel:
645645
created_at: dt.datetime | ApiOmitted = api_field(
646646
description="When has this object been created.",
@@ -668,7 +668,7 @@ def from_internal(cls, value: MetaData) -> Self:
668668
)
669669

670670

671-
@dataclass(kw_only=True, slots=True)
671+
@api_model
672672
class LockedByModel:
673673
site_id: str = api_field(description="Site ID")
674674
program_id: str = api_field(description="Program ID")
@@ -689,7 +689,7 @@ def to_internal(self) -> Sequence[str]:
689689
return [self.site_id, self.program_id, self.instance_id]
690690

691691

692-
@dataclass(kw_only=True)
692+
@api_model
693693
class FolderCustomHostAttributesAndTagGroupsModel(WithDynamicFields):
694694
"""Class for custom host attributes and tag groups."""
695695

cmk/gui/openapi/api_endpoints/models/folder_attribute_models.py

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,6 @@
22
# Copyright (C) 2025 Checkmk GmbH - License: GNU General Public License v2
33
# This file is part of Checkmk (https://checkmk.com). It is subject to the terms and
44
# conditions defined in the file COPYING, which is part of this source code package.
5-
from dataclasses import dataclass
65
from typing import Annotated, Literal
76

87
from pydantic import AfterValidator
@@ -19,12 +18,12 @@
1918
SNMPCredentialsModel,
2019
)
2120
from cmk.gui.openapi.api_endpoints.models.host_attribute_models import BaseHostTagGroupModel
22-
from cmk.gui.openapi.framework.model import api_field, ApiOmitted
21+
from cmk.gui.openapi.framework.model import api_field, api_model, ApiOmitted
2322
from cmk.gui.openapi.framework.model.converter import HostConverter
2423
from cmk.gui.watolib.builtin_attributes import HostAttributeLabels
2524

2625

27-
@dataclass(kw_only=True)
26+
@api_model(slots=False)
2827
class BaseFolderAttributeModel:
2928
"""Base class for all folder attribute models."""
3029

@@ -106,7 +105,7 @@ def management_protocol_from_internal(value: str | None) -> str:
106105
return value
107106

108107

109-
@dataclass(kw_only=True, slots=True)
108+
@api_model
110109
class FolderViewAttributeModel(
111110
BaseFolderAttributeModel,
112111
BaseHostTagGroupModel,

0 commit comments

Comments
 (0)