Coverage for C: \ Users \ peaco \ OneDrive \ Documents \ GitHub \ mt_metadata \ mt_metadata \ common \ person.py: 100%
31 statements
« prev ^ index » next coverage.py v7.13.1, created at 2026-01-10 00:11 -0800
« prev ^ index » next coverage.py v7.13.1, created at 2026-01-10 00:11 -0800
1# =====================================================
2# Imports
3# =====================================================
4from typing import Annotated
6from pydantic import (
7 AliasChoices,
8 AnyUrl,
9 EmailStr,
10 Field,
11 field_validator,
12 ValidationInfo,
13)
15from mt_metadata import NULL_VALUES
16from mt_metadata.base import MetadataBase
17from mt_metadata.common import Comment
20# =====================================================
21class GenericPerson(MetadataBase):
22 organization: Annotated[
23 str | None,
24 Field(
25 default=None,
26 description="Organization full name",
27 alias=None,
28 json_schema_extra={
29 "units": None,
30 "required": False,
31 "examples": ["mt gurus"],
32 },
33 ),
34 ]
36 email: Annotated[
37 EmailStr | None,
38 Field(
39 default=None,
40 description="Email of the contact person",
41 alias=None,
42 json_schema_extra={
43 "units": None,
44 "required": False,
45 "examples": ["mt.guru@em.org"],
46 },
47 ),
48 ]
50 url: Annotated[
51 AnyUrl | None | str,
52 Field(
53 default=None,
54 description="URL of the contact person",
55 alias=None,
56 json_schema_extra={
57 "units": None,
58 "required": False,
59 "examples": ["https://em.org"],
60 },
61 ),
62 ]
64 comments: Annotated[
65 Comment,
66 Field(
67 default_factory=Comment, # type: ignore[return-value]
68 description="Any comments about the person",
69 alias=None,
70 json_schema_extra={
71 "units": None,
72 "required": False,
73 "examples": ["expert digger"],
74 },
75 ),
76 ]
78 @field_validator("comments", mode="before")
79 @classmethod
80 def validate_comments(cls, value, info: ValidationInfo) -> Comment:
81 """
82 Validate that the value is a valid comment.
83 """
84 if isinstance(value, str | None):
85 return Comment(value=value) # type: ignore[return-value]
86 return value
88 @field_validator("url", mode="before")
89 @classmethod
90 def validate_url(cls, value, info: ValidationInfo) -> AnyUrl | None:
91 """
92 Validate that the value is a valid URL.
93 """
94 if isinstance(value, str):
95 if value in NULL_VALUES:
96 return None
97 return AnyUrl(value)
98 elif isinstance(value, AnyUrl):
99 return value
100 elif value is None:
101 return None
104class Person(GenericPerson):
105 name: Annotated[
106 str | None,
107 Field(
108 default="",
109 description="Persons name, should be full first and last name.",
110 validation_alias=AliasChoices("name", "author"),
111 json_schema_extra={
112 "units": None,
113 "required": True,
114 "examples": ["person name"],
115 },
116 ),
117 ]
120## Its too complicated to have an alias for name, because there is no getter for author
121## and with serialization it becomes complicates, easiest solution is to make a different
122## object with a field for author instead of name.
125class AuthorPerson(GenericPerson):
126 author: Annotated[
127 str | None,
128 Field(
129 default="",
130 description="Persons name, should be full first and last name.",
131 validation_alias=AliasChoices("author", "name"),
132 json_schema_extra={
133 "units": None,
134 "required": True,
135 "examples": ["person name"],
136 },
137 ),
138 ]