inverter_bot: setosp command
This commit is contained in:
parent
a1ee00b436
commit
b1badba55e
@ -80,6 +80,7 @@ setbatuv - Set battery under voltage
|
||||
setgencc - Set AC charging current
|
||||
setgenct - Set AC charging thresholds
|
||||
setacmode - Set AC input mode
|
||||
setosp - Set output source priority
|
||||
monstatus - Monitor: dump state
|
||||
monsetcur - Monitor: set charging currents
|
||||
```
|
@ -4,6 +4,7 @@ import re
|
||||
import datetime
|
||||
import json
|
||||
|
||||
from enum import Enum
|
||||
from inverterd import Format, InverterError
|
||||
from html import escape
|
||||
from typing import Optional, Tuple, Union
|
||||
@ -51,7 +52,14 @@ flags_map = {
|
||||
'fault_code_record': 'FTCR',
|
||||
}
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
SETACMODE_STARTED, = range(1)
|
||||
SETOSP_STARTED, = range(1)
|
||||
|
||||
|
||||
class OutputSourcePriority(Enum):
|
||||
SolarUtilityBattery = 'SUB'
|
||||
SolarBatteryUtility = 'SBU'
|
||||
|
||||
|
||||
def monitor_charging(event: ChargingEvent, **kwargs) -> None:
|
||||
@ -283,6 +291,14 @@ def setacmode(mode: ACMode):
|
||||
inverter.exec('set-max-ac-charge-current', (0, a))
|
||||
|
||||
|
||||
def setosp(sp: OutputSourcePriority):
|
||||
logger.debug(f'setosp: sp={sp}')
|
||||
inverter.exec('set-output-charge-priority', (sp,))
|
||||
|
||||
|
||||
# /setacmode
|
||||
# ----------
|
||||
|
||||
def setacmode_start(ctx: Context) -> None:
|
||||
if monitor.active_current is not None:
|
||||
raise RuntimeError('generator charging program is active')
|
||||
@ -338,6 +354,60 @@ def setacmode_cancel(ctx: Context):
|
||||
return ConversationHandler.END
|
||||
|
||||
|
||||
# /setosp
|
||||
# ------
|
||||
|
||||
def setosp_start(ctx: Context) -> None:
|
||||
buttons = []
|
||||
for sp in OutputSourcePriority:
|
||||
buttons.append(ctx.lang(f'setosp_{sp.value.lower()}'))
|
||||
markup = ReplyKeyboardMarkup([buttons, [ctx.lang('cancel')]], one_time_keyboard=False)
|
||||
|
||||
ctx.reply(ctx.lang('select_ac_mode'), markup=markup)
|
||||
return SETOSP_STARTED
|
||||
|
||||
|
||||
def setosp_input(ctx: Context):
|
||||
selected_sp = None
|
||||
for sp in OutputSourcePriority:
|
||||
if ctx.text == ctx.lang(f'setosp_{sp.value.lower()}'):
|
||||
selected_sp = sp
|
||||
break
|
||||
|
||||
if selected_sp is None:
|
||||
raise ValueError('invalid sp')
|
||||
|
||||
# apply the mode
|
||||
setosp(selected_sp)
|
||||
|
||||
# reply to user
|
||||
ctx.reply(ctx.lang('saved'), markup=IgnoreMarkup())
|
||||
|
||||
# notify other users
|
||||
bot.notify_all(
|
||||
lambda lang: bot.lang.get('osp_changed_notification', lang,
|
||||
ctx.user.id, ctx.user.name,
|
||||
bot.lang.get(str(selected_sp.value), lang)),
|
||||
exclude=(ctx.user_id,)
|
||||
)
|
||||
|
||||
bot.start(ctx)
|
||||
return ConversationHandler.END
|
||||
|
||||
|
||||
def setosp_invalid(ctx: Context):
|
||||
ctx.reply(ctx.lang('invalid_mode'), markup=IgnoreMarkup())
|
||||
return SETOSP_STARTED
|
||||
|
||||
|
||||
def setosp_cancel(ctx: Context):
|
||||
bot.start(ctx)
|
||||
return ConversationHandler.END
|
||||
|
||||
|
||||
# other
|
||||
# -----
|
||||
|
||||
def setbatuv(ctx: Context) -> None:
|
||||
try:
|
||||
v = float(ctx.args[0])
|
||||
@ -423,6 +493,7 @@ class InverterBot(Wrapper):
|
||||
done="Готово",
|
||||
unexpected_callback_data="Ошибка: неверные данные",
|
||||
select_ac_mode="Выберите режим:",
|
||||
select_priortiy="Установите приоритет:",
|
||||
invalid_input="Неверное значение",
|
||||
|
||||
flags_press_button='Нажмите кнопку для переключения настройки',
|
||||
@ -457,6 +528,9 @@ class InverterBot(Wrapper):
|
||||
setgenct_dv=f'напряжение отключения заряда, 48 {LT} DV {LT} 58',
|
||||
setgencc_a='максимальный ток заряда, допустимые значения: %s',
|
||||
|
||||
setosp_sub='Solar-Utility-Battery',
|
||||
setosp_sbu='Solar-Battery-Utility',
|
||||
|
||||
# monitor
|
||||
chrg_evt_started='✅ Начали заряжать от генератора.',
|
||||
chrg_evt_finished='✅ Зарядили. Генератор пора выключать.',
|
||||
@ -477,6 +551,7 @@ class InverterBot(Wrapper):
|
||||
|
||||
# other notifications
|
||||
ac_mode_changed_notification='Пользователь <a href="tg://user?id=%d">%s</a> установил режим AC: <b>%s</b>.',
|
||||
osp_changed_notification='Пользователь <a href="tg://user?id=%d">%s</a> установил приоритет источника питания нагрузки: <b>%s</b>.',
|
||||
|
||||
bat_state_normal='Нормальный',
|
||||
bat_state_low='Низкий',
|
||||
@ -493,6 +568,7 @@ class InverterBot(Wrapper):
|
||||
done="Done",
|
||||
unexpected_callback_data="Unexpected callback data",
|
||||
select_ac_mode="Select AC input mode:",
|
||||
select_priortiy="Select priority:",
|
||||
invalid_input="Invalid input",
|
||||
|
||||
flags_press_button='Press a button to toggle a flag.',
|
||||
@ -527,6 +603,9 @@ class InverterBot(Wrapper):
|
||||
setgenct_dv=f'discharging voltage, 48 {LT} DV {LT} 58',
|
||||
setgencc_a='max charging current, allowed values: %s',
|
||||
|
||||
setosp_sub='Solar-Utility-Battery',
|
||||
setosp_sbu='Solar-Battery-Utility',
|
||||
|
||||
# monitor
|
||||
chrg_evt_started='✅ Started charging from AC.',
|
||||
chrg_evt_finished='✅ Finished charging, it\'s time to stop the generator.',
|
||||
@ -547,6 +626,7 @@ class InverterBot(Wrapper):
|
||||
|
||||
# other notifications
|
||||
ac_mode_changed_notification='User <a href="tg://user?id=%d">%s</a> set AC mode to <b>%s</b>.',
|
||||
osp_changed_notification='Пользователь <a href="tg://user?id=%d">%s</a> set output source priority: <b>%s</b>.',
|
||||
|
||||
bat_state_normal='Normal',
|
||||
bat_state_low='Low',
|
||||
@ -585,6 +665,17 @@ class InverterBot(Wrapper):
|
||||
fallbacks=[MessageHandler(self.user_filter & cancel_filter, self.wrap(setacmode_cancel))]
|
||||
))
|
||||
|
||||
self.add_handler(ConversationHandler(
|
||||
entry_points=[CommandHandler('setosp', self.wrap(setosp_start), self.user_filter)],
|
||||
states={
|
||||
SETOSP_STARTED: [
|
||||
*[MessageHandler(text_filter(self.lang.all(f'setosp_{sp.value.lower()}')), self.wrap(setosp_input)) for sp in OutputSourcePriority],
|
||||
MessageHandler(self.user_filter & ~cancel_filter, self.wrap(setosp_invalid))
|
||||
]
|
||||
},
|
||||
fallbacks=[MessageHandler(self.user_filter & cancel_filter, self.wrap(setosp_cancel))]
|
||||
))
|
||||
|
||||
super().run()
|
||||
|
||||
def markup(self, ctx: Optional[Context]) -> Optional[ReplyKeyboardMarkup]:
|
||||
|
Loading…
x
Reference in New Issue
Block a user