You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
721 lines
33 KiB
721 lines
33 KiB
# -*- coding: utf8 -*- |
|
# Общественное достояние, 2023, Алексей Безбородов (Alexei Bezborodov) <AlexeiBv+mirocod_platform_bot@narod.ru> |
|
|
|
# Модуль для редактирования и просмотра таблицы в БД |
|
|
|
from bot_sys import keyboard, user_access, bd_table, bot_bd, bot_subscribes |
|
from bot_modules import access_utils, mod_simple_message, groups_utils |
|
from template import simple_message, bd_item, bd_item_select, bd_item_view, bd_item_delete, bd_item_add, bd_item_edit |
|
|
|
from aiogram.dispatcher import FSMContext |
|
from aiogram.dispatcher.filters.state import State, StatesGroup |
|
|
|
from enum import Enum |
|
from enum import auto |
|
|
|
def EditButton(a_BDTableDestiny): |
|
return 'edit ' + str(a_BDTableDestiny) |
|
|
|
def EnumButton(a_EnumItem): |
|
return 'enum ' + str(a_EnumItem) |
|
|
|
def EditMessage(a_BDTableDestiny): |
|
return 'edit ' + str(a_BDTableDestiny) |
|
|
|
def InlineMessage(a_ButtonName): |
|
return 'inline ' + str(a_ButtonName) |
|
|
|
def CreateMessage(a_BDTableDestiny): |
|
return 'create ' + str(a_BDTableDestiny) |
|
|
|
def EnumMessageForView(a_EnumItem): |
|
return 'enum ' + str(a_EnumItem) |
|
|
|
def NotificationMessage(a_EnumItem): |
|
return 'notification ' + str(a_EnumItem) |
|
|
|
def SubscribeMessage(a_EnumItem): |
|
return 'subscribe ' + str(a_EnumItem) |
|
|
|
class ButtonNames(Enum): |
|
SHOW = auto() |
|
LIST = auto() |
|
ADD = auto() |
|
EDIT = auto() |
|
DEL = auto() |
|
|
|
class Messages(Enum): |
|
SELECT = auto() |
|
ERROR_FIND = auto() |
|
OPEN = auto() |
|
SUCCESS_CREATE = auto() |
|
START_EDIT = auto() |
|
SELECT_TO_EDIT = auto() |
|
SUCCESS_EDIT = auto() |
|
SELECT_TO_DELETE = auto() |
|
SUCCESS_DELETE = auto() |
|
|
|
def GetCurItem(a_Bot, a_TableName, a_KeyName, a_KeyValue): |
|
items = bd_item.GetBDItemsTemplate(a_Bot, a_TableName, a_KeyName)(a_KeyValue) |
|
if len(items) == 1: |
|
return items[0] |
|
return None |
|
|
|
create_fsm_create_cmd = ''' |
|
class FSMCreate{a_ModName}(StatesGroup): |
|
{items} |
|
|
|
fsm = FSMCreate{a_ModName} |
|
''' |
|
|
|
def MakeFSMForAdd(a_ModName, a_Fields): |
|
cmd = create_fsm_create_cmd.replace("{a_ModName}", a_ModName) |
|
items = "" |
|
for i in range(len(a_Fields)): |
|
items += f"\titem{i} = State()\n" |
|
cmd = cmd.replace("{items}", items) |
|
_locals = locals() |
|
exec(cmd, globals(), _locals) |
|
return _locals['fsm'] |
|
|
|
|
|
edit_fsm_cmd = ''' |
|
class FSMEdit{a_ModName}_{a_FieldName}_Item(StatesGroup): |
|
item_field = State() |
|
|
|
fsm = FSMEdit{a_ModName}_{a_FieldName}_Item |
|
''' |
|
|
|
def MakeFSMForEdit(a_ModName, a_FieldName): |
|
cmd = edit_fsm_cmd.replace("{a_ModName}", a_ModName).replace("{a_FieldName}", a_FieldName) |
|
_locals = locals() |
|
exec(cmd, globals(), _locals) |
|
return _locals['fsm'] |
|
|
|
add_and_edit_fsm_cmd = ''' |
|
class FSMAddAndEdit{a_ModName}_{a_FieldName}_Item(StatesGroup): |
|
item_field = State() |
|
|
|
fsm = FSMAddAndEdit{a_ModName}_{a_FieldName}_Item |
|
''' |
|
|
|
def MakeFSMForAddAndEdit(a_ModName, a_FieldName): |
|
cmd = add_and_edit_fsm_cmd.replace("{a_ModName}", a_ModName).replace("{a_FieldName}", a_FieldName) |
|
_locals = locals() |
|
exec(cmd, globals(), _locals) |
|
return _locals['fsm'] |
|
|
|
|
|
class TableOperateModule(mod_simple_message.SimpleMessageModule): |
|
def __init__(self, a_Table, a_Messages, a_Buttons, a_ParentModName, a_ChildModName, a_InitAccess, a_DefInitAccess, a_ChildModuleNameList, a_EditModuleNameList, a_Bot, a_ModuleAgregator, a_BotMessages, a_BotButtons, a_BotSubscribes, a_Log): |
|
super().__init__(a_Messages, a_Buttons, a_InitAccess, a_DefInitAccess, a_ChildModuleNameList, a_Bot, a_ModuleAgregator, a_BotMessages, a_BotButtons, a_BotSubscribes, a_Log) |
|
self.m_Table = a_Table |
|
self.m_EditModuleNameList = a_EditModuleNameList |
|
self.m_ChildModName = a_ChildModName |
|
self.m_ParentModName = a_ParentModName |
|
self.m_SelectPrefix = '' |
|
self.m_EditPrefix = {} |
|
|
|
def GetEditKeyboardButtons(a_Message, a_UserGroups): |
|
return self.GetEditKeyboardButtons(a_Message, a_UserGroups) |
|
self.m_GetEditKeyboardButtonsFunc = GetEditKeyboardButtons |
|
|
|
def GetButtonNameAndKeyValueAndAccess(a_Item): |
|
return self.GetButtonNameAndKeyValueAndAccess(a_Item) |
|
self.m_GetButtonNameAndKeyValueAndAccessFunc = GetButtonNameAndKeyValueAndAccess |
|
|
|
async def PreDelete(a_CallbackQuery, a_Item, a_None, table_name = self.m_Table.GetName()): |
|
return await self.PreDelete(a_CallbackQuery, a_Item, a_None) |
|
self.m_PreDeleteFunc = PreDelete |
|
|
|
async def PostDelete(a_CallbackQuery, a_ItemID): |
|
return await self.PostDelete(a_CallbackQuery, a_ItemID) |
|
self.m_PostDeleteFunc = PostDelete |
|
|
|
async def AddBDItemFunc(a_ItemData, a_UserID): |
|
return await self.AddBDItemFunc(a_ItemData, a_UserID) |
|
self.m_AddBDItemFunc = AddBDItemFunc |
|
|
|
def GetInitBDCommands(self): |
|
return [ |
|
self.m_Table.GetInitTableRequest(), |
|
] + super().GetInitBDCommands() |
|
|
|
def GetStartButtons(self, a_Message, a_UserGroups): |
|
return [ |
|
[ButtonNames.LIST, user_access.AccessMode.VIEW], |
|
[ButtonNames.ADD, user_access.AccessMode.ADD], |
|
[ButtonNames.DEL, user_access.AccessMode.DELETE], |
|
[ButtonNames.EDIT, user_access.AccessMode.EDIT], |
|
] |
|
|
|
def GetStartKeyboardButtons(self, a_Message, a_UserGroups): |
|
mod_buttons = super().GetStartKeyboardButtons(a_Message, a_UserGroups) |
|
cur_buttons = [] |
|
for b in self.GetStartButtons(a_Message, a_UserGroups): |
|
bn = b[0] |
|
ba = b[1] |
|
cur_buttons += [keyboard.ButtonWithAccess(self.GetButton(bn), ba, self.GetAccess())] |
|
return mod_buttons + keyboard.MakeButtons(self.m_Bot, cur_buttons, a_UserGroups) |
|
|
|
def GetAccessForEditKeyboardButtons(self, a_Field): |
|
if a_Field.m_Destiny == bd_table.TableFieldDestiny.ACCESS or a_Field.m_Destiny == bd_table.TableFieldDestiny.DEFAULT_ACCESS: |
|
return user_access.AccessMode.ACCEES_EDIT |
|
return user_access.AccessMode.EDIT |
|
|
|
def GetEditKeyboardButtons(self, a_Message, a_UserGroups): |
|
mod_buttons = keyboard.MakeButtons(self.m_Bot, self.GetButtons(self.m_EditModuleNameList), a_UserGroups) |
|
cur_buttons = [] |
|
for f in self.m_Table.GetFields(): |
|
access = self.GetAccessForEditKeyboardButtons(f) |
|
cur_buttons += [keyboard.ButtonWithAccess(self.GetButton(EditButton(f.m_Destiny)), access, self.GetAccess()),] |
|
return mod_buttons + keyboard.MakeButtons(self.m_Bot, cur_buttons, a_UserGroups) |
|
|
|
def GetShowItemInlineKeyboardTemplate(self, a_ItemID): |
|
def GetShowItemInlineKeyboard(a_Message, a_UserGroups): |
|
return self.GetShowItemInlineKeyboard(a_Message, a_UserGroups, a_ItemID) |
|
return GetShowItemInlineKeyboard |
|
|
|
def GetViewItemInlineKeyboardTemplate(self, a_ItemID): |
|
def GetViewItemInlineKeyboard(a_Message, a_UserGroups): |
|
return self.GetViewItemInlineKeyboard(a_Message, a_UserGroups, a_ItemID) |
|
return GetViewItemInlineKeyboard |
|
|
|
def GetSelectPrefix(self): |
|
return self.m_SelectPrefix |
|
|
|
def GetDelPrefix(self): |
|
return self.m_DelPrefix |
|
|
|
def GetAddPrefix(self): |
|
return self.m_AddPrefix |
|
|
|
def GetShowPrefix(self): |
|
return self.m_ShowPrefix |
|
|
|
def GetShowItemInlineKeyboard(self, a_Message, a_UserGroups, a_ItemID): |
|
cur_buttons = [ |
|
keyboard.InlineButtonWithAccess(self.GetButton(ButtonNames.SHOW), self.GetShowPrefix(), a_ItemID, self.GetAccess(), user_access.AccessMode.VIEW), |
|
] |
|
return keyboard.MakeInlineKeyboardButtons(self.m_Bot, cur_buttons, a_UserGroups) |
|
|
|
def GetViewItemInlineKeyboard(self, a_Message, a_UserGroups, a_ItemID): |
|
if not self.m_ChildModName: |
|
return None |
|
child_mod = self.GetModule(self.m_ChildModName) |
|
cur_buttons = [ |
|
keyboard.InlineButtonWithAccess(child_mod.GetButton(ButtonNames.LIST), child_mod.GetSelectPrefix(), a_ItemID, child_mod.GetAccess(), user_access.AccessMode.VIEW), |
|
] |
|
return keyboard.MakeInlineKeyboardButtons(self.m_Bot, cur_buttons, a_UserGroups) |
|
|
|
def GetButtonNameAndKeyValueAndAccess(self, a_Item): |
|
key_name_id = self.GetKeyFieldID() |
|
name_field_id = self.m_Table.GetFieldIDByDestiny(bd_table.TableFieldDestiny.NAME) |
|
access_field_id = self.m_Table.GetFieldIDByDestiny(bd_table.TableFieldDestiny.ACCESS) |
|
assert key_name_id != None |
|
assert name_field_id != None |
|
assert access_field_id != None |
|
return \ |
|
a_Item[name_field_id],\ |
|
a_Item[key_name_id],\ |
|
a_Item[access_field_id] |
|
|
|
def UpdateMessage(self, a_Msg, a_Lang, a_Item, a_EnablePhoto = False): |
|
a_Msg.UpdateDesc(self.m_Table.ReplaceAllFieldTags(a_Msg.GetDesc(), a_Item)) |
|
photos = [] |
|
field_id = 0 |
|
for f in self.m_Table.GetFields(): |
|
if f.m_Type == bd_table.TableFieldType.ENUM: |
|
for s in f.m_Enum: |
|
msg = self.GetMessage(EnumMessageForView(s)) |
|
if msg: |
|
a_Msg.UpdateDesc(a_Msg.GetDesc().replace(str(s), str(msg.GetMessageForLang(a_Lang).StaticCopy()))) |
|
elif f.m_Type == bd_table.TableFieldType.PHOTO: |
|
photos += [str(a_Item[field_id])] |
|
field_id += 1 |
|
if a_EnablePhoto: |
|
a_Msg.UpdatePhotoID(','.join(photos)) |
|
return a_Msg |
|
|
|
def UpdateMessageByDict(self, a_Msg, a_Lang, a_ItemDict, a_EnablePhoto = False): |
|
a_Msg.UpdateDesc(self.m_Table.ReplaceAllFieldTagsByDict(a_Msg.GetDesc(), a_ItemDict)) |
|
photos = [] |
|
for f in self.m_Table.GetFields(): |
|
if f.m_Type == bd_table.TableFieldType.ENUM: |
|
for s in f.m_Enum: |
|
msg = self.GetMessage(EnumMessageForView(s)) |
|
if msg: |
|
a_Msg.UpdateDesc(a_Msg.GetDesc().replace(str(s), str(msg.GetMessageForLang(a_Lang).StaticCopy()))) |
|
elif f.m_Type == bd_table.TableFieldType.PHOTO: |
|
if f.m_Name in a_ItemDict: |
|
photos += [str(a_ItemDict[f.m_Name])] |
|
if a_EnablePhoto: |
|
a_Msg.UpdatePhotoID(','.join(photos)) |
|
return a_Msg |
|
|
|
def GetParentID(self, a_Item, a_ItemDict, a_TableName): |
|
parent_id = None |
|
parent_id_field = self.m_Table.GetFieldNameByDestiny(bd_table.TableFieldDestiny.PARENT_ID) |
|
if parent_id_field and a_ItemDict and parent_id_field in a_ItemDict: |
|
parent_id = str(a_ItemDict[parent_id_field]) |
|
parent_id_field_id = self.m_Table.GetFieldIDByDestiny(bd_table.TableFieldDestiny.PARENT_ID) |
|
if not parent_id and parent_id_field_id != None and a_Item and len(a_Item) == self.m_Table.GetFieldsCount() and self.m_Table.GetName() == a_TableName: |
|
parent_id = str(a_Item[parent_id_field_id]) |
|
if self.m_ParentModName: |
|
parent_mod = self.GetModule(self.m_ParentModName) |
|
if parent_mod: |
|
key_field_id = parent_mod.m_Table.GetFieldIDByDestiny(bd_table.TableFieldDestiny.KEY) |
|
if not parent_id and key_field_id != None and a_Item and len(a_Item) == parent_mod.m_Table.GetFieldsCount() and parent_mod.m_Table.GetName() == a_TableName: |
|
parent_id = str(a_Item[key_field_id]) |
|
return parent_id |
|
|
|
def GetMessageNameWithTableFieldDestinyAndValue(self, a_NameWithoutDestiny, a_Destiny, a_Value): |
|
return a_NameWithoutDestiny + '?' + str(a_Destiny) + '=' + str(a_Value) |
|
|
|
def ShowMessageTemplate(self, a_Message, Inline_keyboard_template_func = None, a_EnablePhoto = False): |
|
async def ShowMessage(a_CallbackQuery, a_Item, a_ItemDict, table_name = self.m_Table.GetName()): |
|
lang = str(a_CallbackQuery.from_user.language_code) |
|
msg = a_Message |
|
|
|
# Подменяем сообщение, если оно уже есть для PARENT_ID |
|
parent_id = self.GetParentID(a_Item, a_ItemDict, table_name) |
|
if parent_id: |
|
name = self.GetMessageNameWithTableFieldDestinyAndValue(msg.GetName(), bd_table.TableFieldDestiny.PARENT_ID, parent_id) |
|
parent_id_msg = a_Message.FindMessageForLang(name, lang) |
|
if parent_id_msg: |
|
msg = parent_id_msg |
|
|
|
msg = msg.GetMessageForLang(lang).StaticCopy() |
|
# TODO: добавить поддержку языков в a_MessageName |
|
Inline_keyboard_func = None |
|
item_access = None |
|
if a_ItemDict: |
|
msg = self.UpdateMessageByDict(msg, lang, a_ItemDict, a_EnablePhoto = a_EnablePhoto) |
|
|
|
if a_Item and self.m_Table.GetName() == table_name: |
|
if len(a_Item) < self.m_Table.GetFieldsCount() - 1: # Для проектов это нужно. Там на 1 меньше поле. TODO разделить отправку сообщений item_access и Inline_keyboard_func |
|
return simple_message.WorkFuncResult(self.GetMessage(Messages.ERROR_FIND)) |
|
elif len(a_Item) == self.m_Table.GetFieldsCount(): |
|
msg = self.UpdateMessage(msg, lang, a_Item, a_EnablePhoto = a_EnablePhoto) |
|
item_access = a_Item[self.m_Table.GetFieldIDByDestiny(bd_table.TableFieldDestiny.ACCESS)] |
|
if Inline_keyboard_template_func: |
|
Inline_keyboard_func = Inline_keyboard_template_func(a_Item[self.GetKeyFieldID()]) |
|
|
|
return simple_message.WorkFuncResult(msg, item_access = item_access, Inline_keyboard_func = Inline_keyboard_func) |
|
return ShowMessage |
|
|
|
async def PreDelete(self, a_CallbackQuery, a_Item, a_None): |
|
if len(a_Item) < self.m_Table.GetFieldsCount(): |
|
return simple_message.WorkFuncResult(self.GetMessage(Messages.ERROR_FIND)) |
|
access = a_Item[self.m_Table.GetFieldIDByDestiny(bd_table.TableFieldDestiny.ACCESS)] |
|
return simple_message.WorkFuncResult(self.GetMessage(Messages.SUCCESS_DELETE), None, item_access = access) |
|
|
|
async def PostDelete(self, a_CallbackQuery, a_ItemID): |
|
user_id = a_CallbackQuery.from_user.id |
|
self.m_Log.Success(f'Элемент №{a_ItemID} была удалена пользователем {user_id}.') |
|
#TODO: удалить вложенные |
|
self.OnChange() |
|
|
|
subscribe_type = bot_subscribes.SubscribeType.ANY_ITEM_DEL |
|
item_id = -1 |
|
await self.SendSubscribe(subscribe_type, item_id, user_id, item_id) |
|
|
|
subscribe_type = bot_subscribes.SubscribeType.ITEM_DEL |
|
item_id = a_ItemID |
|
await self.SendSubscribe(subscribe_type, item_id, user_id, item_id) |
|
|
|
table_name = self.m_Table.GetName() |
|
key_name = self.GetKeyFieldName() |
|
|
|
cur_item = GetCurItem(self.m_Bot, table_name, key_name, a_ItemID) |
|
|
|
parent_id_field_index = self.m_Table.GetFieldIDByDestiny(bd_table.TableFieldDestiny.PARENT_ID) |
|
if parent_id_field_index and cur_item and cur_item[parent_id_field_index]: |
|
subscribe_type = bot_subscribes.SubscribeType.ANY_ITEM_DEL_WITH_PARENT |
|
item_id = cur_item[parent_id_field_index] |
|
await self.SendSubscribe(subscribe_type, item_id, user_id, item_id) |
|
|
|
return simple_message.WorkFuncResult(self.GetMessage(Messages.SUCCESS_DELETE)) |
|
|
|
async def AddBDItemFunc(self, a_ItemData, a_UserID): |
|
table_name = self.m_Table.GetName() |
|
key_field = self.m_Table.GetFieldNameByDestiny(bd_table.TableFieldDestiny.KEY) |
|
name_field = self.m_Table.GetFieldNameByDestiny(bd_table.TableFieldDestiny.NAME) |
|
photo_field = self.m_Table.GetFieldNameByDestiny(bd_table.TableFieldDestiny.PHOTO) |
|
desc_field = self.m_Table.GetFieldNameByDestiny(bd_table.TableFieldDestiny.DESC) |
|
access_field = self.m_Table.GetFieldNameByDestiny(bd_table.TableFieldDestiny.ACCESS) |
|
create_datetime_field = self.m_Table.GetFieldNameByDestiny(bd_table.TableFieldDestiny.CREATE_DATE) |
|
parent_id_field = self.m_Table.GetFieldNameByDestiny(bd_table.TableFieldDestiny.PARENT_ID) |
|
|
|
def_access = access_utils.GetItemDefaultAccessForModule(self.m_Bot, self.GetName()) |
|
|
|
fields = [] |
|
values = [] |
|
param = () |
|
for f in self.m_Table.GetFields(): |
|
d = f.m_Destiny |
|
n = f.m_Name |
|
if d == bd_table.TableFieldDestiny.KEY: |
|
continue |
|
elif d == bd_table.TableFieldDestiny.CREATE_DATE: |
|
fields += [n] |
|
values += [bot_bd.GetBDDateTimeNow()] |
|
elif d == bd_table.TableFieldDestiny.ACCESS: |
|
fields += [n] |
|
values += ['?'] |
|
param += (def_access + f";{a_UserID}=+", ) |
|
else: |
|
fields += [n] |
|
values += ['?'] |
|
param += (a_ItemData[n], ) |
|
|
|
request = f'INSERT INTO {table_name}({",".join(fields)}) VALUES({",".join(values)})' # RETURNING {key_field} |
|
#print('request', request, param) |
|
res, error = self.m_Bot.SQLRequest(request, commit = True, return_error = True, param = param) |
|
|
|
self.OnChange() |
|
if error: |
|
self.m_Log.Error(f'Пользователь {a_UserID}. Ошибка добавления записи в таблицу {request} {param}.') |
|
else: |
|
self.m_Log.Success(f'Пользователь {a_UserID}. Добавлена запись в таблицу {request} {param}.') |
|
|
|
res_id, error_id = self.m_Bot.SQLRequest(f'SELECT rowid from {table_name} order by ROWID DESC limit 1', commit = False, return_error = True) |
|
table_item_id = -1 |
|
if not error_id and res_id and len(res_id) == 1 and len(res_id[0]) == 1: |
|
table_item_id = str(res_id[0][0]) |
|
#print('res_id', res, error, table_item_id) |
|
|
|
subscribe_type = bot_subscribes.SubscribeType.ANY_ITEM_ADD |
|
item_id = -1 |
|
await self.SendSubscribe(subscribe_type, item_id, a_UserID, table_item_id) |
|
|
|
if parent_id_field and a_ItemData[parent_id_field]: |
|
subscribe_type = bot_subscribes.SubscribeType.ANY_ITEM_ADD_WITH_PARENT |
|
item_id = a_ItemData[parent_id_field] |
|
await self.SendSubscribe(subscribe_type, item_id, a_UserID, table_item_id) |
|
|
|
return res, error |
|
|
|
async def SendMessageToUser(self, a_Message, a_UserID, a_GetButtonsFunc = None, a_GetInlineButtonsFunc = None, parse_mode = None): |
|
a_Message = a_Message.StaticCopy() |
|
a_MessageFromUSer = None |
|
user_groups = groups_utils.GetUserGroupData(self.m_Bot, a_UserID) |
|
try: |
|
#print('SendMessage', self.m_Bot, a_Message, a_GetButtonsFunc, a_GetInlineButtonsFunc, a_UserID, a_MessageFromUSer, user_groups, parse_mode) |
|
await simple_message.SendMessage(self.m_Bot, a_Message, a_GetButtonsFunc, a_GetInlineButtonsFunc, a_UserID, a_MessageFromUSer, user_groups, parse_mode=parse_mode) |
|
return True |
|
except: |
|
return False |
|
|
|
async def SendSubscribe(self, a_Type, a_ItemID, a_OwnerUserID, a_TableItem): |
|
table_name = self.m_Table.GetName() |
|
key_name = self.GetKeyFieldName() |
|
|
|
cur_item = GetCurItem(self.m_Bot, table_name, key_name, a_TableItem) |
|
for s_user_id in self.m_BotSubscribes.GetUserIDs(self.GetName(), a_Type, a_ItemID = a_ItemID): |
|
a_BotMessage = self.GetMessage(SubscribeMessage(a_Type)) |
|
#print('s_user_id', s_user_id, a_BotMessage, a_OwnerUserID, a_TableItem, cur_item) |
|
if not a_BotMessage: |
|
continue |
|
if s_user_id == a_OwnerUserID: |
|
continue |
|
a_UserID = s_user_id |
|
a_BotMessage = a_BotMessage.StaticCopy() |
|
a_BotMessage.UpdateDesc(a_BotMessage.GetDesc().replace("#item_id", str(a_TableItem))) |
|
|
|
inline_keyboard_func = None |
|
if cur_item: |
|
a_BotMessage.UpdateDesc(self.m_Table.ReplaceAllFieldTags(a_BotMessage.GetDesc(), cur_item)) |
|
inline_keyboard_func = self.GetShowItemInlineKeyboardTemplate(a_TableItem) |
|
|
|
await self.SendMessageToUser(a_BotMessage, a_UserID, a_GetInlineButtonsFunc = inline_keyboard_func) |
|
|
|
def SelectSourceTemplate(self, a_PrevPrefix, a_ButtonName): |
|
parent_id_field = self.m_Table.GetFieldNameByDestiny(bd_table.TableFieldDestiny.PARENT_ID) |
|
return bd_item_select.DBItemSelectSource(self.m_Bot, self.m_Table.GetName(), parent_id_field, a_PrevPrefix, a_ButtonName) |
|
|
|
def RegisterSelect(self, a_ButtonName, access_mode, only_parent = False): |
|
a_Prefix = None |
|
if self.m_ParentModName: |
|
parent_mod = self.GetModule(self.m_ParentModName) |
|
a_Prefix = parent_mod.RegisterSelect(a_ButtonName, access_mode, only_parent = False) |
|
|
|
if not only_parent: |
|
a_Prefix = bd_item_select.SelectRegisterHandlers(self.m_Bot, \ |
|
self.SelectSourceTemplate(a_Prefix, a_ButtonName), \ |
|
self.m_GetButtonNameAndKeyValueAndAccessFunc, \ |
|
self.GetMessage(Messages.SELECT), \ |
|
self.m_GetAccessFunc,\ |
|
access_mode = access_mode\ |
|
) |
|
|
|
return a_Prefix |
|
|
|
def AdditionalKeyboardForEditTemplate(self, a_Field, user_access = user_access.AccessMode.EDIT): |
|
if a_Field.m_Type == bd_table.TableFieldType.ENUM: |
|
def KeyboardButtons(a_Message, a_UserGroups): |
|
cur_buttons = [] |
|
for s in a_Field.m_Enum: |
|
cur_buttons += [keyboard.ButtonWithAccess(self.GetButton(EnumButton(s)), user_access, self.GetAccess()),] |
|
return keyboard.MakeButtons(self.m_Bot, cur_buttons, a_UserGroups) |
|
return KeyboardButtons |
|
return None |
|
|
|
def PostProccessingForFieldForEditTemplate(self, a_Field): |
|
if a_Field.m_Type == bd_table.TableFieldType.ENUM: |
|
def PostProccessing(a_Message): |
|
for s in a_Field.m_Enum: |
|
if a_Message == str(self.GetButton(EnumButton(s))): |
|
return str(s) |
|
return a_Message |
|
return PostProccessing |
|
return None |
|
|
|
async def OnChangeField(self, a_Field, a_ItemID, a_ItemData, a_EditUserID): |
|
subscribe_type = bot_subscribes.SubscribeType.ANY_ITEM_EDIT |
|
item_id = -1 |
|
await self.SendSubscribe(subscribe_type, item_id, a_EditUserID, a_ItemID) |
|
|
|
subscribe_type = bot_subscribes.SubscribeType.ITEM_EDIT |
|
item_id = a_ItemID |
|
await self.SendSubscribe(subscribe_type, item_id, a_EditUserID, a_ItemID) |
|
|
|
table_name = self.m_Table.GetName() |
|
key_name = self.GetKeyFieldName() |
|
|
|
cur_item = GetCurItem(self.m_Bot, table_name, key_name, a_ItemID) |
|
#print(cur_item) |
|
|
|
parent_id_field_index = self.m_Table.GetFieldIDByDestiny(bd_table.TableFieldDestiny.PARENT_ID) |
|
if parent_id_field_index and cur_item and cur_item[parent_id_field_index]: |
|
subscribe_type = bot_subscribes.SubscribeType.ANY_ITEM_EDIT_WITH_PARENT |
|
item_id = cur_item[parent_id_field_index] |
|
await self.SendSubscribe(subscribe_type, item_id, a_EditUserID, a_ItemID) |
|
|
|
def RegisterEdit(self, a_Field, a_AccessMode = user_access.AccessMode.EDIT): |
|
a_ButtonName = self.GetButton(EditButton(a_Field.m_Destiny)) |
|
a_EditMessage = self.GetMessage(EditMessage(a_Field.m_Destiny)) |
|
a_FieldName = a_Field.m_Name |
|
|
|
a_FieldType = bd_item.FieldType.text |
|
if a_Field.m_Type == bd_table.TableFieldType.PHOTO: |
|
a_FieldType = bd_item.FieldType.photo |
|
|
|
if not a_ButtonName or not a_EditMessage: |
|
return |
|
|
|
async def OnChange(a_ItemID, a_ItemData, a_EditUserID): |
|
await self.OnChangeField(a_Field, a_ItemID, a_ItemData, a_EditUserID) |
|
return self.OnChange() |
|
|
|
table_name = self.m_Table.GetName() |
|
key_name = self.GetKeyFieldName() |
|
edit_keyboard_func = self.m_GetEditKeyboardButtonsFunc |
|
GetButtonNameAndKeyValueAndAccess = self.m_GetButtonNameAndKeyValueAndAccessFunc |
|
GetAccess = self.m_GetAccessFunc |
|
|
|
a_Prefix = self.RegisterSelect(a_ButtonName, user_access.AccessMode.VIEW, only_parent = True) |
|
|
|
a_Prefix = bd_item_edit.EditBDItemRegisterHandlers(self.m_Bot, \ |
|
self.SelectSourceTemplate(a_Prefix, a_ButtonName), \ |
|
MakeFSMForEdit(self.GetName(), a_FieldName), \ |
|
self.GetMessage(Messages.SELECT_TO_EDIT), \ |
|
self.ShowMessageTemplate(a_EditMessage), \ |
|
self.ShowMessageTemplate(self.GetMessage(Messages.SUCCESS_EDIT)), \ |
|
table_name, \ |
|
key_name, \ |
|
a_FieldName, \ |
|
self.PostProccessingForFieldForEditTemplate(a_Field),\ |
|
GetButtonNameAndKeyValueAndAccess, \ |
|
GetAccess, \ |
|
self.AdditionalKeyboardForEditTemplate(a_Field),\ |
|
edit_keyboard_func, \ |
|
OnChange,\ |
|
access_mode = a_AccessMode, \ |
|
field_type = a_FieldType\ |
|
) |
|
|
|
self.m_EditPrefix.update({a_Field.m_Destiny: a_Prefix}) |
|
|
|
def GetAddFieldDestinys(self): |
|
return ( |
|
bd_table.TableFieldDestiny.NAME, |
|
bd_table.TableFieldDestiny.DESC, |
|
bd_table.TableFieldDestiny.PHOTO, |
|
bd_table.TableFieldDestiny.SUBSCRIBE_TYPE, |
|
bd_table.TableFieldDestiny.ITEM_ID, |
|
bd_table.TableFieldDestiny.USER_NAME, |
|
bd_table.TableFieldDestiny.USER_FAMILY_NAME, |
|
bd_table.TableFieldDestiny.USER_MIDDLE_NAME, |
|
bd_table.TableFieldDestiny.USER_BIRTHDAY, |
|
bd_table.TableFieldDestiny.USER_ADDRESS, |
|
bd_table.TableFieldDestiny.USER_CONTACTS, |
|
bd_table.TableFieldDestiny.USER_CONFIRM, |
|
) |
|
|
|
def GetAddFields(self): |
|
add_destiny = self.GetAddFieldDestinys() |
|
fields = [] |
|
for f in self.m_Table.GetFields(): |
|
if f.m_Destiny in add_destiny: |
|
fields += [f] |
|
return fields |
|
|
|
def AddBDItemRegisterHandlers(self, a_StartCheckFunc, a_AddBDItemFunc, a_ParentPrefix, a_ParentTableName : str, a_ParentKeyFieldName, a_GetButtonNameAndKeyValueAndAccessFunc, a_AccessFunc, a_ButtonFunc, access_mode = user_access.AccessMode.ADD): |
|
fields = self.GetAddFields() |
|
if len(fields) == 0: |
|
return |
|
fsm = MakeFSMForAdd(self.GetName(), fields) |
|
|
|
keyboard_cancel = bd_item.GetCancelKeyboardButtonsTemplate(self.m_Bot, a_AccessFunc, access_mode) |
|
keyboard_skip_and_cancel = bd_item.GetSkipAndCancelKeyboardButtonsTemplate(self.m_Bot, a_AccessFunc, access_mode) |
|
reg_func = self.m_Bot.RegisterMessageHandler |
|
|
|
if a_ParentTableName: |
|
reg_func = self.m_Bot.RegisterCallbackHandler |
|
|
|
def GetFieldType(a_Field): |
|
if a_Field.m_Type == bd_table.TableFieldType.PHOTO: |
|
return bd_item.FieldType.photo |
|
return bd_item.FieldType.text |
|
|
|
def GetContentTypes(a_Field): |
|
if a_Field.m_Type == bd_table.TableFieldType.PHOTO: |
|
return ['photo', 'text'] |
|
return ['text'] |
|
|
|
def GetKeyboard(a_Field): |
|
if a_Field.m_Type == bd_table.TableFieldType.PHOTO: |
|
return keyboard_skip_and_cancel |
|
return keyboard_cancel |
|
|
|
f_id = 0 |
|
f = fields[f_id] |
|
keyboard = bd_item.MixKeyboardFuncTemplate(self.AdditionalKeyboardForEditTemplate(f, user_access.AccessMode.ADD), GetKeyboard(f)) |
|
reg_func(bd_item_add.StartAddBDItemTemplate(self.m_Bot, fsm, getattr(fsm, f'item{f_id}'), self.ShowMessageTemplate(self.GetMessage(CreateMessage(f.m_Destiny))), a_ParentTableName, a_ParentKeyFieldName, a_ParentPrefix, a_AccessFunc, keyboard, a_ButtonFunc, access_mode), a_StartCheckFunc) |
|
|
|
for i in range(len(fields) - 1): |
|
f = fields[i] |
|
next_f = fields[i + 1] |
|
keyboard = bd_item.MixKeyboardFuncTemplate(self.AdditionalKeyboardForEditTemplate(next_f, user_access.AccessMode.ADD), GetKeyboard(next_f)) |
|
self.m_Bot.RegisterMessageHandler(bd_item_add.NextAddBDItemTemplate(self.m_Bot, fsm, None, a_ParentTableName, a_ParentKeyFieldName, f.m_Name, self.ShowMessageTemplate(self.GetMessage(CreateMessage(next_f.m_Destiny))), None, a_AccessFunc, keyboard, a_ButtonFunc, access_mode, field_type = GetFieldType(f)), content_types = GetContentTypes(f), state = getattr(fsm, f'item{i}')) |
|
|
|
f_id = len(fields) - 1 |
|
f = fields[f_id] |
|
self.m_Bot.RegisterMessageHandler(bd_item_add.FinishAddBDItemTemplate(self.m_Bot, fsm, a_AddBDItemFunc, a_ParentTableName, a_ParentKeyFieldName, f.m_Name, self.ShowMessageTemplate(self.GetMessage(Messages.SUCCESS_CREATE)), None, a_AccessFunc, a_ButtonFunc, access_mode, field_type = GetFieldType(f)), content_types = GetContentTypes(f), state = getattr(fsm, f'item{f_id}')) |
|
|
|
def GetKeyFieldDestiny(self): |
|
return bd_table.TableFieldDestiny.KEY |
|
|
|
def GetKeyFieldName(self): |
|
return self.m_Table.GetFieldNameByDestiny(self.GetKeyFieldDestiny()) |
|
|
|
def GetKeyFieldID(self): |
|
return self.m_Table.GetFieldIDByDestiny(self.GetKeyFieldDestiny()) |
|
|
|
def RegisterHandlers(self): |
|
super().RegisterHandlers() |
|
table_name = self.m_Table.GetName() |
|
key_name = self.GetKeyFieldName() |
|
name_field = self.m_Table.GetFieldNameByDestiny(bd_table.TableFieldDestiny.NAME) |
|
desc_field = self.m_Table.GetFieldNameByDestiny(bd_table.TableFieldDestiny.DESC) |
|
photo_field = self.m_Table.GetFieldNameByDestiny(bd_table.TableFieldDestiny.PHOTO) |
|
access_field = self.m_Table.GetFieldNameByDestiny(bd_table.TableFieldDestiny.ACCESS) |
|
def_access_field = self.m_Table.GetFieldNameByDestiny(bd_table.TableFieldDestiny.DEFAULT_ACCESS) |
|
parent_id_field = self.m_Table.GetFieldNameByDestiny(bd_table.TableFieldDestiny.PARENT_ID) |
|
|
|
parent_table_name = None |
|
parent_key_name = None |
|
if self.m_ParentModName: |
|
parent_mod = self.GetModule(self.m_ParentModName) |
|
parent_table_name = parent_mod.m_Table.GetName() |
|
parent_key_name = parent_mod.GetKeyFieldName() |
|
|
|
def GetViewItemInlineKeyboardTemplate(a_ItemID): |
|
return self.GetViewItemInlineKeyboardTemplate(a_ItemID) |
|
|
|
GetButtonNameAndKeyValueAndAccess = self.m_GetButtonNameAndKeyValueAndAccessFunc |
|
GetAccess = self.m_GetAccessFunc |
|
|
|
defaul_keyboard_func = self.m_GetStartKeyboardButtonsFunc |
|
|
|
# Список |
|
a_ButtonName = self.GetButton(ButtonNames.LIST) |
|
if a_ButtonName: |
|
a_Prefix = self.RegisterSelect(a_ButtonName, user_access.AccessMode.VIEW, only_parent = True) |
|
self.m_SelectPrefix = a_Prefix |
|
a_Prefix = bd_item_select.SelectRegisterHandlers(self.m_Bot,\ |
|
self.SelectSourceTemplate(a_Prefix, a_ButtonName), \ |
|
GetButtonNameAndKeyValueAndAccess,\ |
|
self.GetMessage(Messages.SELECT),\ |
|
GetAccess,\ |
|
access_mode = user_access.AccessMode.VIEW\ |
|
) |
|
self.m_ShowPrefix = a_Prefix |
|
bd_item_view.ShowBDItemRegisterHandlers(self.m_Bot,\ |
|
a_Prefix,\ |
|
table_name,\ |
|
key_name,\ |
|
self.ShowMessageTemplate(self.GetMessage(Messages.OPEN), GetViewItemInlineKeyboardTemplate, a_EnablePhoto = True),\ |
|
GetAccess,\ |
|
defaul_keyboard_func,\ |
|
access_mode = user_access.AccessMode.VIEW\ |
|
) |
|
|
|
# Удаление |
|
a_ButtonName = self.GetButton(ButtonNames.DEL) |
|
if a_ButtonName: |
|
a_Prefix = self.RegisterSelect(a_ButtonName, user_access.AccessMode.VIEW) |
|
self.m_DelPrefix = a_Prefix |
|
|
|
bd_item_delete.DeleteBDItemRegisterHandlers(self.m_Bot, \ |
|
a_Prefix, \ |
|
table_name, \ |
|
key_name, \ |
|
self.m_PreDeleteFunc, \ |
|
self.m_PostDeleteFunc, \ |
|
GetAccess, \ |
|
defaul_keyboard_func\ |
|
) |
|
|
|
# Добавление |
|
a_ButtonName = self.GetButton(ButtonNames.ADD) |
|
if a_ButtonName: |
|
a_Prefix = self.RegisterSelect(a_ButtonName, user_access.AccessMode.VIEW, only_parent = True) |
|
self.m_AddPrefix = a_Prefix |
|
|
|
check_func = bd_item.GetCheckForTextFunc(a_ButtonName) |
|
if a_Prefix: |
|
check_func = bd_item.GetCheckForPrefixFunc(a_Prefix) |
|
|
|
self.AddBDItemRegisterHandlers(\ |
|
check_func, \ |
|
self.m_AddBDItemFunc, \ |
|
a_Prefix,\ |
|
parent_table_name, \ |
|
parent_key_name, \ |
|
GetButtonNameAndKeyValueAndAccess, \ |
|
GetAccess, \ |
|
self.m_GetStartKeyboardButtonsFunc\ |
|
) |
|
|
|
# Редактирование |
|
edit_keyboard_func = self.m_GetEditKeyboardButtonsFunc |
|
a_ButtonName = self.GetButton(ButtonNames.EDIT) |
|
if a_ButtonName: |
|
self.m_Bot.RegisterMessageHandler(\ |
|
simple_message.InfoMessageTemplate(\ |
|
self.m_Bot,\ |
|
self.GetMessage(Messages.START_EDIT),\ |
|
edit_keyboard_func,\ |
|
None,\ |
|
GetAccess,\ |
|
access_mode = user_access.AccessMode.EDIT),\ |
|
bd_item.GetCheckForTextFunc(a_ButtonName)\ |
|
) |
|
|
|
for f in self.m_Table.GetFields(): |
|
self.RegisterEdit(f) |
|
|
|
def OnChange(self): |
|
pass
|
|
|