otf-api 0.6.0__py3-none-any.whl → 0.6.1__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
otf_api/__init__.py CHANGED
@@ -6,7 +6,7 @@ from loguru import logger
6
6
  from .api import Otf
7
7
  from .auth import OtfUser
8
8
 
9
- __version__ = "0.6.0"
9
+ __version__ = "0.6.1"
10
10
 
11
11
 
12
12
  __all__ = ["Otf", "OtfUser"]
otf_api/models/base.py CHANGED
@@ -1,141 +1,14 @@
1
- import inspect
2
- import typing
3
- from typing import ClassVar, TypeVar
1
+ from typing import ClassVar
4
2
 
5
- from box import Box
6
3
  from pydantic import BaseModel, ConfigDict
7
4
 
8
- if typing.TYPE_CHECKING:
9
- from pydantic.main import IncEx
10
5
 
11
- T = TypeVar("T", bound="OtfItemBase")
12
-
13
-
14
- class BetterDumperMixin:
15
- """A better dumper for Pydantic models that includes properties in the dumped data. Must be mixed
16
- into a Pydantic model, as it overrides the `model_dump` method.
17
-
18
- Includes support for nested models, and has an option to not include properties when dumping.
19
- """
20
-
21
- def get_properties(self) -> list[str]:
22
- """Get the properties of the model."""
23
- cls = type(self)
24
-
25
- properties: list[str] = []
26
- methods = inspect.getmembers(self, lambda f: not (inspect.isroutine(f)))
27
- for prop_name, _ in methods:
28
- if hasattr(cls, prop_name) and isinstance(getattr(cls, prop_name), property):
29
- properties.append(prop_name)
30
-
31
- return properties
32
-
33
- @typing.overload
34
- def model_dump(
35
- self,
36
- *,
37
- mode: typing.Literal["json", "python"] | str = "python",
38
- include: "IncEx" = None,
39
- exclude: "IncEx" = None,
40
- by_alias: bool = False,
41
- exclude_unset: bool = False,
42
- exclude_defaults: bool = False,
43
- exclude_none: bool = False,
44
- round_trip: bool = False,
45
- warnings: bool = True,
46
- include_properties: bool = True,
47
- ) -> Box[str, typing.Any]: ...
48
-
49
- @typing.overload
50
- def model_dump(
51
- self,
52
- *,
53
- mode: typing.Literal["json", "python"] | str = "python",
54
- include: "IncEx" = None,
55
- exclude: "IncEx" = None,
56
- by_alias: bool = False,
57
- exclude_unset: bool = False,
58
- exclude_defaults: bool = False,
59
- exclude_none: bool = False,
60
- round_trip: bool = False,
61
- warnings: bool = True,
62
- include_properties: bool = False,
63
- ) -> dict[str, typing.Any]: ...
64
-
65
- def model_dump(
66
- self,
67
- *,
68
- mode: typing.Literal["json", "python"] | str = "python",
69
- include: "IncEx" = None,
70
- exclude: "IncEx" = None,
71
- by_alias: bool = False,
72
- exclude_unset: bool = False,
73
- exclude_defaults: bool = False,
74
- exclude_none: bool = False,
75
- round_trip: bool = False,
76
- warnings: bool = True,
77
- include_properties: bool = True,
78
- ) -> dict[str, typing.Any] | Box[str, typing.Any]:
79
- """Usage docs: https://docs.pydantic.dev/2.4/concepts/serialization/#modelmodel_dump
80
-
81
- Generate a dictionary representation of the model, optionally specifying which fields to include or exclude.
82
-
83
- Args:
84
- mode: The mode in which `to_python` should run.
85
- If mode is 'json', the dictionary will only contain JSON serializable types.
86
- If mode is 'python', the dictionary may contain any Python objects.
87
- include: A list of fields to include in the output.
88
- exclude: A list of fields to exclude from the output.
89
- by_alias: Whether to use the field's alias in the dictionary key if defined.
90
- exclude_unset: Whether to exclude fields that are unset or None from the output.
91
- exclude_defaults: Whether to exclude fields that are set to their default value from the output.
92
- exclude_none: Whether to exclude fields that have a value of `None` from the output.
93
- round_trip: Whether to enable serialization and deserialization round-trip support.
94
- warnings: Whether to log warnings when invalid fields are encountered.
95
- include_properties: Whether to include properties in the dumped data.
96
-
97
- Returns:
98
- A dictionary representation of the model. Will be a `Box` if `include_properties` is `True`, otherwise a
99
- regular dictionary.
100
-
101
- """
102
- dumped_data = typing.cast(BaseModel, super()).model_dump(
103
- mode=mode,
104
- include=include,
105
- exclude=exclude,
106
- by_alias=by_alias,
107
- exclude_unset=exclude_unset,
108
- exclude_defaults=exclude_defaults,
109
- exclude_none=exclude_none,
110
- round_trip=round_trip,
111
- warnings=warnings,
112
- )
113
-
114
- if not include_properties:
115
- return dumped_data
116
-
117
- properties = self.get_properties()
118
-
119
- # set properties to their values
120
- for prop_name in properties:
121
- dumped_data[prop_name] = getattr(self, prop_name)
122
-
123
- # if the property is a Pydantic model, dump it as well
124
- for k, v in dumped_data.items():
125
- if issubclass(type(getattr(self, k)), BaseModel):
126
- dumped_data[k] = getattr(self, k).model_dump()
127
- elif hasattr(v, "model_dump"):
128
- dumped_data[k] = v.model_dump()
129
-
130
- return Box(dumped_data)
131
-
132
-
133
- class OtfItemBase(BetterDumperMixin, BaseModel):
134
- model_config: ClassVar[ConfigDict] = ConfigDict(arbitrary_types_allowed=True, extra="forbid")
6
+ class OtfItemBase(BaseModel):
7
+ model_config: ClassVar[ConfigDict] = ConfigDict(arbitrary_types_allowed=True, extra="allow")
135
8
 
136
9
 
137
10
  class OtfListBase(BaseModel):
138
- model_config: ClassVar[ConfigDict] = ConfigDict(arbitrary_types_allowed=True, extra="forbid")
11
+ model_config: ClassVar[ConfigDict] = ConfigDict(arbitrary_types_allowed=True, extra="allow")
139
12
  collection_field: ClassVar[str] = "data"
140
13
 
141
14
  @property
@@ -101,7 +101,7 @@ class MemberDetail(OtfItemBase):
101
101
  state: None
102
102
  postal_code: None = Field(..., alias="postalCode")
103
103
  phone_number: str = Field(..., alias="phoneNumber")
104
- home_phone: str = Field(..., alias="homePhone")
104
+ home_phone: str | None = Field(..., alias="homePhone")
105
105
  work_phone: None = Field(..., alias="workPhone")
106
106
  phone_type: None = Field(..., alias="phoneType")
107
107
  birth_day: date | str = Field(..., alias="birthDay")
@@ -34,6 +34,7 @@ class Class(OtfItemBase):
34
34
  ot_base_class_uuid: str | None = None
35
35
  starts_at_local: str
36
36
  name: str | None = None
37
+ type: str | None = None
37
38
  coach: Coach
38
39
  studio: Studio
39
40
 
@@ -25,6 +25,14 @@ class TreadData(OtfItemBase):
25
25
  agg_tread_distance: int = Field(..., alias="aggTreadDistance")
26
26
 
27
27
 
28
+ class RowData(OtfItemBase):
29
+ row_speed: float = Field(..., alias="rowSpeed")
30
+ row_pps: float = Field(..., alias="rowPps")
31
+ row_Spm: float = Field(..., alias="rowSpm")
32
+ agg_row_distance: int = Field(..., alias="aggRowDistance")
33
+ row_pace: int = Field(..., alias="rowPace")
34
+
35
+
28
36
  class TelemetryItem(OtfItemBase):
29
37
  relative_timestamp: int = Field(..., alias="relativeTimestamp")
30
38
  hr: int
@@ -36,6 +44,7 @@ class TelemetryItem(OtfItemBase):
36
44
  description="The timestamp of the telemetry item, calculated from the class start time and relative timestamp.",
37
45
  )
38
46
  tread_data: TreadData | None = Field(None, alias="treadData")
47
+ row_data: RowData | None = Field(None, alias="rowData")
39
48
 
40
49
 
41
50
  class Telemetry(OtfItemBase):
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: otf-api
3
- Version: 0.6.0
3
+ Version: 0.6.1
4
4
  Summary: Python OrangeTheory Fitness API Client
5
5
  License: MIT
6
6
  Author: Jessica Smith
@@ -18,7 +18,7 @@ Classifier: Topic :: Internet :: WWW/HTTP
18
18
  Classifier: Topic :: Software Development :: Libraries
19
19
  Classifier: Topic :: Software Development :: Libraries :: Application Frameworks
20
20
  Classifier: Topic :: Software Development :: Libraries :: Python Modules
21
- Requires-Dist: aiohttp (==3.8.*)
21
+ Requires-Dist: aiohttp (==3.10.*)
22
22
  Requires-Dist: humanize (>=4.9.0,<5.0.0)
23
23
  Requires-Dist: inflection (==0.5.*)
24
24
  Requires-Dist: loguru (==0.7.2)
@@ -26,7 +26,6 @@ Requires-Dist: pendulum (>=3.0.0,<4.0.0)
26
26
  Requires-Dist: pint (==0.24.*)
27
27
  Requires-Dist: pycognito (==2024.5.1)
28
28
  Requires-Dist: pydantic (==2.7.3)
29
- Requires-Dist: python-box (>=7.2.0,<8.0.0)
30
29
  Project-URL: Documentation, https://otf-api.readthedocs.io/en/stable/
31
30
  Description-Content-Type: text/markdown
32
31
 
@@ -1,8 +1,8 @@
1
- otf_api/__init__.py,sha256=eRrcOgzcFV7KIhf6KwQ5AnvOaGfAam3AKbP01hAFOys,237
1
+ otf_api/__init__.py,sha256=-EBFAulRLsnoEbSE-S6B2s6VI9Oat7KW1a7p6qpfou4,237
2
2
  otf_api/api.py,sha256=QlRHXDwzbB97aCfacb_9FVox-5AuPLMweRQAZkz-EE0,34885
3
3
  otf_api/auth.py,sha256=XzwLSi5M3DyG7bE7DmWAzXF2y6fkJyAZxHUA9lpW25M,10231
4
4
  otf_api/models/__init__.py,sha256=3GHBOirQA4yu06cgD9pYmCU8u8_F9nxNHeSXDuFpe5A,1428
5
- otf_api/models/base.py,sha256=FrYzMVA4-EWhaKwzem8bEAzRu_jK-RTCkDj5ihTSkZM,5442
5
+ otf_api/models/base.py,sha256=gsMf3XGKqc68CRC-Mp3ARdnXKCpbWWGttZ8pfUwuEu0,664
6
6
  otf_api/models/responses/__init__.py,sha256=xxwz-JwRd0upmI0VNdvInbAm2FOQvPo3pS0SEhWfkI4,1947
7
7
  otf_api/models/responses/body_composition_list.py,sha256=RTC5bQpmMDUKqFl0nGFExdDxfnbOAGoBLWunjpOym80,12193
8
8
  otf_api/models/responses/book_class.py,sha256=bWURKEjLZWPzwu3HNP2zUmHWo7q7h6_z43a9KTST0Ec,15413
@@ -15,21 +15,21 @@ otf_api/models/responses/enums.py,sha256=Au8XhD-4T8ljiueUykFDc6Qz7kOoTlJ_kiDEx7n
15
15
  otf_api/models/responses/favorite_studios.py,sha256=C5JSyiNijm6HQEBVrV9vPfZexSWQ1IlN0E3Ag0GeP_0,4982
16
16
  otf_api/models/responses/latest_agreement.py,sha256=aE8hbWE4Pgguw4Itah7a1SqwOLpJ6t9oODFwLQ8Wzo0,774
17
17
  otf_api/models/responses/lifetime_stats.py,sha256=3nWjXJoIcTV_R-Q-3SXo63Uj2xjkFtNXmzj_jPcZPyo,3339
18
- otf_api/models/responses/member_detail.py,sha256=WG_GjS_7mZQ72d5rgu7e1dc3e4fVaR5HRlxFtbJfct8,6024
18
+ otf_api/models/responses/member_detail.py,sha256=qgP_gaiIi6Jr5SI7RSrj8l9p6aCbVK0fJX2LgI5Gazk,6031
19
19
  otf_api/models/responses/member_membership.py,sha256=_z301T9DrdQW9vIgnx_LeZmkRhvMVhkxrn_v6DDfCUk,995
20
20
  otf_api/models/responses/member_purchases.py,sha256=JoTk3hYjsq4rXogVivZxeFaM-j3gIChmIAGVldOU7rE,6085
21
21
  otf_api/models/responses/out_of_studio_workout_history.py,sha256=FwdnmTgFrMtQ8PngsmCv3UroWj3kDnQg6KfGLievoaU,1709
22
22
  otf_api/models/responses/performance_summary_detail.py,sha256=H5yWxGShR4uiXvY2OaniENburTGM7DKQjN7gvF3MG6g,1585
23
- otf_api/models/responses/performance_summary_list.py,sha256=R__tsXGz5tVX5gfoRoVUNK4UP2pXRoK5jdSyHABsDXs,1234
23
+ otf_api/models/responses/performance_summary_list.py,sha256=z1W1b7rOZ9HESgRL9P_krd7MSGaMASxCVr3EpYOLBvE,1262
24
24
  otf_api/models/responses/studio_detail.py,sha256=CJBCsi4SMs_W5nrWE4hfCs1ugJ5t7GrH80hTv7Ie3eg,5007
25
25
  otf_api/models/responses/studio_services.py,sha256=mFDClPtU0HCk5fb19gjGKpt2F8n8kto7sj1pE_l4RdQ,1836
26
- otf_api/models/responses/telemetry.py,sha256=8dl8FKLeyb6jtqsZT7XD4JzXBMLlami448-Jt0tFbSY,1663
26
+ otf_api/models/responses/telemetry.py,sha256=MTI9fV9LniWU73xRfV_ZcdQeaeDLuaYMcQgL239lEAI,2012
27
27
  otf_api/models/responses/telemetry_hr_history.py,sha256=vDcLb4wTHVBw8O0mGblUujHfJegkflOCWW-bnTXNCI0,763
28
28
  otf_api/models/responses/telemetry_max_hr.py,sha256=xKxH0fIlOqFyZv8UW98XsxF-GMoIs9gnCTAbu88ZQtg,266
29
29
  otf_api/models/responses/total_classes.py,sha256=WrKkWbq0eK8J0RC4qhZ5kmXnv_ZTDbyzsoRm7XKGlss,288
30
30
  otf_api/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
31
- otf_api-0.6.0.dist-info/AUTHORS.md,sha256=FcNWMxpe8KDuTq4Qau0SUXsabQwGs9TGnMp1WkXRnj8,123
32
- otf_api-0.6.0.dist-info/LICENSE,sha256=UaPT9ynYigC3nX8n22_rC37n-qmTRKLFaHrtUwF9ktE,1071
33
- otf_api-0.6.0.dist-info/METADATA,sha256=lzG11-AQbcrEr5whF8QiBWSeJljHCG3V2OL_I1hDl6M,2031
34
- otf_api-0.6.0.dist-info/WHEEL,sha256=sP946D7jFCHeNz5Iq4fL4Lu-PrWrFsgfLXbbkciIZwg,88
35
- otf_api-0.6.0.dist-info/RECORD,,
31
+ otf_api-0.6.1.dist-info/AUTHORS.md,sha256=FcNWMxpe8KDuTq4Qau0SUXsabQwGs9TGnMp1WkXRnj8,123
32
+ otf_api-0.6.1.dist-info/LICENSE,sha256=UaPT9ynYigC3nX8n22_rC37n-qmTRKLFaHrtUwF9ktE,1071
33
+ otf_api-0.6.1.dist-info/METADATA,sha256=A9Afi7GJdLWBRCN-0lZ_OV5AHm0RfDos1kd8Nr0n2eo,1989
34
+ otf_api-0.6.1.dist-info/WHEEL,sha256=sP946D7jFCHeNz5Iq4fL4Lu-PrWrFsgfLXbbkciIZwg,88
35
+ otf_api-0.6.1.dist-info/RECORD,,