airfresher

This commit is contained in:
monster
2019-01-09 01:47:33 +03:00
parent 88c68449be
commit 9b63b82b86
19 changed files with 129 additions and 682 deletions
+1 -4
View File
@@ -1,10 +1,7 @@
ARG VERSION ARG VERSION
FROM acockburn/appdaemon:${VERSION} FROM acockburn/appdaemon:${VERSION}
#log encoding temporary fix
RUN sed -i -e 's/safe_enc = lambda s: str(s).encode("utf-8", "replace").decode("ascii", "replace")/safe_enc = lambda s: str(s)/g' /usr/src/app/appdaemon/utils.py
RUN pip3 install \ RUN pip3 install \
emp_mos_api==0.9 \ emp_mos_api \
sqlalchemy \ sqlalchemy \
mysqlclient mysqlclient
@@ -4,7 +4,7 @@ import globals
class KitchenLedController(hass.Hass): class KitchenLedController(hass.Hass):
listen_event_handle_list = [] listen_event_handle_list = []
def initialize(self): def initialize(self):
if not globals.check_args(self,['watch_entity']): if not globals.check_args(self,['watch_entity', 'topic']):
return return
self.listen_event_handle_list.append(self.listen_state(self.entity_changed, self.args['watch_entity'])) self.listen_event_handle_list.append(self.listen_state(self.entity_changed, self.args['watch_entity']))
@@ -15,4 +15,4 @@ class KitchenLedController(hass.Hass):
stete = "off" stete = "off"
if new == "on": if new == "on":
stete = "on" stete = "on"
self.call_service("mqtt/publish", topic = "home/kitchen-led/kitchen-led/state/set", payload = stete) self.call_service("mqtt/publish", topic = self.args['topic'], payload = stete)
@@ -5,5 +5,17 @@ kitchen_led_controller:
module: kitchen_led_controller module: kitchen_led_controller
class: KitchenLedController class: KitchenLedController
watch_entity: light.kitchen watch_entity: light.kitchen
topic: home/kitchen-led/kitchen-led/state/set
global_dependencies:
- globals
#################################
# LIGHT BUTTONS #
#################################
kitchen_mini_light_controller:
module: kitchen_led_controller
class: KitchenLedController
watch_entity: light.kitchen
topic: home/plug/kitchen-mini-light/status/set
global_dependencies: global_dependencies:
- globals - globals
@@ -48,4 +48,4 @@ class ReportByPresence(hass.Hass):
message = "В доме остались работать следующие устройства:\n" + message message = "В доме остались работать следующие устройства:\n" + message
self.notify(message, name = self.args['notify']) self.notify(message, name = self.args['notify'])
else: else:
self.notify("Все устройства в доме выключены.", name = self.args['notify']) self.notify("Все устройства в доме выключены.", name = self.args['notify'])
@@ -17,12 +17,16 @@ import appdaemon.plugins.hass.hassapi as hass
class WaterValveControl(hass.Hass): class WaterValveControl(hass.Hass):
standby_power_limit = 15 standby_power_limit = 15
timer = None timer = None
listen_event_handle_list = []
timers = []
def initialize(self): def initialize(self):
if 'water_valve' not in self.args or 'water_devices' not in self.args or 'notify' not in self.args: if 'water_valve' not in self.args or 'water_devices' not in self.args or 'notify' not in self.args:
self.error("Please provide water_valve, water_devices and notify in config!") self.error("Please provide water_valve, water_devices and notify in config!")
return return
self.listen_event(self.away_mode, "away_mode")
self.listen_event(self.return_home_mode, "return_home_mode") self.listen_event_handle_list.append(self.listen_event(self.away_mode, "away_mode"))
self.listen_event_handle_list.append(self.listen_event(self.return_home_mode, "return_home_mode"))
self.log(self.get_turned_on_devices()) self.log(self.get_turned_on_devices())
def return_home_mode(self, event_id, event_args, kwargs): def return_home_mode(self, event_id, event_args, kwargs):
@@ -47,7 +51,7 @@ class WaterValveControl(hass.Hass):
device_names += self.friendly_name(device) device_names += self.friendly_name(device)
self.notify('В доме остались требующие воды устройства ({}), подача воды не будет отключена.'.format(device_names), name = self.args['notify']) self.notify('В доме остались требующие воды устройства ({}), подача воды не будет отключена.'.format(device_names), name = self.args['notify'])
self.cancel_current_timer() self.cancel_current_timer()
self.timer = self.run_every(self.wait_when_device_is_done, self.datetime(), 5*60) self.timers.append(self.run_every(self.wait_when_device_is_done, self.datetime(), 5*60))
else: else:
self.turn_off(self.args['water_valve']) self.turn_off(self.args['water_valve'])
for device in self.args['water_devices']: for device in self.args['water_devices']:
@@ -83,7 +87,7 @@ class WaterValveControl(hass.Hass):
return powered_on_devices return powered_on_devices
def cancel_current_timer(self): def cancel_current_timer(self):
if self.timer != None: for timer in self.timers:
self.log('canceling timer') self.log('canceling timer')
self.cancel_timer(self.timer) self.cancel_timer(timer)
self.timer = None self.timers = []
@@ -6,6 +6,7 @@ lock:
user_65537: Данил (сред) user_65537: Данил (сред)
user_65538: Света (указ) user_65538: Света (указ)
user_65539: Мама (указ) user_65539: Мама (указ)
user_65540: Саня
notify: telegram notify: telegram
global_dependencies: global_dependencies:
- globals - globals
-628
View File
@@ -1,628 +0,0 @@
# -*- coding: utf-8 -*-
from __future__ import print_function
import requests
from datetime import datetime, tzinfo
from copy import deepcopy
class AuthException(Exception):
pass
class EmpServerException(Exception):
pass
class Client(object):
"""
Клиента
"""
def __init__(self, **kwargs):
self.token = kwargs.get('token')
self.guid = kwargs.get('guid')
#requests
self.verify = kwargs.get('verify', True)
self.timeout = kwargs.get('timeout', 3.0)
self.session_id = None # emp mos ru
self.user_agent = kwargs.get('user_agent')
self.dev_app_version = kwargs.get('dev_app_version')
self.dev_user_agent = kwargs.get('dev_user_agent')
self.headers = {'Cache-Control': 'no-cache',
'Host': 'emp.mos.ru',
'Connection': 'Keep-Alive',
'Accept-Encoding': 'gzip',
'User-Agent': self.user_agent}
self.pheaders = deepcopy(self.headers)
self.pheaders.update({
'X-Cache-ov': '15552000',
'X-Cache-ov-mode': 'FORCE_NETWORK'
})
self.session = requests.Session()
def raise_for_status(self, answer):
"""
:param answer: JSON
{
u'errorCode': 0, # 0-OK,
401-Auth error
u'execTime': 0.138262,
u'errorMessage': u'', # error message
u'session_id': u'6c3333333c33333e44e21e7d43c46e03',
u'result': None or JSON
}
:return:
"""
# print('Exec time:', answer['execTime'])
if answer['errorCode'] == 401:
raise AuthException()
if answer['errorCode'] != 0:
if answer['errorMessage']:
raise EmpServerException(u'{0} (code:{1})'.format(answer['errorMessage'], answer['errorCode']))
raise EmpServerException(u'code:{0}'.format(answer['errorCode']))
def is_active(self):
"""
:return: True если уже залогинился
"""
return self.session_id is not None
def login(self, telephone, pwd):
"""
:param telephone: Телефон. Вид: 7xxxxxxxxxx
:param pwd: Пароль из приложения Госуслуги Москвы
:return: JSON
{
u'is_filled': True,
u'surname': u'x',
u'name': u'x',
u'session_id': u'6c3333333c33333e44e21e7d43c46e03'},
u'request_id': u'UN=PRO-12345678-1234-1234-1234-123456789123'
}
"""
login_data = {
'device_info': {
'guid': self.guid,
'user_agent': self.dev_user_agent,
'app_version': self.dev_app_version
},
'auth': {
'login': telephone,
'password': pwd,
'guid': self.guid
}
}
ret = self.session.post('https://emp.mos.ru/v1.0/auth/virtualLogin',
params={'token': self.token},
headers={'Content-Type': 'application/json; charset=UTF-8',
'Connection': 'Keep-Alive',
'Accept-Encoding': 'gzip',
'User-Agent': self.user_agent,
'cache-control': 'no-cache',
'Host': 'emp.mos.ru',
'Accept': '*/*'},
verify=self.verify,
timeout=self.timeout,
json=login_data)
response = ret.json()
self.raise_for_status(response)
self.session_id = response['session_id']
return response['result']
def get_profile(self):
"""
:return: JSON
{
u'drive_license': None,
u'firstname': u'x',
u'middlename': u'x',
u'lastname': u'x',
u'birthdate': u'dd.mm.YYYY',
u'msisdn': u'71234567890', # your telephone
u'email_confirmed': True,
u'email': u'x@x.ru'
}
"""
assert self.session_id
ret = self.session.get('https://emp.mos.ru/v1.0/profile/get',
params={'token': self.token,
'info[guid]': self.guid,
'auth[session_id]': self.session_id
},
headers=self.pheaders,
verify=self.verify,
timeout=self.timeout)
response = ret.json()
self.raise_for_status(response)
return response['result']['profile']
def get_flats(self):
"""
:return: JSON array
[{
u'name': u'x',
u'paycode': u'1234567890',
u'flat_id': u'1234567',
u'electro_account': None,
u'flat_number': u'0',
u'unad': u'0',
u'address': u'x',
u'electro_device': None,
u'unom': u'1234567' # Идентификатор дома
},{...}
]
"""
assert self.session_id
ret = self.session.get('https://emp.mos.ru/v1.0/flat/get',
params={'token': self.token,
'info[guid]': self.guid,
'auth[session_id]': self.session_id
},
headers=self.pheaders,
verify=self.verify,
timeout = self.timeout)
response = ret.json()
self.raise_for_status(response)
return response['result']
def get_watercounters(self, flat_id):
"""
:param flat_id: unicode string from flat_response
response[0]['flat_id']
:return:
{
u'stat_title': u'x',
u'archive': [
{
u'cold_indication': 1.55,
u'hot_indication': 1.2,
u'period': u'2017-08-31+03:00'
}, {
u'cold_indication': 1.3,
u'hot_indication': 0.39999999999998,
u'period': u'2017-09-30+03:00'
}, {
+10 эл-тов. Всего 12.
}],
u'counters': [
{
u'checkup': u'2021-08-08+03:00', # дата поверки
u'counterId': 123456, # id счетчика в emp.mos.ru
u'num': u'123456', # серийный номер счетчика
u'type': 1, # ХВС
u'indications': [
{
u'indication': u'200.24',
u'period': u'2018-07-31+03:00'
}, {
u'indication': u'200.6',
u'period': u'2018-06-30+03:00'
}, {
u'indication': u'200.5',
u'period': u'2018-05-31+03:00'
}, {
u'indication': u'200.5',
u'period': u'2018-04-30+03:00'
}]
},
{..}
]
}
"""
assert self.session_id
wheaders = deepcopy(self.headers)
wheaders.update({
'X-Clears-tags': 'WATER_COUNTERS',
'X-Cache-ov-mode': 'DEFAULT',
'Content-Type': 'application/json; charset=UTF-8' })
wcrequest = {
'flat_id': flat_id,
'is_widget': False,
'info': {
'guid': self.guid
},
'auth': {
'session_id': self.session_id
}
}
ret = self.session.post('https://emp.mos.ru/v1.0/watercounters/get',
params={'token': self.token},
headers=wheaders,
verify=self.verify,
timeout=self.timeout,
json=wcrequest)
response = ret.json()
self.raise_for_status(response)
return response['result']
def send_watercounters(self, flat_id, counters_data):
"""
:param flat_id: flat_response['flat_id']
:param counters_data: array of
[{
'counter_id': u'123456', # ['counters'][0]['counterId']
'period': datetime.now().strftime("%Y-%m-%d"),
'indication': 'xxx,xx'
}, {
...
}]
:return:
"""
assert self.session_id
wheaders = deepcopy(self.headers)
wheaders.update({
'X-Clears-tags': 'WATER_COUNTERS',
'Content-Type': 'application/json; charset=UTF-8'
})
wcrequest = {'flat_id': flat_id,
'counters_data': counters_data,
'info': {
'guid': self.guid
},
'auth': {
'session_id': self.session_id
}}
ret = self.session.post('https://emp.mos.ru/v1.0/watercounters/addValues',
params={'token': self.token},
headers=wheaders,
verify=self.verify,
timeout=self.timeout,
json=wcrequest)
response = ret.json()
self.raise_for_status(response)
return response['result']
def get_electrocounters(self, flat_id):
"""
:param flat_id: unicode string from flat_response
response[0]['flat_id']
:return:
{
"address": "город ...",
"electro_account": "851xxxx475",
"electro_device": "04xxx17",
"balance": 0,
"is_debt": false,
"description": "Внимание! Передача показаний возможна с 15 по 26 число месяца. При вводе текущих показаний обращайте внимание на значность счетчиков. В случае если показания введены с неверной значностью (большей, чем значность счетчика), они не будут загружены.",
"sh_znk": 5,
"zones": [{
"name": "T1",
"value": "6887"
}],
"intervals": [{
"name": "T1",
"value": "00:00-23:59"
}]
}
"""
assert self.session_id
wheaders = deepcopy(self.headers)
wheaders.update({
'X-Clears-tags': 'ELECTRO_COUNTERS',
'X-Cache-ov-mode': 'DEFAULT',
'Content-Type': 'application/json; charset=UTF-8' })
wcrequest = {
'flat_id': flat_id,
'is_widget': False,
'info': {
'guid': self.guid,
'user_agent': self.dev_user_agent,
'app_version': self.dev_app_version
},
'auth': {
'session_id': self.session_id
}
}
ret = self.session.post('https://emp.mos.ru/v1.0/electrocounters/get',
params={'token': self.token},
headers=wheaders,
verify=self.verify,
timeout=self.timeout,
json=wcrequest)
response = ret.json()
self.raise_for_status(response)
return response['result']
def send_electrocounters(self, flat_id, counters_data):
"""
:param flat_id: flat_response['flat_id']
:param counters_data: array of
[{
'counter_id': u'123456', # ['counters'][0]['counterId']
'period': datetime.now().strftime("%Y-%m-%d"),
'indication': 'xxx,xx'
}, {
...
}]
:return:
"""
assert self.session_id
wheaders = deepcopy(self.headers)
wheaders.update({
'X-Clears-tags': 'ELECTRO_COUNTERS',
'Content-Type': 'application/json; charset=UTF-8'
})
wcrequest = {'flat_id': flat_id,
'counters_data': counters_data,
'info': {
'guid': self.guid,
'user_agent': self.dev_user_agent,
'app_version': self.dev_app_version
},
'auth': {
'session_id': self.session_id
}}
ret = self.session.post('https://emp.mos.ru/v1.0/electrocounters/addValues',
params={'token': self.token},
headers=wheaders,
verify=self.verify,
timeout=self.timeout,
json=wcrequest)
response = ret.json()
self.raise_for_status(response)
return response['result']
def get_epd(self, flat_id, period, is_debt=True):
"""
:param flat_id: unicode string from flat_response
response[0]['flat_id']
:param period: unicode string represents date in 27.09.2018 format
:param is_debt: True/False
:return:
{
"is_debt": true,
"is_paid": true,
"amount": 2982.77,
"service_code": "emp.zkh",
"insurance": 61.93,
"ammount_insurance": 3044.7
}
"""
assert self.session_id
wheaders = deepcopy(self.headers)
wheaders.update({
'X-Clears-tags': 'EPD',
'X-Cache-ov-mode': 'DEFAULT',
'Content-Type': 'application/json; charset=UTF-8' })
wcrequest = {
'flat_id': flat_id,
'period': period,
'is_debt': is_debt,
'info': {
'guid': self.guid
},
'auth': {
'session_id': self.session_id
}
}
ret = self.session.post('https://emp.mos.ru/v1.1/epd/get',
params={'token': self.token},
headers=wheaders,
verify=self.verify,
timeout=self.timeout,
json=wcrequest)
response = ret.json()
self.raise_for_status(response)
return response['result']
def get_car_fines(self, sts_number):
"""
:param sts_number: unicode string contains car sts_numer
:return:
{
"paid": [{
"seriesAndNumber": "xxxxx",
"date": "2018-08-30+03:00",
"offence_place": "МОСКВА Г. МКАД,xxxx, ВНЕШНЯЯ СТОРОНА",
"offenceType": "12.9ч.2 - Превышение установленной скорости движения транспортного средства на величину от 20 до 40 километров в час ",
"cost": "500",
"is_discount": false,
"drive_license": null,
"sts_number": "xxxxxxx",
"executionState": "Исполнено",
"is_fssp": false
}],
"unpaid": []
}
"""
assert self.session_id
wheaders = deepcopy(self.headers)
wheaders.update({
'X-Clears-tags': 'FORCE_NETWORK',
'X-Cache-ov-mode': 'DEFAULT',
'Content-Type': 'application/json; charset=UTF-8' })
wcrequest = {
'sts_number': sts_number,
'info': {
'guid': self.guid
},
'auth': {
'session_id': self.session_id
}
}
ret = self.session.post('https://emp.mos.ru/v1.0/offence/getOffence',
params={'token': self.token},
headers=wheaders,
verify=self.verify,
timeout=self.timeout,
json=wcrequest)
response = ret.json()
self.raise_for_status(response)
return response['result']
def logout(self, timeout=None):
"""
Почему то очень долго выполняется (5 сек)
"""
if self.session_id:
logout_data = {
'info': {
'guid': self.guid
},
'auth': {
'session_id': self.session_id
}
}
ret = self.session.post('https://emp.mos.ru/v1.0/auth/logout',
params={'token': self.token},
headers=self.headers,
timeout=timeout or self.timeout,
json=logout_data)
response = ret.json()
self.raise_for_status(response)
self.session_id = None
return response['result']
class MosAPI(object):
"""
kwargs:
token: уникальный ключ приложения
guid: некий уникальный ключ
https_verify: ключ verify в GET, POST запросах, по умолчанию 'False'
timeout: ключ timeout в GET, POST запросах
user_agent: версия веб клиента
dev_user_agent: 'Android' для ОС Android
dev_app_version: версия ОС
"""
def __init__(self, **kwargs):
self.kwargs = kwargs
self._clients = {'default': Client(**kwargs)}
def client(self, client_id='default', **kwargs):
if client_id and \
client_id not in self._clients:
k = self.kwargs
k.update(kwargs)
self._clients[client_id] = Client(**k)
return self._clients[client_id]
# if only one client
def is_active(self):
return self.client().is_active()
def login(self, *args):
return self.client().login(*args)
def logout(self, *args):
return self.client().logout(*args)
def get_profile(self):
return self.client().get_profile()
def get_flats(self):
return self.client().get_flats()
def get_watercounters(self, *args):
return self.client().get_watercounters(*args)
def send_watercounters(self, *args):
return self.client().send_watercounters(*args)
def get_electrocounters(self, *args):
return self.client().get_electrocounters(*args)
def send_electrocounters(self, *args):
return self.client().send_electrocounters(*args)
def get_epd(self, *args):
return self.client().get_epd(*args)
def get_car_fines(self, *args):
return self.client().get_car_fines(*args)
class Water():
COLD = 1
HOT = 2
@staticmethod
def water_abbr(water):
if water == Water.COLD: return u'ХВС'
elif water == Water.HOT: return u'ГВС'
@staticmethod
def name(water):
if water == Water.COLD: return u'холодная вода'
elif water == Water.HOT: return u'горячая вода'
class Watercounter():
"""
[{ 'counterId': 1437373, # внутреннее id счетчика
'type': 1, # тип воды
'num': '417944', # серийный номер счетчика
'checkup': '2023-09-25+03:00', # дата следующей поверки
'indications':
[{'period': '2018-08-31+03:00', 'indication': '21.38'},
{'period': '2018-07-31+03:00', 'indication': '20.7'},
{'period': '2018-06-30+03:00', 'indication': '19'}]
},
{...}
]
list(filter(lambda x: x['num'] == num, response['counters']))
list(filter(lambda x: x['counterId'] == id, response['counters']))
list(filter(lambda x: x['type'] == water_type_id, response['counters']))
"""
@staticmethod
def last_value(counter):
"""
alphabetical sort data =)
:param counter: counter JSON
:return: float or None
"""
indications = counter['indications']
indications.sort(key=lambda x: x['period'])
if indications:
return float(indications[-1]['indication'])
@staticmethod
def water_title(counter):
return Watercounter.humanreadable_name(counter['type'])
@staticmethod
def checkup(counter):
"""
https://docs.python.org/3/library/datetime.html#datetime.timezone
Если нужно UTC d.replace(tzinfo=None)
:param counter: counter JSON
:return: datetime с временной зоной
"""
checkup = counter['checkup']
d = datetime.strptime(checkup, '%Y-%m-%d%z') #'checkup': '2023-09-25+03:00'
return d
@staticmethod
def serialize_for_send(counter, value):
"""
:param counterId: id счетчика. не номер из приложения!
:param value: значение float
:return: dict
"""
return {
'counter_id': int(counter['counterId']),
'period': datetime.now().strftime("%Y-%m-%d"),
'indication': '{:.2f}'.format(value).replace('.', ',')
}
+2 -1
View File
@@ -2,7 +2,8 @@ import globals
import datetime as dt import datetime as dt
from automation import Automation, Base from automation import Automation, Base
from datetime import datetime, tzinfo, timedelta from datetime import datetime, tzinfo, timedelta
from mos_lib import MosAPI, Watercounter, Water, EmpServerException from emp_mos_api.mos import MosAPI, Watercounter, Water, EmpServerException
#from mos_lib import MosAPI, Watercounter, Water, EmpServerException
class WaterCounterSender(Automation): class WaterCounterSender(Automation):
timezone = '+03:00' timezone = '+03:00'
+23 -1
View File
@@ -1,9 +1,31 @@
db: power_history:
module: db module: db
class: Db class: Db
connectionstring: !secret mysql_url connectionstring: !secret mysql_url
entity_id: sensor.power_total entity_id: sensor.power_total
debug: true
global_dependencies:
- automation
counter_hot_history:
module: db
class: Db
connectionstring: !secret mysql_url
entity_id: sensor.counter_hot
debug: true
global_dependencies:
- automation
counter_cold_history:
module: db
class: Db
connectionstring: !secret mysql_url
entity_id: sensor.counter_cold
debug: true debug: true
global_dependencies: global_dependencies:
- automation - automation
@@ -0,0 +1,50 @@
import appdaemon.plugins.hass.hassapi as hass
import globals
import datetime
#
# Entity timer
# Turn on and off this entities
#
# Args:
#
# None
#
# Release Notes
#
# Version 1.0:
# Initial Version
class AirFresher(hass.Hass):
timers = []
fresh_times = 0
def initialize(self):
self.listen_state(self.light_change, 'group.bath_light')
def light_change(self, entity, attribute, old, new, kwargs):
if (old == "on" and new == "off"):
self.log('Stop freshing timer.')
self.cancel_timers()
if (old == "off" and new == "on"):
self.log('Start freshing timer.')
self.fresh_times = 0
newtime = self.datetime()+datetime.timedelta(minutes=3)
self.timers.append(self.run_every(self.timer_tick, newtime, 5*60))
def timer_tick(self, args) -> None:
self.fresh()
def cancel_timers(self) -> None:
for timer in self.timers:
self.cancel_timer(timer)
timers = []
def fresh(self):
self.fresh_times = self.fresh_times + 1
if (self.fresh_times > 5):
self.log('Fresh max times is reached. Canceling timer.')
self.cancel_timers()
return
self.log('freshing in {}'.format(self.fresh_times))
self.call_service("mqtt/publish", topic = "home/airfresher/airfresher/fresh/set", payload = "1")
@@ -0,0 +1,8 @@
airfresher:
module: airfresher
class: AirFresher
# on_time: "09:00:00"
# off_time: "22:00:00"
# entity: switch.ledstrip
global_dependencies:
- globals
+2 -19
View File
@@ -33,7 +33,6 @@ services:
depends_on: depends_on:
- mysql - mysql
- mosquitto - mosquitto
- influxdb
- broadlink - broadlink
network_mode: "host" network_mode: "host"
restart: always restart: always
@@ -45,7 +44,7 @@ services:
appdaemon: appdaemon:
image: monster1025/appdaemon image: monster1025/appdaemon
build: build:
context: ./appdaemon context: ./appdaemon/docker
args: args:
VERSION: 3.0.2 VERSION: 3.0.2
container_name: appdaemon container_name: appdaemon
@@ -135,7 +134,7 @@ services:
environment: environment:
- GF_SECURITY_ADMIN_PASSWORD=grafanapass - GF_SECURITY_ADMIN_PASSWORD=grafanapass
links: links:
- "influxdb:influxdb" - "mysql:mysql"
ports: ports:
- "3000:3000" - "3000:3000"
restart: always restart: always
@@ -143,19 +142,3 @@ services:
driver: json-file driver: json-file
options: options:
max-size: 50m max-size: 50m
influxdb:
image: influxdb
container_name: influxdb
volumes:
- "/etc/localtime:/etc/localtime:ro"
- "/srv/influxdb/db:/var/lib/influxdb"
- "/srv/influxdb/log:/var/log/influxdb"
ports:
- "8083:8083"
- "8086:8086"
restart: always
logging:
driver: json-file
options:
max-size: 50m
-1
View File
@@ -50,7 +50,6 @@ switch: !include_dir_merge_list configuration/switch
tts: !include_dir_merge_list configuration/tts tts: !include_dir_merge_list configuration/tts
#one item #one item
influxdb: !include configuration/influxdb.yaml
mqtt: !include configuration/mqtt/mqtt.yaml mqtt: !include configuration/mqtt/mqtt.yaml
telegram_bot: !include configuration/bot/telegram_bot.yaml telegram_bot: !include configuration/bot/telegram_bot.yaml
vacuum: !include configuration/xiaomi_aqara/vacuum.yaml vacuum: !include configuration/xiaomi_aqara/vacuum.yaml
@@ -3,4 +3,4 @@ kitchen_light:
control: hidden control: hidden
entities: entities:
- light.kitchen - light.kitchen
- switch.kitchen_mini_light #- switch.kitchen_mini_light
@@ -4,4 +4,5 @@
entities: entities:
- sensor.temperature_158d00012d9ad7 - sensor.temperature_158d00012d9ad7
- sensor.humidity_158d00012d9ad7 - sensor.humidity_158d00012d9ad7
- light.bath - light.bath
- sensor.airfresher_remain
-12
View File
@@ -1,12 +0,0 @@
host: !secret base_localname
port: 8086
database: hass
max_retries: 3
default_measurement: state
include:
domains:
- sensor
- binary_sensor
- switch
@@ -0,0 +1,13 @@
#################################################
# AirFresher #
#################################################
- platform: mqtt
state_topic: 'home/airfresher/airfresher/remain'
name: 'airfresher_remain'
# value_template: '{{ (value | float ) / 1000 }}'
unit_of_measurement: 'times'
- platform: template
sensors:
airfresher_remain_percent:
value_template: "{{ ((100 / 1400) * (states('sensor.airfresher_remain') | int )) | round(2) }}"
@@ -1,4 +0,0 @@
# - platform: template
# sensors:
# lux_outside:
# value_template: '{{0}}'
@@ -2,7 +2,7 @@
sensors: sensors:
power_main_total: power_main_total:
unit_of_measurement: 'kWh' unit_of_measurement: 'kWh'
value_template: "{{ states('sensor.power_total') | float + 4733.6 | round(2) }}" value_template: "{{ (states('sensor.power_total') | float + 4733.6) | round(2) }}"
#4733.6 - разница показаний. #4733.6 - разница показаний.
- platform: modbus - platform: modbus