Skip to content

Commit

Permalink
wip
Browse files Browse the repository at this point in the history
  • Loading branch information
bj00rn committed Nov 17, 2022
1 parent e7bd8c5 commit 240dfb6
Show file tree
Hide file tree
Showing 23 changed files with 318 additions and 240 deletions.
4 changes: 2 additions & 2 deletions .devcontainer/configuration.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ default_config:
logger:
default: info
logs:
custom_components.integration_blueprint: debug
custom_components.saleryd_ftx: debug

# If you need to debug uncomment the line below (doc: https://www.home-assistant.io/integrations/debugpy/)
# debugpy:
debugpy:
2 changes: 1 addition & 1 deletion .devcontainer/devcontainer.json
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
// See https://aka.ms/vscode-remote/devcontainer.json for format details.
{
"image": "ghcr.io/ludeeus/devcontainer/integration:stable",
"name": "Blueprint integration development",
"name": "SalerydLoke integration development",
"context": "..",
"appPort": [
"9123:8123"
Expand Down
68 changes: 34 additions & 34 deletions .vscode/launch.json
Original file line number Diff line number Diff line change
@@ -1,35 +1,35 @@
{
// For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
"version": "0.2.0",
"configurations": [
{
// Example of attaching to local debug server
"name": "Python: Attach Local",
"type": "python",
"request": "attach",
"port": 5678,
"host": "localhost",
"pathMappings": [
{
"localRoot": "${workspaceFolder}",
"remoteRoot": "."
}
]
},
{
// Example of attaching to my production server
"name": "Python: Attach Remote",
"type": "python",
"request": "attach",
"port": 5678,
"host": "homeassistant.local",
"pathMappings": [
{
"localRoot": "${workspaceFolder}",
"remoteRoot": "/usr/src/homeassistant"
}
]
}
]
}
// For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
"version": "0.2.0",
"configurations": [
{
// Example of attaching to local debug server
"name": "Python: Attach Local",
"type": "python",
"request": "attach",
"port": 5678,
"host": "localhost",
"justMyCode": false,
"pathMappings": [
{
"localRoot": "${workspaceFolder}",
"remoteRoot": "."
}
]
},
{
// Example of attaching to my production server
"name": "Python: Attach Remote",
"type": "python",
"request": "attach",
"port": 5678,
"host": "homeassistant.local",
"pathMappings": [
{
"localRoot": "${workspaceFolder}",
"remoteRoot": "/usr/src/homeassistant"
}
]
}
]
}
75 changes: 0 additions & 75 deletions custom_components/integration_blueprint/api.py

This file was deleted.

31 changes: 0 additions & 31 deletions custom_components/integration_blueprint/translations/fr.json

This file was deleted.

31 changes: 0 additions & 31 deletions custom_components/integration_blueprint/translations/nb.json

This file was deleted.

Original file line number Diff line number Diff line change
Expand Up @@ -14,11 +14,10 @@
from homeassistant.helpers.aiohttp_client import async_get_clientsession
from homeassistant.helpers.update_coordinator import DataUpdateCoordinator, UpdateFailed

from .api import IntegrationBlueprintApiClient
from .api import SalerydLokeApiClient

from .const import (
CONF_PASSWORD,
CONF_USERNAME,
CONF_WEBSOCKET_URL,
DOMAIN,
PLATFORMS,
STARTUP_MESSAGE,
Expand All @@ -40,13 +39,12 @@ async def async_setup_entry(hass: HomeAssistant, entry: ConfigEntry):
hass.data.setdefault(DOMAIN, {})
_LOGGER.info(STARTUP_MESSAGE)

username = entry.data.get(CONF_USERNAME)
password = entry.data.get(CONF_PASSWORD)
url = entry.data.get(CONF_WEBSOCKET_URL)

session = async_get_clientsession(hass)
client = IntegrationBlueprintApiClient(username, password, session)
client = SalerydLokeApiClient(url, session)

coordinator = BlueprintDataUpdateCoordinator(hass, client=client)
coordinator = SalerydLokeDataUpdateCoordinator(hass, client=client)
await coordinator.async_refresh()

if not coordinator.last_update_success:
Expand All @@ -65,12 +63,10 @@ async def async_setup_entry(hass: HomeAssistant, entry: ConfigEntry):
return True


class BlueprintDataUpdateCoordinator(DataUpdateCoordinator):
class SalerydLokeDataUpdateCoordinator(DataUpdateCoordinator):
"""Class to manage fetching data from the API."""

def __init__(
self, hass: HomeAssistant, client: IntegrationBlueprintApiClient
) -> None:
def __init__(self, hass: HomeAssistant, client: SalerydLokeApiClient) -> None:
"""Initialize."""
self.api = client
self.platforms = []
Expand Down
120 changes: 120 additions & 0 deletions custom_components/saleryd_ftx/api.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,120 @@
"""Sample API Client."""
import logging
import asyncio
import socket
from typing import Optional
import aiohttp
import async_timeout
from homeassistant.exceptions import IntegrationError

TIMEOUT = 10
SAMPLE_TIMEOUT = 5


_LOGGER: logging.Logger = logging.getLogger(__package__)

HEADERS = {"Content-type": "application/json; charset=UTF-8"}


class SalerydLokeApiClient:
"""Api Client"""

def __init__(self, url, session: aiohttp.ClientSession) -> None:
"""Sample API Client."""
self._url = url
self._session = session

async def async_get_data(self) -> dict:
"""Get data from the API."""
return await self.api_wrapper("ws_get", self._url)

async def async_send_command(self, command):
return await self.api_wrapper("ws_set", self._url, command)

async def async_set_title(self, value: str) -> None:
"""Get data from the API."""
url = "https://jsonplaceholder.typicode.com/posts/1"
await self.api_wrapper("patch", url, data={"title": value}, headers=HEADERS)

def parse_message(self, msg):
"""parse socket message"""
parsed = None

try:
if msg[0] == "#":
if msg[1] == "?" or msg[1] == "$":
# ignore acks
_LOGGER.debug("Ignoring message %s", msg)
return
# parse response
value = msg[1::].split(":")[1].strip()
key = msg[1::].split(":")[0]
parsed = (key, value)
except Exception as exc:
_LOGGER.warning("Failed to parse message %s", msg)
raise ParseError() from exc
return parsed

async def api_wrapper(
self, method: str, url: str, data: dict = dict, headers: dict = dict
) -> dict:
"""Get information from the API."""

try:
async with async_timeout.timeout(TIMEOUT):
if method == "ws_get":
state = {}
async with self._session.ws_connect(self._url) as websocket:
_LOGGER.debug("Connected to %s", url)
command = "#\r"
_LOGGER.debug("Outgoing message %s", command)
await websocket.send_str(command)
nsamples = 50
count = 0
_LOGGER.debug("Starting sampling of %d messages", nsamples)
async for msg in websocket:
try:
_LOGGER.debug("Incoming message [%d]: %s", count, msg)
parsed = self.parse_message(msg.data)
key, value = parsed
state[key] = value
except ParseError:
pass
count = count + 1
if count >= nsamples:
_LOGGER.debug(
"Finished sampling, got %d messages", count
)
_LOGGER.debug("Got state %s", state)
return state
elif method == "ws_set":
async with self._session.ws_connect(
self._url, headers=headers
) as websocket:
await websocket.send_str(f"{data}\r")

except asyncio.TimeoutError as exception:
_LOGGER.error(
"Timeout error fetching information from %s - %s",
url,
exception,
)

except (KeyError, TypeError) as exception:
_LOGGER.error(
"Error parsing information from %s - %s",
url,
exception,
)
except (aiohttp.ClientError, socket.gaierror) as exception:
_LOGGER.error(
"Error fetching information from %s - %s",
url,
exception,
)
except Exception as exception: # pylint: disable=broad-except
_LOGGER.error("Something really wrong happened! - %s", exception)


class ParseError(IntegrationError):
pass
Loading

0 comments on commit 240dfb6

Please sign in to comment.