-
-
Notifications
You must be signed in to change notification settings - Fork 26
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Adds Config flow renames `icon_tomorrow` to `icon_soon` adds `days_as_soon` config option
- Loading branch information
1 parent
cb042d0
commit 05bbeb6
Showing
10 changed files
with
466 additions
and
52 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,32 @@ | ||
name: Release | ||
|
||
on: | ||
release: | ||
types: [published] | ||
|
||
jobs: | ||
release: | ||
name: Prepare release | ||
runs-on: ubuntu-latest | ||
steps: | ||
- uses: actions/checkout@v1 | ||
- name: "Set version numbmer" | ||
run: | | ||
sed -i '/VERSION = /c\VERSION = "${{ github.ref }}"' custom_components/anniversaries/const.py | ||
sed -i 's|refs/heads/||' custom_components/anniversaries/const.py | ||
sed -i 's|refs/tags/||' custom_components/anniversaries/const.py | ||
# Pack the HACS dir as a zip and upload to the release | ||
- name: ZIP Anniversaries Dir | ||
run: | | ||
cd /home/runner/work/Anniversaries/Anniversaries/custom_components/anniversaries | ||
zip anniversaries.zip -r ./ | ||
- name: Upload zip to release | ||
uses: svenstaro/upload-release-action@v1-release | ||
|
||
with: | ||
repo_token: ${{ secrets.GITHUB_TOKEN }} | ||
file: /home/runner/work/Anniversaries/Anniversaries/custom_components/anniversaries/anniversaries.zip | ||
asset_name: anniversaries.zip | ||
tag: ${{ github.ref }} | ||
overwrite: true |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,42 @@ | ||
{ | ||
"config": { | ||
"title": "Anniversaries", | ||
"step": { | ||
"user": { | ||
"title": "Anniversaries", | ||
"description": "Enter the sensor name and configure sensor parameters. More info on https://github.com/pinkywafer/Anniversaries", | ||
"data": { | ||
"name": "Friendly name", | ||
"date": "First Date (yyyy-mm-dd)", | ||
"icon_normal": "Icon", | ||
"icon_today": "Icon when anniversary is today", | ||
"days_as_soon": "Number of Days to consider soon", | ||
"icon_soon": "Icon when anniversary is soon", | ||
"date_format": "Date format (see http://strftime.org/)" | ||
} | ||
} | ||
}, | ||
"error": { | ||
"invalid_date": "The date is not valid. Please enter a valid 'YYYY-MM-DD' date" | ||
} | ||
}, | ||
"options": { | ||
"step": { | ||
"init": { | ||
"title": "Anniversaries", | ||
"description": "Change sensor parameters. More info on https://github.com/pinkywafer/Anniversaries", | ||
"data": { | ||
"date": "First Date (yyyy-mm-dd)", | ||
"icon_normal": "Icon", | ||
"icon_today": "Icon when anniversary is today", | ||
"days_as_soon": "Number of Days to consider soon", | ||
"icon_soon": "Icon when anniversary is soon", | ||
"date_format": "Date format (see http://strftime.org/)" | ||
} | ||
} | ||
}, | ||
"error": { | ||
"invalid_date": "The date is not valid. Please enter a valid 'YYYY-MM-DD' date" | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1 +1,95 @@ | ||
"""Anniversaries Sensor""" | ||
"""Anniversaries Platform""" | ||
import os | ||
from datetime import timedelta | ||
import logging | ||
from homeassistant import config_entries | ||
import voluptuous as vol | ||
import homeassistant.helpers.config_validation as cv | ||
from homeassistant.helpers import discovery | ||
from homeassistant.util import Throttle | ||
from .sensor import anniversaries | ||
|
||
from integrationhelper.const import CC_STARTUP_VERSION | ||
|
||
from homeassistant.const import CONF_NAME | ||
|
||
from .const import ( | ||
CONF_SENSORS, | ||
CONF_ENABLED, | ||
DEFAULT_NAME, | ||
DOMAIN_DATA, | ||
DOMAIN, | ||
ISSUE_URL, | ||
PLATFORM, | ||
VERSION, | ||
CONFIG_SCHEMA, | ||
) | ||
|
||
#MIN_TIME_BETWEEN_UPDATES = timedelta(seconds=30) | ||
|
||
_LOGGER = logging.getLogger(__name__) | ||
|
||
|
||
async def async_setup(hass, config): | ||
"""Set up this component using YAML.""" | ||
if config.get(DOMAIN) is None: | ||
# config flow setup | ||
return True | ||
|
||
# log startup message | ||
_LOGGER.info( | ||
CC_STARTUP_VERSION.format(name=DOMAIN, version=VERSION, issue_link=ISSUE_URL) | ||
) | ||
platform_config = config[DOMAIN].get(CONF_SENSORS, {}) | ||
|
||
# If platform is not enabled, skip. | ||
if not platform_config: | ||
return False | ||
|
||
for entry in platform_config: | ||
hass.async_create_task( | ||
discovery.async_load_platform(hass, PLATFORM, DOMAIN, entry, config) | ||
) | ||
hass.async_create_task( | ||
hass.config_entries.flow.async_init( | ||
DOMAIN, context={"source": config_entries.SOURCE_IMPORT}, data={} | ||
) | ||
) | ||
return True | ||
|
||
|
||
async def async_setup_entry(hass, config_entry): | ||
"""Set up this integration using UI.""" | ||
if config_entry.source == config_entries.SOURCE_IMPORT: | ||
# set up using YAML | ||
hass.async_create_task(hass.config_entries.async_remove(config_entry.entry_id)) | ||
return False | ||
# log startup message | ||
_LOGGER.info( | ||
CC_STARTUP_VERSION.format(name=DOMAIN, version=VERSION, issue_link=ISSUE_URL) | ||
) | ||
config_entry.options = config_entry.data | ||
config_entry.add_update_listener(update_listener) | ||
# Add sensor | ||
hass.async_add_job( | ||
hass.config_entries.async_forward_entry_setup(config_entry, PLATFORM) | ||
) | ||
return True | ||
|
||
|
||
async def async_remove_entry(hass, config_entry): | ||
"""Handle removal of an entry.""" | ||
try: | ||
await hass.config_entries.async_forward_entry_unload(config_entry, PLATFORM) | ||
_LOGGER.info( | ||
"Successfully removed sensor from the Anniversaries integration" | ||
) | ||
except ValueError: | ||
pass | ||
|
||
|
||
async def update_listener(hass, entry): | ||
"""Update listener.""" | ||
entry.data = entry.options | ||
await hass.config_entries.async_forward_entry_unload(entry, PLATFORM) | ||
hass.async_add_job(hass.config_entries.async_forward_entry_setup(entry, PLATFORM)) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,138 @@ | ||
""" config flow """ | ||
from collections import OrderedDict | ||
import logging | ||
from homeassistant.core import callback | ||
import voluptuous as vol | ||
import homeassistant.helpers.config_validation as cv | ||
from homeassistant import config_entries | ||
from datetime import datetime | ||
import uuid | ||
|
||
from .const import ( | ||
DOMAIN, | ||
DEFAULT_ICON_NORMAL, | ||
DEFAULT_ICON_SOON, | ||
DEFAULT_ICON_TODAY, | ||
DEFAULT_DATE_FORMAT, | ||
DEFAULT_SOON, | ||
CONF_SENSOR, | ||
CONF_ENABLED, | ||
CONF_ICON_NORMAL, | ||
CONF_ICON_TODAY, | ||
CONF_ICON_SOON, | ||
CONF_DATE, | ||
CONF_DATE_FORMAT, | ||
CONF_SENSORS, | ||
CONF_SOON, | ||
) | ||
|
||
from homeassistant.const import CONF_NAME | ||
|
||
_LOGGER = logging.getLogger(__name__) | ||
|
||
|
||
@config_entries.HANDLERS.register(DOMAIN) | ||
class AnniversariesFlowHandler(config_entries.ConfigFlow): | ||
CONNECTION_CLASS = config_entries.CONN_CLASS_LOCAL_POLL | ||
|
||
def __init__(self): | ||
self._errors = {} | ||
self._data = {} | ||
self._data["unique_id"] = str(uuid.uuid4()) | ||
|
||
async def async_step_user(self, user_input=None): # pylint: disable=unused-argument | ||
self._errors = {} | ||
if user_input is not None: | ||
self._data.update(user_input) | ||
if is_not_date(user_input[CONF_DATE]): | ||
self._errors["base"] = "invalid_date" | ||
if self._errors == {}: | ||
return self.async_create_entry(title=self._data["name"], data=self._data) | ||
return await self._show_user_form(user_input) | ||
|
||
async def _show_user_form(self, user_input): | ||
name = "" | ||
date = "" | ||
icon_normal = DEFAULT_ICON_NORMAL | ||
icon_soon = DEFAULT_ICON_SOON | ||
icon_today = DEFAULT_ICON_TODAY | ||
date_format = DEFAULT_DATE_FORMAT | ||
days_as_soon = DEFAULT_SOON | ||
if user_input is not None: | ||
if CONF_NAME in user_input: | ||
name = user_input[CONF_NAME] | ||
if CONF_DATE in user_input: | ||
date = user_input[CONF_DATE] | ||
if CONF_ICON_NORMAL in user_input: | ||
icon_normal = user_input[CONF_ICON_NORMAL] | ||
if CONF_ICON_SOON in user_input: | ||
icon_soon = user_input[CONF_ICON_SOON] | ||
if CONF_ICON_TODAY in user_input: | ||
icon_today = user_input[CONF_ICON_TODAY] | ||
if CONF_DATE_FORMAT in user_input: | ||
date_format = user_input[CONF_DATE_FORMAT] | ||
data_schema = OrderedDict() | ||
data_schema[vol.Required(CONF_NAME, default=name)] = str | ||
data_schema[vol.Required(CONF_DATE, default=date)] = str | ||
data_schema[vol.Required(CONF_ICON_NORMAL, default=icon_normal)] = str | ||
data_schema[vol.Required(CONF_ICON_TODAY, default=icon_today)] = str | ||
data_schema[vol.Required(CONF_SOON, default=days_as_soon)] = int | ||
data_schema[vol.Required(CONF_ICON_SOON, default=icon_soon)] = str | ||
data_schema[vol.Required(CONF_DATE_FORMAT, default=date_format)] = str | ||
return self.async_show_form(step_id="user", data_schema=vol.Schema(data_schema), errors=self._errors) | ||
|
||
async def async_step_import(self, user_input): # pylint: disable=unused-argument | ||
"""Import a config entry. | ||
Special type of import, we're not actually going to store any data. | ||
Instead, we're going to rely on the values that are in config file. | ||
""" | ||
if self._async_current_entries(): | ||
return self.async_abort(reason="single_instance_allowed") | ||
|
||
return self.async_create_entry(title="configuration.yaml", data={}) | ||
|
||
@staticmethod | ||
@callback | ||
def async_get_options_flow(config_entry): | ||
if config_entry.options.get("unique_id", None) is not None: | ||
return OptionsFlowHandler(config_entry) | ||
else: | ||
return EmptyOptions(config_entry) | ||
|
||
def is_not_date(date): | ||
try: | ||
datetime.strptime(date, "%Y-%m-%d") | ||
return False | ||
except ValueError: | ||
return True | ||
|
||
class OptionsFlowHandler(config_entries.OptionsFlow): | ||
def __init__(self, config_entry): | ||
self.config_entry = config_entry | ||
self._data = config_entry.options | ||
|
||
async def async_step_init(self, user_input=None): | ||
self._errors = {} | ||
if user_input is not None: | ||
self._data.update(user_input) | ||
if is_not_date(user_input[CONF_DATE]): | ||
self._errors["base"] = "invalid_date" | ||
if self._errors == {}: | ||
return self.async_create_entry(title="", data=self._data) | ||
return await self._show_init_form(user_input) | ||
|
||
async def _show_init_form(self, user_input): | ||
data_schema = OrderedDict() | ||
data_schema[vol.Required(CONF_DATE, default=self.config_entry.options.get(CONF_DATE),)] = str | ||
data_schema[vol.Required(CONF_ICON_NORMAL,default=self.config_entry.options.get(CONF_ICON_NORMAL),)] = str | ||
data_schema[vol.Required(CONF_ICON_TODAY,default=self.config_entry.options.get(CONF_ICON_SOON),)] = str | ||
data_schema[vol.Required(CONF_SOON,default=self.config_entry.options.get(CONF_SOON),)] = int | ||
data_schema[vol.Required(CONF_ICON_SOON,default=self.config_entry.options.get(CONF_ICON_SOON),)] = str | ||
data_schema[vol.Required(CONF_DATE_FORMAT,default=self.config_entry.options.get(CONF_DATE_FORMAT),)] = str | ||
return self.async_show_form( | ||
step_id="init", data_schema=vol.Schema(data_schema), errors=self._errors | ||
) | ||
|
||
class EmptyOptions(config_entries.OptionsFlow): | ||
def __init__(self, config_entry): | ||
self.config_entry = config_entry |
Oops, something went wrong.