Skip to content

Commit

Permalink
✨ v2.7.0 (#161)
Browse files Browse the repository at this point in the history
* ✨ v2.7.0

- **IMPORTANCE: Of a service is activated by automation, the sensors will no longer be updated. Therefore, activate the `xplora_watch.see` service with a corresponding interval.**

- Download the photos, videos and voice mails
- if the `www` folder does not exist, it will be created
- float error (latitude/longitude) fixed
- Added license information from opencagedata
- dead code removed
- update geocoder for OpenCageData
- updates user agent

* %s in logging function

* %s in logging function 2.

* Bump pyxplora_api to 2.5.17

* Update coordinator.py

* Update config_flow.py

* Update config_flow.py

* Update coordinator.py

* Update coordinator.py

* Update coordinator.py

* Update coordinator.py

* Update coordinator.py

* Update coordinator.py

* Update hacs.json

* Update ua.json
  • Loading branch information
Ludy87 authored Feb 10, 2023
1 parent 4bd3ef2 commit a6e274c
Show file tree
Hide file tree
Showing 16 changed files with 505 additions and 293 deletions.
2 changes: 1 addition & 1 deletion .github/actions/update_readme.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
with open("countries.md", "w") as text_file:
text_file.write("| country name | country code |\n")
text_file.write("|--------------|--------------|\n")
with open(".github/actions/country.json", "r") as json_file:
with open(".github/actions/country.json") as json_file:
countries = json.loads(json_file.read())
for country in countries:
text_file.write(f"| {country['name']} | {country['code']} |\n")
14 changes: 13 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,8 @@ Xplora® Watch Version 2 integration for Home Assistant

## Features

**IMPORTANCE: Of a service is activated by automation, the sensors will no longer be updated. Therefore, activate the `xplora_watch.see` service with a corresponding interval.**

| Features | Type |
| ---------------------------------------------------------------------------------------------------- | -------------- |
| Battery | Sensor |
Expand Down Expand Up @@ -52,7 +54,7 @@ Copy the xplora_watch [last Releae](https://github.com/Ludy87/xplora_watch/relea
### INSTALLATION mit HACS

1. Ensure that [HACS](https://hacs.xyz/) is installed.
2. Search for and install the "__Xplora® Watch Integration__" integration. [![GitHub release (latest by date)](https://img.shields.io/github/v/release/Ludy87/xplora_watch)](https://github.com/Ludy87/xplora_watch/releases)
2. Search for and install the "**Xplora® Watch Integration**" integration. [![GitHub release (latest by date)](https://img.shields.io/github/v/release/Ludy87/xplora_watch)](https://github.com/Ludy87/xplora_watch/releases)
3. [Configuration for the "Xplora® Watch Version 2" integration is now performed via a config flow as opposed to yaml configuration file.](https://github.com/Ludy87/xplora_watch#basis-configuration)

---
Expand All @@ -73,6 +75,16 @@ Xplora® should now appear as a card under the HA Integrations page with "Config

---

## Downloaded from voice messages, Videos and Images (v2.7.0)

- All voice messages, videos and images are stored in `config/www/{voice|video|image|}`. [#152](https://github.com/Ludy87/xplora_watch/discussions/152)
- The voice message will be downloaded as amr and converted to mp3.
- Videos as mp4
- Images as jpeg
- updated [Markdown Card Sample](https://raw.githubusercontent.com/Ludy87/xplora_watch/main/samples/markdown-card-read-messages.md) [#155](https://github.com/Ludy87/xplora_watch/issues/155)

---

## Delete Messages from App (v2.6.0)

- new service added - delete only app message
Expand Down
5 changes: 3 additions & 2 deletions custom_components/xplora_watch/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@

from .const import DATA_HASS_CONFIG, DOMAIN
from .coordinator import XploraDataUpdateCoordinator
from .helper import create_service_yaml_file
from .helper import create_service_yaml_file, create_www_directory
from .services import async_setup_services, async_unload_services

PLATFORMS = [Platform.BINARY_SENSOR, Platform.DEVICE_TRACKER, Platform.NOTIFY, Platform.SENSOR, Platform.SWITCH]
Expand All @@ -36,11 +36,12 @@ async def async_setup_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool:

hass.data.setdefault(DOMAIN, {})

async_setup_services(hass, coordinator)
await async_setup_services(hass, coordinator)

hass.data[DOMAIN][entry.entry_id] = coordinator
watches = await coordinator.controller.setDevices()

await create_www_directory(hass)
create_service_yaml_file(hass, entry, watches)

for platform in PLATFORMS:
Expand Down
90 changes: 45 additions & 45 deletions custom_components/xplora_watch/config_flow.py
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
)
from homeassistant.core import callback
from homeassistant.data_entry_flow import FlowResult
from homeassistant.helpers import aiohttp_client

from .const import (
CONF_COUNTRY_CODE,
Expand Down Expand Up @@ -74,12 +75,27 @@
}


@callback
async def sign_in(hass: core.HomeAssistant, data: dict[str, Any] = None) -> PXA.PyXploraApi:
controller: PXA.PyXploraApi = PXA.PyXploraApi(
countrycode=data.get(CONF_COUNTRY_CODE, None),
phoneNumber=data.get(CONF_PHONENUMBER, None),
password=data.get(CONF_PASSWORD, ""),
userLang=data.get(CONF_USERLANG, None),
timeZone=data.get(CONF_TIMEZONE, None),
email=data.get(CONF_EMAIL, None),
session=aiohttp_client.async_create_clientsession(hass),
)
await controller.init()
return controller


async def validate_input(hass: core.HomeAssistant, data: dict[str, Any]) -> dict[str, str]:
"""Validate the user input allows us to connect.
Data has the keys from DATA_SCHEMA with values provided by the user.
"""

account = PXA.PyXploraApi()
account = PXA.PyXploraApi(session=aiohttp_client.async_create_clientsession(hass))
await account.init(signup=False)
if not await account.checkEmailOrPhoneExist(
UserContactType.EMAIL if data.get(CONF_EMAIL, None) else UserContactType.PHONE,
Expand All @@ -89,17 +105,8 @@ async def validate_input(hass: core.HomeAssistant, data: dict[str, Any]) -> dict
):
raise PhoneOrEmailFail()

account = PXA.PyXploraApi(
countrycode=data.get(CONF_COUNTRY_CODE, None),
phoneNumber=data.get(CONF_PHONENUMBER, None),
password=data[CONF_PASSWORD],
userLang=data[CONF_USERLANG],
timeZone=data[CONF_TIMEZONE],
email=data.get(CONF_EMAIL, None),
)

try:
await account.init()
await sign_in(hass=hass, data=data)
except LoginError as err:
raise LoginError(err.error_message)

Expand Down Expand Up @@ -157,7 +164,6 @@ async def async_step_user_phone(self, user_input: dict[str, Any] | None = None)
"""Handle the initial step."""
errors: dict[str, str] = {}
if user_input is not None:

unique_id = f"{user_input[CONF_PHONENUMBER]}"

await self.async_set_unique_id(unique_id)
Expand Down Expand Up @@ -187,7 +193,6 @@ async def async_step_user_email(self, user_input: dict[str, Any] | None = None)
"""Handle the initial step."""
errors: dict[str, str] = {}
if user_input is not None:

unique_id = f"{user_input[CONF_EMAIL]}"

await self.async_set_unique_id(unique_id)
Expand Down Expand Up @@ -222,38 +227,8 @@ def __init__(self, config_entry: ConfigEntry) -> None:
super().__init__()
self.config_entry = config_entry

async def async_step_init(self, user_input: dict[str, Any] | None = None) -> FlowResult:
"""Handle options flow."""
errors: dict[str, str] = {}
controller = PXA.PyXploraApi(
self.config_entry.data.get(CONF_COUNTRY_CODE, None),
self.config_entry.data.get(CONF_PHONENUMBER, None),
self.config_entry.data.get(CONF_PASSWORD, None),
self.config_entry.data.get(CONF_USERLANG, None),
self.config_entry.data.get(CONF_TIMEZONE, None),
email=self.config_entry.data.get(CONF_EMAIL, None),
)
await controller.init()
watches = await controller.setDevices()
_options = self.config_entry.options

schema = OrderedDict()
schema[vol.Required(CONF_WATCHES, default=_options.get(CONF_WATCHES, watches))] = cv.multi_select(watches)
i = 1
for watch in watches:
schema[vol.Optional(f"{CONF_WATCHES}_{i}", default=_options.get(f"{CONF_WATCHES}_{i}", watch))] = cv.string
i += 1

language = _options.get(CONF_LANGUAGE, self.config_entry.data.get(CONF_LANGUAGE, DEFAULT_LANGUAGE))

signin_typ = [
SIGNIN.get(language, DEFAULT_LANGUAGE).get(CONF_EMAIL)
if CONF_EMAIL in self.config_entry.data
else SIGNIN.get(language, DEFAULT_LANGUAGE).get(CONF_PHONENUMBER)
]

_home_zone = self.hass.states.get(HOME).attributes
options = vol.Schema(
def get_options(self, signin_typ, schema, language, _options, _home_zone):
return vol.Schema(
{
vol.Optional(CONF_SIGNIN_TYP, default=signin_typ[0]): vol.In(signin_typ),
**schema,
Expand Down Expand Up @@ -283,6 +258,31 @@ async def async_step_init(self, user_input: dict[str, Any] | None = None) -> Flo
}
)

async def async_step_init(self, user_input: dict[str, Any] | None = None) -> FlowResult:
"""Handle options flow."""
errors: dict[str, str] = {}
controller = await sign_in(self.hass, self.config_entry.data)
watches = await controller.setDevices()
_options = self.config_entry.options

schema = OrderedDict()
schema[vol.Required(CONF_WATCHES, default=_options.get(CONF_WATCHES, watches))] = cv.multi_select(watches)
i = 1
for watch in watches:
schema[vol.Optional(f"{CONF_WATCHES}_{i}", default=_options.get(f"{CONF_WATCHES}_{i}", watch))] = cv.string
i += 1

language = _options.get(CONF_LANGUAGE, self.config_entry.data.get(CONF_LANGUAGE, DEFAULT_LANGUAGE))

signin_typ = [
SIGNIN.get(language, DEFAULT_LANGUAGE).get(CONF_EMAIL)
if CONF_EMAIL in self.config_entry.data
else SIGNIN.get(language, DEFAULT_LANGUAGE).get(CONF_PHONENUMBER)
]

_home_zone = self.hass.states.get(HOME).attributes
options = self.get_options(signin_typ, schema, language, _options, _home_zone)

if user_input is not None:
errors = validate_options_input(user_input)

Expand Down
Loading

0 comments on commit a6e274c

Please sign in to comment.