Skip to content

Commit

Permalink
Merge branch 'dev'
Browse files Browse the repository at this point in the history
  • Loading branch information
gazoodle committed Feb 26, 2025
2 parents 2d79c4f + e278e30 commit 8d32dfc
Show file tree
Hide file tree
Showing 14 changed files with 384 additions and 253 deletions.
64 changes: 24 additions & 40 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -19,15 +19,24 @@ This library is hosted on PyPI and can be installed with the following command-l

`pip install geckolib`

# CUI sample

_Work In Progress_

There is a complete async sample which uses the full API and shows how to
client the SpaManager class, react to events, discover devices and so on.
This can be run using `python3 -m geckolib cui`. On Windows you will need to
install the `curses` library.

It can also be used to diagnose issues with your Gecko client, test drive your
spa and investigate anything that the previous GeckoShell was able to do.

# GeckoShell usage

Once the library is installed, you should be able to start a Python interpreter session
by using the command `python3`, then executing the following commands
Once the library is installed, you should be able to start a Gecko shell with the
command `python3 -m geckolib shell`

```python
>>> from geckolib import GeckoShell
>>> GeckoShell.run()


<Disclaimer>
:
Expand Down Expand Up @@ -101,38 +110,12 @@ Spa$
```

If you want to get some diagnostics you can enable file logging at the start of the session

```python
>>> from geckolib import GeckoShell
>>> GeckoShell.run(["logfile client.log"])

:
:

```

or it can be used later after you've connected to your spa with the `logfile` command

```
Spa$ logfile client.log
```

The file `client.log` will contain diagnostic information that may be useful
for tracking down issues
Diagnostics are created for each run, you can find them in the folder where the shell
was started in the file `shell.log`

If you want to start the client and point it at a specific IP address (maybe you have your SPA on a different subnet), you can issue the discovery command as part of the launch parameters

```python
>>> from geckolib import GeckoShell
>>> GeckoShell.run(["logfile client.log", "discover 192.168.1.2"])

:
:

```
`python3 -m geckolib shell "discover 192.168.1.2"`

# Simulator Usage

Expand Down Expand Up @@ -259,12 +242,6 @@ Turning pump 1 off
```

# Complete sample

There is also a complete async sample which can be found in the repo under
the /sample folder. This can be run using `python3 complete.py`. Full path
https://github.com/gazoodle/geckolib/tree/main/sample. Only works on Linux

# Home Assistant integration

The best example of use is in the Home Assistant integration which can be
Expand Down Expand Up @@ -301,6 +278,13 @@ https://www.gnu.org/licenses/gpl-3.0.html
- When there are two spas loaded, the ping frequency seems to be too high. Is this related to the
shared global config?
- Expose the master timeouts as configurations and the ud timeouts as controls
- Keep looking to see if there is a time sync mechanism

## Done/Fixed in 1.0.6
- Fix error in pump is_on function if the state accessor wasn't created.
- Bubble generator now tolerant of AuxAsBubbleGen being present and turned on, but no output set to AUX
- Moving simulator, shell and CUI support to module main command.
- CUI sample is work in progress, check-in needed for bug fix!

## Done/Fixed in 1.0.5
- Fix DIV/0 in inMix RGB scaler
Expand Down
80 changes: 0 additions & 80 deletions sample/abstract_display.py

This file was deleted.

58 changes: 0 additions & 58 deletions sample/complete.py

This file was deleted.

8 changes: 0 additions & 8 deletions sample/context_sample.py

This file was deleted.

3 changes: 2 additions & 1 deletion src/geckolib/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,7 @@
)
from .spa_events import GeckoSpaEvent
from .spa_state import GeckoSpaState
from .utils import GeckoShell, GeckoSimulator, GeckoSnapshot
from .utils import CUI, GeckoShell, GeckoSimulator, GeckoSnapshot

# Module logger, uses the library name (at this time it was geckolib) and it
# is silent unless required ...
Expand All @@ -69,6 +69,7 @@
__version__ = VERSION

__all__ = [
"CUI",
"VERSION",
"AsyncTasks",
"GeckoAsyncFacade",
Expand Down
41 changes: 41 additions & 0 deletions src/geckolib/__main__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
"""Main module. Supports python -m geckolib syntax."""

# ruff: noqa: T201

import logging
from pathlib import Path
from sys import argv

from geckolib import CUI, GeckoShell, GeckoSimulator


def usage() -> None:
"""Print usage."""
print("Usage: python3 -m geckolib <shell|simulator|cui> [client args]")


def install_logging(command: str) -> None:
"""Everyone needs logging, you say when, you say where, you say how much."""
Path(f"{command}.log").unlink(True) # noqa: FBT003
file_logger = logging.FileHandler(f"{command}.log")
file_logger.setLevel(logging.DEBUG)
file_logger.setFormatter(
logging.Formatter("%(asctime)s %(name)s %(levelname)s %(message)s")
)
logging.getLogger().addHandler(file_logger)
logging.getLogger().setLevel(logging.DEBUG)


if len(argv) == 1:
usage()
elif argv[1] == "shell":
install_logging(argv[1])
GeckoShell.run(argv[2:])
elif argv[1] == "simulator":
install_logging(argv[1])
GeckoSimulator.run(["load ../tests/snapshots/default.snapshot", "start"] + argv[2:])
elif argv[1] == "cui":
install_logging(argv[1])
CUI.launch()
else:
usage()
2 changes: 1 addition & 1 deletion src/geckolib/_version.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
"""Single module version."""

VERSION = "1.0.5"
VERSION = "1.0.6"
2 changes: 1 addition & 1 deletion src/geckolib/automation/bubblegen.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ class GeckoBubbleGenerator(GeckoPump):
def __init__(self, facade: GeckoAsyncFacade) -> None:
"""Initialize the bubble generator."""
super().__init__(facade, "Bubble Generator", "Aux")
if "AuxAsBubbleGen" in self.facade.spa.accessors:
if self.is_available and "AuxAsBubbleGen" in self.facade.spa.accessors:
self.set_availability(
is_available=self.facade.spa.accessors["AuxAsBubbleGen"].value
)
2 changes: 1 addition & 1 deletion src/geckolib/automation/pump.py
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ def __init__(self, facade: GeckoAsyncFacade, name: str, key: str) -> None:
super().__init__(facade, name, key)
self.device_class = GeckoConstants.DEVICE_CLASS_PUMP
self.pump_type = GeckoPump.PumpType.NONE
self._state_accessor: GeckoStructAccessor
self._state_accessor: GeckoStructAccessor | None = None

if key in facade.spa.struct.connections:
self.pump_type = GeckoPump.PumpType.SINGLE_SPEED
Expand Down
3 changes: 2 additions & 1 deletion src/geckolib/utils/__init__.py
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
"""GeckoLib utilities."""

from .async_command import AsyncCmd
from .cui import CUI
from .shell import GeckoShell
from .simulator import GeckoSimulator
from .snapshot import GeckoSnapshot

__all__ = ["AsyncCmd", "GeckoShell", "GeckoSimulator", "GeckoSnapshot"]
__all__ = ["CUI", "AsyncCmd", "GeckoShell", "GeckoSimulator", "GeckoSnapshot"]
5 changes: 5 additions & 0 deletions src/geckolib/utils/cui/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
"""Geckolib cui utils."""

from .cui import CUI

__all__ = ["CUI"]
Loading

0 comments on commit 8d32dfc

Please sign in to comment.