spond_classes

Introduction

Spond is a team/group-oriented events system.

The unofficial Python spond package gets data from the Spond API and returns dict objects.

This unofficial Python spond-classes package parses those dicts to Pydantic class instances.

Key classes

These are the classes intended for direct user instantiation:

 1"""
 2# Introduction
 3
 4[Spond](https://spond.com/welcome) is a team/group-oriented events system.
 5
 6The unofficial Python [`spond`](https://github.com/Olen/Spond/) package gets data from
 7the Spond API and returns `dict` objects.
 8
 9This unofficial Python [`spond-classes`](https://github.com/elliot-100/Spond-classes)
10package parses those `dict`s to [Pydantic](https://docs.pydantic.dev/) class instances.
11
12# Key classes
13
14These are the classes intended for direct user instantiation:
15
16- `Event` via `Event.list_from_data()`
17- `Group` via `Group.list_from_data()`
18"""
19
20# Explicitly import classes and functions into the package namespace to define the API.
21
22from . import typing
23from .event import Event, Responses
24from .group import FieldDef, Group
25from .member import Member
26from .profile_ import Profile
27from .role import Role
28from .subgroup import Subgroup
29
30__all__ = [
31    "Event",
32    "Responses",
33    "FieldDef",
34    "Group",
35    "Member",
36    "Profile",
37    "Role",
38    "Subgroup",
39    "typing",
40]
class Event(pydantic.main.BaseModel):
 42class Event(BaseModel):
 43    """Represents an event in the Spond system."""
 44
 45    uid: str = Field(alias="id")
 46    """`id` in Spond API; aliased as that's a Python built-in, and the Spond package
 47    uses `uid`."""
 48    heading: str
 49    """Same name in Spond API."""
 50    responses: Responses
 51    """Same name in Spond API."""
 52    type: Literal["AVAILABILITY", "EVENT", "RECURRING"]
 53    """Same name in Spond API.
 54
 55    'AVAILABILITY': availability request.
 56    'EVENT': regular event.
 57    'RECURRING': instance of recurring event."""
 58    created_time: datetime = Field(alias="createdTime")
 59    """Derived from `createdTime` in Spond API."""
 60    end_time: datetime = Field(alias="endTimestamp")
 61    """Datetime at which the `Event` ends.
 62    Derived from `endTimestamp` in Spond API."""
 63    start_time: datetime = Field(alias="startTimestamp")
 64    """Datetime at which the `Event` starts.
 65    Derived from `startTimestamp` in Spond API."""
 66
 67    # Optional in API data
 68    cancelled: bool | None = Field(default=None)
 69    """Same name in Spond API. Not always present. Use `Event.is_cancelled` instead to
 70    always return a `bool`."""
 71    hidden: bool | None = Field(default=None)
 72    """Same name in Spond API. Not always present. Use `Event.is_hidden` instead to
 73    always return a `bool`."""
 74    invite_time: datetime | None = Field(alias="inviteTime", default=None)
 75    """Derived from `inviteTime` in Spond API.
 76    Not always present."""
 77
 78    def __str__(self) -> str:
 79        """Return simple human-readable description.
 80
 81        Includes only key fields in custom order.
 82        """
 83        return (
 84            f"Event(uid='{self.uid}', "
 85            f"heading='{self.heading}', "
 86            f"start_time: {self.start_time}, "
 87            "…)"
 88        )
 89
 90    @property
 91    def url(self) -> str:
 92        """Return the URL of the `Event`, for convenience."""
 93        return f"https://spond.com/client/sponds/{self.uid}/"
 94
 95    @property
 96    def is_cancelled(self) -> bool:
 97        """Return whether the `Event` is cancelled."""
 98        return getattr(self, "cancelled", False)
 99
100    @property
101    def is_hidden(self) -> bool:
102        """Return whether the `Event` is hidden."""
103        return getattr(self, "hidden", False)
104
105    @classmethod
106    def list_from_data(cls, data: Iterable[DictFromJSON]) -> list[Self]:
107        """Construct a list of `Event`s from the list returned by `Spond.get_events()`.
108
109        Parameters
110        ----------
111        data
112            as returned by `spond.spond.Spond.get_events()`.
113
114        Returns
115        -------
116        `list[Event]`
117
118        Raises
119        ------
120        `TypeError`
121            if an item in `data` is not a `dict`.
122        """
123        return [cls.from_dict(item) for item in data]
124
125    @classmethod
126    def from_dict(cls, dict_: DictFromJSON) -> Self:
127        """Construct an `Event`.
128
129        Parameters
130        ----------
131        dict_
132            as returned by `spond.spond.Spond.get_event()`
133            or from the list returned by `spond.spond.Spond.get_events()`.
134
135        Returns
136        -------
137        `Event`
138
139        Raises
140        ------
141        `TypeError`
142            if `dict_` is not a `dict`.
143        """
144        _ensure_dict(dict_)
145        return cls(**dict_)

Represents an event in the Spond system.

uid: str = PydanticUndefined

id in Spond API; aliased as that's a Python built-in, and the Spond package uses uid.

heading: str = PydanticUndefined

Same name in Spond API.

responses: Responses = PydanticUndefined

Same name in Spond API.

type: Literal['AVAILABILITY', 'EVENT', 'RECURRING'] = PydanticUndefined

Same name in Spond API.

'AVAILABILITY': availability request. 'EVENT': regular event. 'RECURRING': instance of recurring event.

created_time: datetime.datetime = PydanticUndefined

Derived from createdTime in Spond API.

end_time: datetime.datetime = PydanticUndefined

Datetime at which the Event ends. Derived from endTimestamp in Spond API.

start_time: datetime.datetime = PydanticUndefined

Datetime at which the Event starts. Derived from startTimestamp in Spond API.

cancelled: bool | None = None

Same name in Spond API. Not always present. Use Event.is_cancelled instead to always return a bool.

hidden: bool | None = None

Same name in Spond API. Not always present. Use Event.is_hidden instead to always return a bool.

invite_time: datetime.datetime | None = None

Derived from inviteTime in Spond API. Not always present.

url: str
90    @property
91    def url(self) -> str:
92        """Return the URL of the `Event`, for convenience."""
93        return f"https://spond.com/client/sponds/{self.uid}/"

Return the URL of the Event, for convenience.

is_cancelled: bool
95    @property
96    def is_cancelled(self) -> bool:
97        """Return whether the `Event` is cancelled."""
98        return getattr(self, "cancelled", False)

Return whether the Event is cancelled.

is_hidden: bool
100    @property
101    def is_hidden(self) -> bool:
102        """Return whether the `Event` is hidden."""
103        return getattr(self, "hidden", False)

Return whether the Event is hidden.

@classmethod
def list_from_data(cls, data: Iterable[dict[str, typing.Any]]) -> list[typing.Self]:
105    @classmethod
106    def list_from_data(cls, data: Iterable[DictFromJSON]) -> list[Self]:
107        """Construct a list of `Event`s from the list returned by `Spond.get_events()`.
108
109        Parameters
110        ----------
111        data
112            as returned by `spond.spond.Spond.get_events()`.
113
114        Returns
115        -------
116        `list[Event]`
117
118        Raises
119        ------
120        `TypeError`
121            if an item in `data` is not a `dict`.
122        """
123        return [cls.from_dict(item) for item in data]

Construct a list of Events from the list returned by Spond.get_events().

Parameters
  • data: as returned by spond.spond.Spond.get_events().
Returns
  • list[Event]
Raises
  • TypeError: if an item in data is not a dict.
@classmethod
def from_dict(cls, dict_: dict[str, typing.Any]) -> Self:
125    @classmethod
126    def from_dict(cls, dict_: DictFromJSON) -> Self:
127        """Construct an `Event`.
128
129        Parameters
130        ----------
131        dict_
132            as returned by `spond.spond.Spond.get_event()`
133            or from the list returned by `spond.spond.Spond.get_events()`.
134
135        Returns
136        -------
137        `Event`
138
139        Raises
140        ------
141        `TypeError`
142            if `dict_` is not a `dict`.
143        """
144        _ensure_dict(dict_)
145        return cls(**dict_)

Construct an Event.

Parameters
  • dict_: as returned by spond.spond.Spond.get_event() or from the list returned by spond.spond.Spond.get_events().
Returns
Raises
  • TypeError: if dict_ is not a dict.
class Responses(pydantic.main.BaseModel):
21class Responses(BaseModel):
22    """Represents the responses to an `Event`."""
23
24    # Lists which always exist in API data, but may be empty
25    accepted_uids: list[str] = Field(alias="acceptedIds")
26    """`acceptedIds` in Spond API.
27    May be empty."""
28    declined_uids: list[str] = Field(alias="declinedIds")
29    """`declinedIds` in Spond API.
30    May be empty."""
31    unanswered_uids: list[str] = Field(alias="unansweredIds")
32    """`unansweredIds` in Spond API.
33    May be empty."""
34    waiting_list_uids: list[str] = Field(alias="waitinglistIds")
35    """`waitinglistIds` in Spond API.
36    May be empty."""
37    unconfirmed_uids: list[str] = Field(alias="unconfirmedIds")
38    """`unconfirmedIds` in Spond API.
39    May be empty."""

Represents the responses to an Event.

accepted_uids: list[str] = PydanticUndefined

acceptedIds in Spond API. May be empty.

declined_uids: list[str] = PydanticUndefined

declinedIds in Spond API. May be empty.

unanswered_uids: list[str] = PydanticUndefined

unansweredIds in Spond API. May be empty.

waiting_list_uids: list[str] = PydanticUndefined

waitinglistIds in Spond API. May be empty.

unconfirmed_uids: list[str] = PydanticUndefined

unconfirmedIds in Spond API. May be empty.

class FieldDef(pydantic.main.BaseModel):
20class FieldDef(BaseModel):
21    """Custom field definition."""
22
23    uid: str = Field(alias="id")
24    """`id` in Spond API; aliased as that's a Python built-in, and the Spond package
25    uses `uid`."""
26    name: str

Custom field definition.

uid: str = PydanticUndefined

id in Spond API; aliased as that's a Python built-in, and the Spond package uses uid.

name: str = PydanticUndefined
class Group(pydantic.main.BaseModel):
 29class Group(BaseModel):
 30    """Represents a group in the Spond system.
 31
 32    A `Group` has:
 33    - zero, one or more `Member`s
 34    - zero, one or more `Role`s
 35    - zero, one or more `Subgroup`s
 36    """
 37
 38    uid: str = Field(alias="id")
 39    """`id` in Spond API; aliased as that's a Python built-in, and the Spond package
 40    uses `uid`."""
 41    name: str
 42    """Same name in Spond API."""
 43
 44    # Mutables which always exist in Spond API data, but may be empty
 45    members: list[Member]
 46    """`Member`s belonging to the `Group`.
 47    Derived from `members` in Spond API.
 48    May be empty."""
 49    roles: list[Role]
 50    """`Role`s belonging to the `Group`.
 51    Derived from `roles` in Spond API.
 52    May be empty."""
 53    subgroups: list[Subgroup] = Field(alias="subGroups")
 54    """`Subgroup`s belonging to the `Group`.
 55    Derived from `subGroups` in Spond API.
 56    May be empty."""
 57    field_defs: list[FieldDef] = Field(alias="fieldDefs")
 58    """Custom field definitions.
 59    Derived from `fieldDefs` in Spond API.
 60    May be empty."""
 61
 62    def __str__(self) -> str:
 63        """Return simple human-readable description.
 64
 65        Includes only key fields in custom order.
 66        """
 67        return f"Group(uid='{self.uid}', name='{self.name}', …)"
 68
 69    @classmethod
 70    def list_from_data(cls, data: Iterable[DictFromJSON]) -> list[Self]:
 71        """Construct a list of `Group`s from the list returned by `Spond.get_groups()`.
 72
 73        Parameters
 74        ----------
 75        data
 76            as returned by `spond.spond.Spond.get_groups()`.
 77
 78        Returns
 79        -------
 80        `list[Group]`
 81
 82        Raises
 83        ------
 84        `TypeError`
 85            if an item in `data` is not a `dict`.
 86        """
 87        return [cls.from_dict(item) for item in data]
 88
 89    @classmethod
 90    def from_dict(cls, dict_: DictFromJSON) -> Self:
 91        """Construct a `Group`.
 92
 93        Parameters
 94        ----------
 95        dict_
 96            as returned by `spond.spond.Spond.get_group()`
 97            or from the list returned by `spond.spond.Spond.get_groups()`.
 98
 99        Returns
100        -------
101        `Group`
102
103        Raises
104        ------
105        `TypeError`
106            if `dict_` is not a `dict`.
107        """
108        _ensure_dict(dict_)
109        return cls(**dict_)
110
111    def member_by_uid(self, uid: str) -> Member:
112        """Return the `Member` with matching `uid`.
113
114        Parameters
115        ----------
116        uid
117
118        Returns
119        -------
120        `Member`
121
122        Raises
123        ------
124        LookupError
125            If `uid` is not found.
126        """
127        for member in self.members:
128            if member.uid == uid:
129                return member
130        err_msg = f"No Member found with id='{uid}'."
131        raise LookupError(err_msg)
132
133    def role_by_uid(self, uid: str) -> Role:
134        """Return the `Role` with matching `uid`.
135
136        Parameters
137        ----------
138        uid
139
140        Returns
141        -------
142        `Role`
143
144        Raises
145        ------
146        LookupError
147            If `uid` is not found.
148        """
149        for role in self.roles:
150            if role.uid == uid:
151                return role
152        err_msg = f"No Role found with id='{uid}'."
153        raise LookupError(err_msg)
154
155    def subgroup_by_uid(self, uid: str) -> Subgroup:
156        """Return the `Subgroup` with matching `uid`.
157
158        Parameters
159        ----------
160        uid
161
162        Returns
163        -------
164        `Subgroup`
165
166        Raises
167        ------
168        LookupError
169            If `uid` is not found.
170        """
171        for subgroup in self.subgroups:
172            if subgroup.uid == uid:
173                return subgroup
174        err_msg = f"No Subgroup found with id='{uid}'."
175        raise LookupError(err_msg)
176
177    def members_by_subgroup(self, subgroup: Subgroup) -> list[Member]:
178        """Return `Member`s in the `Subgroup`.
179
180        Parameters
181        ----------
182        subgroup
183            `Subgroup` from which to return `Member`s.
184
185        Returns
186        -------
187        list[`Member`]
188
189        Raises
190        ------
191        TypeError
192            If `subgroup` is not a `Subgroup` instance.
193        """
194        if not isinstance(subgroup, Subgroup):
195            err_msg = "`subgroup` must be a Subgroup."
196            raise TypeError(err_msg)
197        return [
198            member for member in self.members if subgroup.uid in member.subgroup_uids
199        ]
200
201    def members_by_role(self, role: Role) -> list[Member]:
202        """Return `Member`s with the `Role`.
203
204        Parameters
205        ----------
206        role
207            `Role` from which to return `Member`s.
208
209        Returns
210        -------
211        list[`Member`]
212
213        Raises
214        ------
215        TypeError
216            If `role` is not a `Role` instance.
217        """
218        if not isinstance(role, Role):
219            err_msg = "`role` must be a Role."
220            raise TypeError(err_msg)
221        return [
222            member
223            for member in self.members
224            if member.role_uids and role.uid in member.role_uids
225        ]

Represents a group in the Spond system.

A Group has:

uid: str = PydanticUndefined

id in Spond API; aliased as that's a Python built-in, and the Spond package uses uid.

name: str = PydanticUndefined

Same name in Spond API.

members: list[Member] = PydanticUndefined

Members belonging to the Group. Derived from members in Spond API. May be empty.

roles: list[Role] = PydanticUndefined

Roles belonging to the Group. Derived from roles in Spond API. May be empty.

subgroups: list[Subgroup] = PydanticUndefined

Subgroups belonging to the Group. Derived from subGroups in Spond API. May be empty.

field_defs: list[FieldDef] = PydanticUndefined

Custom field definitions. Derived from fieldDefs in Spond API. May be empty.

@classmethod
def list_from_data(cls, data: Iterable[dict[str, typing.Any]]) -> list[typing.Self]:
69    @classmethod
70    def list_from_data(cls, data: Iterable[DictFromJSON]) -> list[Self]:
71        """Construct a list of `Group`s from the list returned by `Spond.get_groups()`.
72
73        Parameters
74        ----------
75        data
76            as returned by `spond.spond.Spond.get_groups()`.
77
78        Returns
79        -------
80        `list[Group]`
81
82        Raises
83        ------
84        `TypeError`
85            if an item in `data` is not a `dict`.
86        """
87        return [cls.from_dict(item) for item in data]

Construct a list of Groups from the list returned by Spond.get_groups().

Parameters
  • data: as returned by spond.spond.Spond.get_groups().
Returns
  • list[Group]
Raises
  • TypeError: if an item in data is not a dict.
@classmethod
def from_dict(cls, dict_: dict[str, typing.Any]) -> Self:
 89    @classmethod
 90    def from_dict(cls, dict_: DictFromJSON) -> Self:
 91        """Construct a `Group`.
 92
 93        Parameters
 94        ----------
 95        dict_
 96            as returned by `spond.spond.Spond.get_group()`
 97            or from the list returned by `spond.spond.Spond.get_groups()`.
 98
 99        Returns
100        -------
101        `Group`
102
103        Raises
104        ------
105        `TypeError`
106            if `dict_` is not a `dict`.
107        """
108        _ensure_dict(dict_)
109        return cls(**dict_)

Construct a Group.

Parameters
  • dict_: as returned by spond.spond.Spond.get_group() or from the list returned by spond.spond.Spond.get_groups().
Returns
Raises
  • TypeError: if dict_ is not a dict.
def member_by_uid(self, uid: str) -> Member:
111    def member_by_uid(self, uid: str) -> Member:
112        """Return the `Member` with matching `uid`.
113
114        Parameters
115        ----------
116        uid
117
118        Returns
119        -------
120        `Member`
121
122        Raises
123        ------
124        LookupError
125            If `uid` is not found.
126        """
127        for member in self.members:
128            if member.uid == uid:
129                return member
130        err_msg = f"No Member found with id='{uid}'."
131        raise LookupError(err_msg)

Return the Member with matching uid.

Parameters
  • uid
Returns
Raises
  • LookupError: If uid is not found.
def role_by_uid(self, uid: str) -> Role:
133    def role_by_uid(self, uid: str) -> Role:
134        """Return the `Role` with matching `uid`.
135
136        Parameters
137        ----------
138        uid
139
140        Returns
141        -------
142        `Role`
143
144        Raises
145        ------
146        LookupError
147            If `uid` is not found.
148        """
149        for role in self.roles:
150            if role.uid == uid:
151                return role
152        err_msg = f"No Role found with id='{uid}'."
153        raise LookupError(err_msg)

Return the Role with matching uid.

Parameters
  • uid
Returns
Raises
  • LookupError: If uid is not found.
def subgroup_by_uid(self, uid: str) -> Subgroup:
155    def subgroup_by_uid(self, uid: str) -> Subgroup:
156        """Return the `Subgroup` with matching `uid`.
157
158        Parameters
159        ----------
160        uid
161
162        Returns
163        -------
164        `Subgroup`
165
166        Raises
167        ------
168        LookupError
169            If `uid` is not found.
170        """
171        for subgroup in self.subgroups:
172            if subgroup.uid == uid:
173                return subgroup
174        err_msg = f"No Subgroup found with id='{uid}'."
175        raise LookupError(err_msg)

Return the Subgroup with matching uid.

Parameters
  • uid
Returns
Raises
  • LookupError: If uid is not found.
def members_by_subgroup( self, subgroup: Subgroup) -> list[Member]:
177    def members_by_subgroup(self, subgroup: Subgroup) -> list[Member]:
178        """Return `Member`s in the `Subgroup`.
179
180        Parameters
181        ----------
182        subgroup
183            `Subgroup` from which to return `Member`s.
184
185        Returns
186        -------
187        list[`Member`]
188
189        Raises
190        ------
191        TypeError
192            If `subgroup` is not a `Subgroup` instance.
193        """
194        if not isinstance(subgroup, Subgroup):
195            err_msg = "`subgroup` must be a Subgroup."
196            raise TypeError(err_msg)
197        return [
198            member for member in self.members if subgroup.uid in member.subgroup_uids
199        ]

Return Members in the Subgroup.

Parameters
Returns
Raises
  • TypeError: If subgroup is not a Subgroup instance.
def members_by_role(self, role: Role) -> list[Member]:
201    def members_by_role(self, role: Role) -> list[Member]:
202        """Return `Member`s with the `Role`.
203
204        Parameters
205        ----------
206        role
207            `Role` from which to return `Member`s.
208
209        Returns
210        -------
211        list[`Member`]
212
213        Raises
214        ------
215        TypeError
216            If `role` is not a `Role` instance.
217        """
218        if not isinstance(role, Role):
219            err_msg = "`role` must be a Role."
220            raise TypeError(err_msg)
221        return [
222            member
223            for member in self.members
224            if member.role_uids and role.uid in member.role_uids
225        ]

Return Members with the Role.

Parameters
Returns
Raises
  • TypeError: If role is not a Role instance.
class Member(pydantic.main.BaseModel):
11class Member(BaseModel):
12    """Represents a member in the Spond system.
13
14    A `Member` is an individual's `Group`-specific record.
15
16    A `Member` may have a `Profile`.
17    """
18
19    uid: str = Field(alias="id")
20    """`id` in Spond API; aliased as that's a Python built-in, and the Spond package
21    uses `uid`."""
22    created_time: datetime = Field(alias="createdTime")
23    """Derived from `createdTime` in Spond API."""
24    first_name: str = Field(alias="firstName")
25    """`firstName` in Spond API."""
26    last_name: str = Field(alias="lastName")
27    """`lastName` in Spond API."""
28
29    # Mutables which always exist in Spond API data, but may be empty
30    subgroup_uids: list[str] = Field(alias="subGroups")
31    """`subGroups` in Spond API; aliased to avoid confusion with `Subgroup` instances.
32    May be empty."""
33    fields: dict[str, int | str] = Field(alias="fields")
34    """Custom fields. Same name in Spond API.
35    May be empty."""
36
37    # Optional in Spond API data
38    email: EmailStr | None = Field(default=None)
39    """Same name in Spond API. Not always present."""
40    phone_number: str | None = Field(alias="phoneNumber", default=None)
41    """`phoneNumber` in Spond API.
42    Not always present."""
43    profile: Profile | None = None  # Availability may depend on permissions
44    """Derived from `profile` in Spond API.
45    Not always present."""
46    role_uids: list[str] | None = Field(alias="roles", default=None)
47    """`roles` in Spond API; aliased to avoid confusion with `Role` instances.
48    Not always present."""
49
50    def __str__(self) -> str:
51        """Return simple human-readable description.
52
53        Includes only key fields in custom order.
54        """
55        return f"Member(uid='{self.uid}', full_name='{self.full_name}', …)"
56
57    @property
58    def full_name(self) -> str:
59        """Return the `Member`'s full name, for convenience."""
60        return f"{self.first_name} {self.last_name}"

Represents a member in the Spond system.

A Member is an individual's Group-specific record.

A Member may have a Profile.

uid: str = PydanticUndefined

id in Spond API; aliased as that's a Python built-in, and the Spond package uses uid.

created_time: datetime.datetime = PydanticUndefined

Derived from createdTime in Spond API.

first_name: str = PydanticUndefined

firstName in Spond API.

last_name: str = PydanticUndefined

lastName in Spond API.

subgroup_uids: list[str] = PydanticUndefined

subGroups in Spond API; aliased to avoid confusion with Subgroup instances. May be empty.

fields: dict[str, int | str] = PydanticUndefined

Custom fields. Same name in Spond API. May be empty.

email: pydantic.networks.EmailStr | None = None

Same name in Spond API. Not always present.

phone_number: str | None = None

phoneNumber in Spond API. Not always present.

profile: Profile | None = None

Derived from profile in Spond API. Not always present.

role_uids: list[str] | None = None

roles in Spond API; aliased to avoid confusion with Role instances. Not always present.

full_name: str
57    @property
58    def full_name(self) -> str:
59        """Return the `Member`'s full name, for convenience."""
60        return f"{self.first_name} {self.last_name}"

Return the Member's full name, for convenience.

class Profile(pydantic.main.BaseModel):
 7class Profile(BaseModel):
 8    """Represents a profile in the Spond system.
 9
10    A `Profile` is an individual's account-specific record.
11
12    A `Profile` belongs to a `Member`.
13    """
14
15    uid: str = Field(alias="id")
16    """`id` in Spond API; aliased as that's a Python built-in, and the Spond package
17    uses `uid`."""
18    first_name: str = Field(alias="firstName")
19    """`firstName` in Spond API."""
20    last_name: str = Field(alias="lastName")
21    """`lastName` in Spond API."""
22
23    # Optional in Spond API data
24    email: EmailStr | None = Field(default=None)
25    """Same name in Spond API. Not always present."""
26    phone_number: str | None = Field(alias="phoneNumber", default=None)
27    """`phoneNumber` in Spond API.
28    Not always present."""
29
30    def __str__(self) -> str:
31        """Return simple human-readable description.
32
33        Includes only key fields in custom order.
34        """
35        return f"Profile(uid='{self.uid}', full_name='{self.full_name}', …)"
36
37    @property
38    def full_name(self) -> str:
39        """Return the `Profile`'s full name, for convenience."""
40        return f"{self.first_name} {self.last_name}"

Represents a profile in the Spond system.

A Profile is an individual's account-specific record.

A Profile belongs to a Member.

uid: str = PydanticUndefined

id in Spond API; aliased as that's a Python built-in, and the Spond package uses uid.

first_name: str = PydanticUndefined

firstName in Spond API.

last_name: str = PydanticUndefined

lastName in Spond API.

email: pydantic.networks.EmailStr | None = None

Same name in Spond API. Not always present.

phone_number: str | None = None

phoneNumber in Spond API. Not always present.

full_name: str
37    @property
38    def full_name(self) -> str:
39        """Return the `Profile`'s full name, for convenience."""
40        return f"{self.first_name} {self.last_name}"

Return the Profile's full name, for convenience.

class Role(pydantic.main.BaseModel):
 7class Role(BaseModel):
 8    """Represents a role in the Spond system.
 9
10    A `Role` belongs to a `Group`.
11
12    Use `Group.members_by_role()` to get subordinate `Member`s.
13    """
14
15    uid: str = Field(alias="id")
16    """`id` in Spond API; aliased as that's a Python built-in, and the Spond package
17    uses `uid`."""
18    name: str
19    """Same name in Spond API."""
20
21    def __str__(self) -> str:
22        """Return simple human-readable description."""
23        return f"Role(uid='{self.uid}', name='{self.name}')"

Represents a role in the Spond system.

A Role belongs to a Group.

Use Group.members_by_role() to get subordinate Members.

uid: str = PydanticUndefined

id in Spond API; aliased as that's a Python built-in, and the Spond package uses uid.

name: str = PydanticUndefined

Same name in Spond API.

class Subgroup(pydantic.main.BaseModel):
 7class Subgroup(BaseModel):
 8    """Represents a subgroup in the Spond system.
 9
10    A `Subgroup` belongs to a `Group`.
11
12    Use `Group.members_by_subgroup()` to get subordinate `Member`s.
13    """
14
15    uid: str = Field(alias="id")
16    """`id` in Spond API; aliased as that's a Python built-in, and the Spond package
17    uses `uid`."""
18    name: str
19    """Same name in Spond API."""
20
21    def __str__(self) -> str:
22        """Return simple human-readable description."""
23        return f"Subgroup(uid='{self.uid}', name='{self.name}')"

Represents a subgroup in the Spond system.

A Subgroup belongs to a Group.

Use Group.members_by_subgroup() to get subordinate Members.

uid: str = PydanticUndefined

id in Spond API; aliased as that's a Python built-in, and the Spond package uses uid.

name: str = PydanticUndefined

Same name in Spond API.