@@ -150,12 +150,11 @@ class EventType(_IntFlag): # pylint:disable=too-few-public-methods
150
150
151
151
class NTPIncompleteError (TimeoutError ):
152
152
"""
153
- NTP synchronize has never completed successfully yet .
153
+ Indicates that NTP synchronization has not yet completed successfully.
154
154
155
155
Raised when an NTP operation cannot complete in non-blocking mode or during retries.
156
-
157
- For transient errors and partial progress. Further NTP calls will retry or
158
- continue to the next step.
156
+ This exception represents transient errors and partial progress. Further NTP calls will
157
+ retry or continue to the next step.
159
158
"""
160
159
161
160
@@ -166,14 +165,14 @@ class NTP: # pylint:disable=too-many-instance-attributes
166
165
167
166
This class uses a simple state machine to manage synchronization:
168
167
- USING_CACHED_REFERENCE (state 3): The default state where the cached time reference is used.
169
- - Transitions to GETTING_SOCKET when the cache expires.
168
+ - Transitions to GETTING_SOCKET when the cache expires.
170
169
- GETTING_SOCKET (state 1): Attempts to perform a DNS lookup for the NTP server.
171
- - Transitions to GETTING_PACKET on success.
172
- - Remains in this state if retries are needed.
170
+ - Transitions to GETTING_PACKET on success.
171
+ - Remains in this state if retries are needed.
173
172
- GETTING_PACKET (state 2): Sends an NTP request and waits for the response.
174
- - Transitions back to USING_CACHED_REFERENCE.
175
- - On failure, any existing cached value will continue to be used until the next scheduled
176
- synchronization.
173
+ - Transitions back to USING_CACHED_REFERENCE.
174
+ - On failure, any existing cached value will continue to be used until the next scheduled
175
+ synchronization.
177
176
178
177
The state transitions are managed by the `_update_time_sync` method, which is called if
179
178
the cached time is expired when `utc_ns` is accessed.
@@ -213,14 +212,16 @@ def __init__( # pylint:disable=too-many-arguments
213
212
:param object socketpool: A socket provider such as CPython's `socket` module.
214
213
:param str server: The domain (url) of the ntp server to query.
215
214
:param int port: The port of the ntp server to query.
216
- :param float tz_offset: Timezone offset in hours from UTC. Only useful for timezone ignorant
217
- CircuitPython. CPython will determine timezone automatically and adjust (so don't use
218
- this.) For example, Pacific daylight savings time is -7.
215
+ :param float tz_offset: Timezone offset in hours from UTC. This applies to both timezone
216
+ ignorant CircuitPython and CPython. CPython is aware of timezones,
217
+ but this code uses methods that do not access that, to be
218
+ consistent with CircuitPython.
219
+ For example, Pacific daylight savings time is -7.
219
220
:param int socket_timeout: UDP socket timeout, in seconds.
220
221
:param int cache_seconds: How many seconds to use a cached result from NTP server
221
- (default 0, which respects NTP server's minimum).
222
+ (default 0, which respects NTP server's minimum).
222
223
:param bool blocking: Determines whether the NTP operations should be blocking or
223
- non-blocking.
224
+ non-blocking.
224
225
"""
225
226
self ._pool : SocketPool = socketpool
226
227
self ._server : str = server
@@ -251,25 +252,25 @@ def __init__( # pylint:disable=too-many-arguments
251
252
@property
252
253
def datetime (self ) -> time .struct_time :
253
254
"""
254
- Time (structure) based on NTP sever time reference. Time synchronization is updated
255
+ Time (structure) based on NTP server time reference. Time synchronization is updated
255
256
if the cache has expired.
256
257
257
- CircuitPython always expects to be working with UTC. CPython though will use it's own
258
+ CircuitPython always expects to be working with UTC. CPython though will use its own
258
259
notion of the current time zone when using localtime. To get those to be consistent,
259
260
localtime is overridden (during import) to use gmtime when running in CPython. That
260
- way this should always return UTC information.
261
+ way this should always return UTC based information.
261
262
262
- :returns time.struct_time: current UTC time in seconds.
263
+ :returns time.struct_time: Current UTC time in seconds.
263
264
"""
264
265
current_time_s = self .utc_ns // NS_PER_SEC # seconds since unix epoch
265
266
return localtime (current_time_s )
266
267
267
268
@property
268
269
def utc_ns (self ) -> int :
269
- """UTC (unix epoch) time in nanoseconds based on NTP sever time reference.
270
+ """UTC (unix epoch) time in nanoseconds based on NTP server time reference.
270
271
Time synchronization updated if the cache has expired.
271
272
272
- :returns: integer number of nanoseconds since the unix epoch (1970-01-01 00:00:00).
273
+ :returns int: Integer number of nanoseconds since the unix epoch (1970-01-01 00:00:00).
273
274
:raises NTPIncompleteError: if no NTP synchronization has been successful yet.
274
275
"""
275
276
if time .monotonic_ns () > self ._next_sync :
@@ -373,26 +374,29 @@ def register_ntp_event_callback(
373
374
374
375
Callbacks can be used to turn off the radio to save power, initiate a network
375
376
connection, or other progress monitoring processes.
376
- EG: wifi.radio.enabled = False or connection_manager.connect()
377
+ EG: `wifi.radio.enabled = False` or `connection_manager.connect()`
378
+
379
+ .. caution::
377
380
378
- NOTE: This implementation does not prevent duplicate registration of the same callback.
379
- All attempts to consistently identify when a callback is already registered have
380
- failed due to the limitations of the current circuitpython implementation. Comparing
381
- the callback value directly, converting to string using str(), or repr(), or to a
382
- number using id() all have cases where an identical callback reference will be
383
- treated as different.
381
+ This implementation does not prevent duplicate registration of the same callback.
382
+ All attempts to consistently identify when a callback is already registered have
383
+ failed due to the limitations of the current CircuitPython implementation. Comparing
384
+ the callback value directly, converting to string using ` str()` , or ` repr()` , or to a
385
+ number using ` id()` all have cases where an identical callback reference will be
386
+ treated as different.
384
387
385
- If the same callback is registered multiple times, with the same event type, it will
386
- be called multiple times when that event type occurs.
388
+ If the same callback is registered multiple times, with the same event type, it will
389
+ be called multiple times when that event type occurs.
387
390
388
391
:param Callable[[IntFlag, int], None] callback: The callback function to register.
389
392
:param IntFlag event_types: The event types that should trigger this callback. This can
390
- be a single event type or a combination of multiple events.
391
- Defaults to EventType.SYNC_COMPLETE.
392
- :raises TypeError: If the event_types argument is not a valid event type or combination of
393
- event types.
393
+ be a single event type or a combination of multiple events.
394
+ Defaults to `EventType.SYNC_COMPLETE`.
395
+ :raises TypeError: If the `event_types` argument is not a valid event type or combination
396
+ of event types.
397
+
398
+ Usage examples::
394
399
395
- Usage examples:
396
400
from adafruit_ntp import NTP, EventType
397
401
ntp = NTP(socketpool)
398
402
@@ -410,9 +414,9 @@ def on_ntp_event(event_type: IntFlag, next_time: int) -> None:
410
414
elif event_type == EventType.LOOKUP_FAILED:
411
415
print(f"DNS lookup failed, need to verify active network connection.")
412
416
413
- # Register for multiple events for a single callback
414
- ntp.register_ntp_event_callback(on_ntp_event, EventType.SYNC_COMPLETE | \\
415
- EventType.SYNC_FAILED | EventType.LOOKUP_FAILED)
417
+ # Register a single callback for multiple events
418
+ ntp.register_ntp_event_callback(on_ntp_event,
419
+ EventType.SYNC_COMPLETE | EventType. SYNC_FAILED | EventType.LOOKUP_FAILED)
416
420
"""
417
421
if not isinstance (event_types , (_IntFlag , int )):
418
422
raise TypeError (f"{ type (event_types )} is not compatible with event types" )
0 commit comments