python-linkplay 0.0.12__tar.gz → 0.0.14__tar.gz

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.
Files changed (23) hide show
  1. {python_linkplay-0.0.12/src/python_linkplay.egg-info → python_linkplay-0.0.14}/PKG-INFO +1 -1
  2. python_linkplay-0.0.14/src/linkplay/__version__.py +1 -0
  3. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/src/linkplay/bridge.py +17 -1
  4. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/src/linkplay/consts.py +3 -0
  5. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/src/linkplay/controller.py +24 -19
  6. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/src/linkplay/utils.py +0 -2
  7. {python_linkplay-0.0.12 → python_linkplay-0.0.14/src/python_linkplay.egg-info}/PKG-INFO +1 -1
  8. python_linkplay-0.0.12/src/linkplay/__version__.py +0 -1
  9. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/LICENSE +0 -0
  10. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/README.md +0 -0
  11. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/pyproject.toml +0 -0
  12. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/setup.cfg +0 -0
  13. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/setup.py +0 -0
  14. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/src/linkplay/__init__.py +0 -0
  15. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/src/linkplay/__main__.py +0 -0
  16. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/src/linkplay/discovery.py +0 -0
  17. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/src/linkplay/endpoint.py +0 -0
  18. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/src/linkplay/exceptions.py +0 -0
  19. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/src/python_linkplay.egg-info/SOURCES.txt +0 -0
  20. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/src/python_linkplay.egg-info/dependency_links.txt +0 -0
  21. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/src/python_linkplay.egg-info/not-zip-safe +0 -0
  22. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/src/python_linkplay.egg-info/requires.txt +0 -0
  23. {python_linkplay-0.0.12 → python_linkplay-0.0.14}/src/python_linkplay.egg-info/top_level.txt +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: python_linkplay
3
- Version: 0.0.12
3
+ Version: 0.0.14
4
4
  Summary: A Python Library for Seamless LinkPlay Device Control
5
5
  Author: Velleman Group nv
6
6
  License: MIT
@@ -0,0 +1 @@
1
+ __version__ = '0.0.14'
@@ -4,6 +4,7 @@ from typing import Any
4
4
 
5
5
  from linkplay.consts import (
6
6
  INPUT_MODE_MAP,
7
+ LOGGER,
7
8
  PLAY_MODE_SEND_MAP,
8
9
  ChannelType,
9
10
  DeviceAttribute,
@@ -258,11 +259,13 @@ class LinkPlayBridge:
258
259
  endpoint: LinkPlayEndpoint
259
260
  device: LinkPlayDevice
260
261
  player: LinkPlayPlayer
262
+ multiroom: LinkPlayMultiroom | None
261
263
 
262
264
  def __init__(self, *, endpoint: LinkPlayEndpoint):
263
265
  self.endpoint = endpoint
264
266
  self.device = LinkPlayDevice(self)
265
267
  self.player = LinkPlayPlayer(self)
268
+ self.multiroom = None
266
269
 
267
270
  def __str__(self) -> str:
268
271
  if self.device.name == "":
@@ -276,14 +279,20 @@ class LinkPlayBridge:
276
279
  "endpoint": self.endpoint.to_dict(),
277
280
  "device": self.device.to_dict(),
278
281
  "player": self.player.to_dict(),
282
+ "multiroom": self.multiroom.to_dict() if self.multiroom else None,
279
283
  }
280
284
 
281
285
  async def json_request(self, command: str) -> dict[str, str]:
282
286
  """Performs a GET request on the given command and returns the result as a JSON object."""
283
- return await self.endpoint.json_request(command)
287
+ LOGGER.debug(str.format("Request {} at {}", command, self.endpoint))
288
+ response = await self.endpoint.json_request(command)
289
+ LOGGER.debug(str.format("Response {}: {}", command, response))
290
+ return response
284
291
 
285
292
  async def request(self, command: str) -> None:
286
293
  """Performs a GET request on the given command and verifies the result."""
294
+
295
+ LOGGER.debug(str.format("Request command at {}: {}", self.endpoint, command))
287
296
  await self.endpoint.request(command)
288
297
 
289
298
 
@@ -298,6 +307,13 @@ class LinkPlayMultiroom:
298
307
  self.leader = leader
299
308
  self.followers = []
300
309
 
310
+ def to_dict(self):
311
+ """Return the state of the LinkPlayMultiroom."""
312
+ return {
313
+ "leader": self.leader.to_dict(),
314
+ "followers": [follower.to_dict() for follower in self.followers],
315
+ }
316
+
301
317
  async def update_status(self, bridges: list[LinkPlayBridge]) -> None:
302
318
  """Updates the multiroom status."""
303
319
  properties: dict[Any, Any] = await self.leader.json_request(
@@ -1,5 +1,8 @@
1
+ import logging
1
2
  from enum import IntFlag, StrEnum
2
3
 
4
+ LOGGER = logging.getLogger("linkplay")
5
+
3
6
  API_ENDPOINT: str = "{}/httpapi.asp?command={}"
4
7
  API_TIMEOUT: int = 2
5
8
  UNKNOWN_TRACK_PLAYING: str = "Unknown"
@@ -40,31 +40,36 @@ class LinkPlayController:
40
40
  async def discover_multirooms(self) -> None:
41
41
  """Attempts to discover multirooms on the local network."""
42
42
 
43
+ # Find and update existing multirooms
44
+ multirooms = [bridge.multiroom for bridge in self.bridges if bridge.multiroom]
45
+
46
+ removed_multirooms = []
47
+ for multiroom in multirooms:
48
+ for follower in multiroom.followers:
49
+ follower.multiroom = None
50
+ await multiroom.update_status(self.bridges)
51
+ if len(multiroom.followers) > 0:
52
+ for follower in multiroom.followers:
53
+ follower.multiroom = multiroom
54
+ else:
55
+ multiroom.leader.multiroom = None
56
+ removed_multirooms.append(multiroom)
57
+
43
58
  # Create new multirooms from new bridges
44
- new_multirooms = []
45
59
  for bridge in self.bridges:
46
- has_multiroom = any(
47
- multiroom for multiroom in self.multirooms if multiroom.leader == bridge
48
- )
49
-
50
- if has_multiroom:
60
+ if bridge.multiroom:
51
61
  continue
52
62
 
53
63
  multiroom = LinkPlayMultiroom(bridge)
54
64
  await multiroom.update_status(self.bridges)
55
65
  if len(multiroom.followers) > 0:
56
- new_multirooms.append(multiroom)
57
-
58
- # Update existing multirooms
59
- for multiroom in self.multirooms:
60
- await multiroom.update_status(self.bridges)
66
+ multirooms.append(multiroom)
67
+ bridge.multiroom = multiroom
68
+ for follower in multiroom.followers:
69
+ follower.multiroom = multiroom
61
70
 
62
- # Remove multirooms if they have no followers
63
- empty_multirooms = [
64
- multiroom for multiroom in self.multirooms if not multiroom.followers
65
- ]
66
- for empty_multiroom in empty_multirooms:
67
- self.multirooms.remove(empty_multiroom)
71
+ # Remove multirooms with no followers
72
+ multirooms = [item for item in multirooms if item not in removed_multirooms]
68
73
 
69
- # Add new multirooms
70
- self.multirooms.extend(new_multirooms)
74
+ # Update multirooms in controller
75
+ self.multirooms = multirooms
@@ -24,8 +24,6 @@ from linkplay.consts import (
24
24
  )
25
25
  from linkplay.exceptions import LinkPlayRequestException
26
26
 
27
- _LOGGER = logging.getLogger(__name__)
28
-
29
27
 
30
28
  async def session_call_api(endpoint: str, session: ClientSession, command: str) -> str:
31
29
  """Calls the LinkPlay API and returns the result as a string.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: python_linkplay
3
- Version: 0.0.12
3
+ Version: 0.0.14
4
4
  Summary: A Python Library for Seamless LinkPlay Device Control
5
5
  Author: Velleman Group nv
6
6
  License: MIT
@@ -1 +0,0 @@
1
- __version__ = '0.0.12'