Compare commits

..

30 Commits

Author SHA1 Message Date
09def1cd63 transliteration-decoder: add automatic photo caption detection and let bot core deal with exceptions 2023-09-19 18:20:31 +03:00
604054af9e auto-schedule-pro-v2: add lookup capability to current lesson requests and make styling more flexible 2023-09-12 12:24:33 +03:00
d6bd061090 auto-schedule-pro-v2: in schedule lookup set date to be always on top even if the lesson is single 2023-09-12 11:44:03 +03:00
e57773ccbb auto-schedule-pro-v2: hotfixes and add "default" label next to auto-generated values 2023-09-12 10:04:00 +03:00
05a8039b18 auto-schedule-pro-v2: add clear option to remove custom setting value and clean up old code remnants 2023-09-12 09:52:38 +03:00
a22fb2b4b1 auto-schedule-pro-v2: hotfixing many issues at once to make the module work properly 2023-09-11 22:29:52 +03:00
1381ddb007 auto-schedule-pro-v2: implement templates support for custom output theming 2023-09-11 21:36:24 +03:00
e9bec0159f auto-schedule-pro-v2: change spacing between schedule lookup parts 2023-09-06 17:39:58 +03:00
5dc78b8cb0 auto-schedule-pro-v2: fix HTML escaping 2023-09-06 17:36:18 +03:00
67b3c4278b auto-schedule-pro-v2: fix date showing up twice during schedule lookup 2023-09-06 17:33:12 +03:00
0497cbf9b7 add support for parse_mode selection in all module APIs and update modules to respect these changes 2023-09-06 17:22:26 +03:00
2b9ac41ced improve error reporting system, switch to schedule-v2 format in auto-schedule-pro-v2 2023-09-05 20:40:57 +03:00
fc450f633e update .gitignore to not track __pycache__ folders 2023-09-05 19:22:49 +03:00
1070362bc6 auto-schedule-pro-v2: prepare for migration from schedule-v1 to schedule-v2 format 2023-09-05 19:13:52 +03:00
d2915c10e2 auto-schedule-pro: update schedule.json 2023-09-05 19:07:45 +03:00
ebdae6256e main.py: disable MarkdownV2 to avoid errors 2023-09-05 13:22:11 +03:00
8cc68080e8 auto-schedule-pro: update schedule.json 2023-09-05 13:17:15 +03:00
94275048bb auto-schedule-pro: updated schedule.json 2023-09-05 11:47:34 +03:00
1504e03e13 main.py: added temporary fix for MarkdownV2 support 2023-09-05 11:46:59 +03:00
87424c8786 transliteration-decoder: add support for MarkdownV2 2023-09-04 21:36:13 +03:00
b21b16b817 auto-schedule-pro-v2: add initial support for MarkdownV2 2023-09-04 21:34:33 +03:00
12ee02cee0 main.py: enable MarkdownV2 formatting 2023-09-04 21:33:23 +03:00
ba353a3609 auto-schedule-pro: update schedule.json 2023-09-03 07:56:45 +03:00
69cb179d87 auto-schedule-pro: update schedule for 3 semester 2023-08-08 18:18:46 +03:00
1bd7fc2ef1 auto-schedule-pro-v2: improve holiday exclusive easter egg (triggered at !пара) 2023-08-07 23:32:45 +03:00
535087fae1 auto-schedule-pro-v2: temporary change responce to !пара (holidays exclusive) 2023-08-07 22:58:32 +03:00
e8a61a9e36 auto-schedule-pro: commit last additions.json edit as of 2 semester 2023-08-07 22:33:37 +03:00
5d7f89cff0 auto-schedule-pro: fix issues related to reading links from containers 2023-08-07 22:32:10 +03:00
763cc4d131 add new module: translator 2023-08-01 12:09:35 +03:00
bd22e8e9b6 hotfix: make bot core API v1 respect recent change from self.RESPONCE to self.RESPONSE 2023-06-29 13:46:44 +03:00
23 changed files with 770 additions and 108 deletions

2
.gitignore vendored
View File

@@ -1,2 +1,4 @@
config/*
modules/irc-bridge/error.log
__pycache__/
modules/auto-schedule-pro-v2/preference-db

39
main.py
View File

@@ -7,6 +7,7 @@ import sys
import os
import threading
import importlib
import traceback
# global variables
STOP_REQUESTED = False
@@ -38,7 +39,8 @@ class ModuleV1:
# set environmental variables
def set_env(self):
self.RESPONCE = ""
self.RESPONSE = ""
self.FORMAT = ""
def set_predefine(self):
try:
@@ -54,10 +56,11 @@ class ModuleV1:
self.MESSAGE = msg
try:
exec(self.code)
return self.RESPONCE
return self.RESPONSE, self.FORMAT
except Exception as e:
print(f"[ERROR] module v1: module \"{self.path}\" ({self.alias}) raised exception \"{e}\"")
return ""
print(f"[ERROR] module v1: traceback:\ntraceback.format_exc()")
return "", None
class ModuleV2:
@@ -72,11 +75,11 @@ class ModuleV2:
# running the module
def process(self, msg):
try:
response = self.obj.process(msg, self.path)
return response
return self.obj.process(msg, self.path)
except Exception as e:
print(f"[ERROR] module v2: module \"{self.path}\" ({self.alias}) raised exception \"{e}\"")
return None
print(f"[ERROR] module v2: traceback:\ntraceback.format_exc()")
return None, None
# module control unit
@@ -188,12 +191,21 @@ def queue_processor():
# modules are used in here
for mod in mcu.modules:
if mod.enabled:
if mod.version == 1 or mod.version == 2:
responce = mod.process(msg)
if responce:
updater.bot.send_message(chat_id=msg.chat.id, text=responce,
if mod.version in [1, 2]:
response, formatting = mod.process(msg)
if response:
if formatting == None:
updater.bot.send_message(chat_id=msg.chat.id, text=response,
disable_web_page_preview=True)
print(f"Responded using module {mod.path} ({mod.alias}) with text: {responce}")
print(f"Responded using module {mod.path} ({mod.alias}) with text: {response}")
break
elif formatting in ["Markdown", "MarkdownV2", "HTML"]:
updater.bot.send_message(chat_id=msg.chat.id, text=response,
disable_web_page_preview=True,
parse_mode=formatting)
print(f"Responded using module {mod.path} ({mod.alias}) with text (using {formatting}): {response}")
break
del message_queue[0]
@@ -204,9 +216,10 @@ def queue_processor():
break
else:
time.sleep(1)
except Exception:
except Exception as e:
print(f"[ERROR] queue_processor: current message queue: {message_queue}")
print("[ERROR] queue_processor: error while processing message, trying to delete it...")
print(f"[ERROR] Traceback:\n{traceback.format_exc()}")
print(f"[ERROR] queue_processor: error while processing message ({e}), trying to delete it...")
try:
del message_queue[0]
print("[INFO] queue_processor: deleted broken message from the queue")

View File

@@ -6,6 +6,7 @@ import sys
import os
import threading
import importlib
import traceback
from telegram import Message, Chat
@@ -40,6 +41,7 @@ class ModuleV1:
# set environmental variables
def set_env(self):
self.RESPONSE = ""
self.FORMAT = ""
def set_predefine(self):
try:
@@ -55,10 +57,11 @@ class ModuleV1:
self.MESSAGE = msg
try:
exec(self.code)
return self.RESPONSE
return self.RESPONSE, self.FORMAT
except Exception as e:
print(f"[ERROR] module v1: module \"{self.path}\" ({self.alias}) raised exception \"{e}\"")
return ""
print(f"[ERROR] module v1: traceback:\n{traceback.format_exc()}")
return "", None
class ModuleV2:
@@ -73,11 +76,11 @@ class ModuleV2:
# running the module
def process(self, msg):
try:
responce = self.obj.process(msg, self.path)
return responce
return self.obj.process(msg, self.path)
except Exception as e:
print(f"[ERROR] module v2: module \"{self.path}\" ({self.alias}) raised exception \"{e}\"")
return None
print(f"[ERROR] module v2: traceback:\n{traceback.format_exc()}")
return None, None
# module control unit
@@ -188,11 +191,16 @@ def queue_processor():
# modules are used in here
for mod in mcu.modules:
if mod.enabled:
if mod.version == 1 or mod.version == 2:
response = mod.process(msg)
if mod.version in [1, 2]:
response, formatting = mod.process(msg)
if response:
if formatting == None:
print(f"Responded using module {mod.path} ({mod.alias}) with text: {response}")
break
elif formatting in ["Markdown", "MarkdownV2", "HTML"]:
print(f"Responded using module {mod.path} ({mod.alias}) with text (using {formatting}): {response}")
break
del message_queue[0]
else:
@@ -203,6 +211,7 @@ def queue_processor():
except Exception:
print(f"[ERROR] queue_processor: current message queue: {message_queue}")
print(f"[ERROR] Traceback:\n{traceback.format_exc()}")
print("[ERROR] queue_processor: error while processing message, trying to delete it...")
try:
del message_queue[0]

View File

@@ -0,0 +1,26 @@
[
{
},
{
},
{
},
{
},
{
},
{},
{},
{
},
{
},
{
},
{
},
{
},
{},
{}
]

View File

@@ -1,15 +1,19 @@
from datetime import datetime
import json
import os
def readfile(filename):
with open(module_path + filename) as f:
return f.read()
def writefile(filename, data):
with open(module_path + filename, 'w') as f:
f.write(data)
# global constants
# Accusative - znahidnyj
WEEKDAYS_ACCUSATIVE = ["понеділок", "вівторок", "середу", "четвер", "п'ятницю", "суботу", "неділю"]
# Genitive - rodovyj
WEEKDAYS_GENITIVE_NEXT = ["наступного понеділка", "наступного вівторка", "наступної середи", "наступного четверга",
"наступної п'ятниці", "наступної суботи", "наступної неділі"]
@@ -17,9 +21,119 @@ WEEKDAYS_GENITIVE_NEXT = ["наступного понеділка", "насту
WEEKDAYS_GENITIVE_THIS = ["цього понеділка", "цього вівторка", "цієї середи", "цього четверга", "цієї п'ятниці",
"цієї суботи", "цієї неділі"]
lesson_types_to_strings = {
"lec": "лекція",
"prac": "практика",
"lab": "лабораторна"
}
# global variables
module_path = ""
def get_preference_by_id(user_id, name):
if not os.path.exists(module_path + f"preference-db/{user_id}.json"):
return None
raw_prefs = readfile(f"preference-db/{user_id}.json")
try:
preferences = json.loads(raw_prefs)
except Exception as e:
return None
if not name in preferences:
return None
return preferences[name]
def get_all_preferences_by_id(user_id):
user_preferences = {
"output-style": "legacy-vibrant",
"output-style-lesson": "None",
"output-style-lookup": "None"
}
# label defaults as defaults and let custom settings override these labels
for i in user_preferences:
user_preferences[i] += " <i>(default)</i>"
for i in user_preferences:
override = get_preference_by_id(user_id, i)
if override != None:
user_preferences[i] = override
return user_preferences
def set_preference_by_id(user_id, name, value):
if not os.path.exists(module_path + "preference-db/"):
os.mkdir(module_path + "preference-db/")
preferences = {}
if os.path.exists(module_path + f"preference-db/{user_id}.json"):
try:
raw_prefs = readfile(f"preference-db/{user_id}.json")
preferences = json.loads(raw_prefs)
except Exception as e:
preferences = {}
else:
preferences = {}
preferences[name] = value
final_data = json.dumps(preferences)
writefile(f"preference-db/{user_id}.json", final_data)
def clear_preference_by_id(user_id, name):
if not os.path.exists(module_path + "preference-db/"):
os.mkdir(module_path + "preference-db/")
preferences = {}
if os.path.exists(module_path + f"preference-db/{user_id}.json"):
try:
raw_prefs = readfile(f"preference-db/{user_id}.json")
preferences = json.loads(raw_prefs)
except Exception as e:
preferences = {}
else:
preferences = {}
if name in preferences:
del preferences[name]
final_data = json.dumps(preferences)
writefile(f"preference-db/{user_id}.json", final_data)
def load_template(template, part):
return readfile(f"templates/{template}/{part}.msg")
def escaped_string_markdownV2(input_string):
result_string = input_string
symbols_to_escape = ['_', '*', '[', ']', '(', ')', '~', '`', '>', '#', '+', '-', '=', '|', '{', '}', '.', '!']
for symbol in symbols_to_escape:
result_string = result_string.replace(symbol, f"\\{symbol}")
return result_string
def escaped_string_html(input_string):
result_string = input_string
symbols_to_escape = ['<', '>']
for symbol in symbols_to_escape:
result_string = result_string.replace(symbol, f"\\{symbol}")
return result_string
def get_human_readable_date(start_datetime, end_datetime,
current_day, current_week):
@@ -43,27 +157,69 @@ def get_human_readable_date(start_datetime, end_datetime,
return human_readable_date
def generate_lesson_description(lesson, start_datetime, end_datetime, current_day, current_week, overrides={}):
output_settings = {"name": True, "date": True, "teacher": True, "link": True}
output_settings.update(overrides)
def get_name_of_lesson_type(lesson_type):
if lesson_type in lesson_types_to_strings:
return lesson_types_to_strings[lesson_type]
result = ""
if output_settings['name']:
result += f"{lesson['name']}\n"
def generate_lesson_description(lesson, start_datetime, end_datetime, current_day, current_week, overrides={},
custom_name_prefix="Назва", template="legacy-vibrant", force_date_at_top=False):
# temporarily not supported
#output_settings = {"name": True, "date": True, "teacher": True, "link": True, "comment": True}
#output_settings.update(overrides)
if output_settings['date']:
if lesson.__class__ == dict:
if force_date_at_top:
total_result = load_template(template, "date")
human_readable_date = get_human_readable_date(start_datetime, end_datetime,
current_day, current_week)
result += f"Дата: {human_readable_date}\n"
total_result = total_result.replace("%DATE%", human_readable_date)
if output_settings['teacher']:
result += f"Викладач: {lesson['teacher']}\n"
total_result += load_template(template, "multiple")
for i in ['name', 'teacher', 'link']:
total_result = total_result.replace(f"%{i.upper()}%", lesson[i])
if output_settings['link']:
result += f"Посилання на пару: {lesson['link']}"
total_result = total_result.replace("%DATE%", human_readable_date)
total_result = total_result.replace("%TYPE%", get_name_of_lesson_type(lesson['type']))
total_result = total_result.replace("%NAME_PREFIX%", custom_name_prefix)
return result
return total_result + "\n"
else:
active_template = load_template(template, "single")
for i in ['name', 'teacher', 'link']:
active_template = active_template.replace(f"%{i.upper()}%", lesson[i])
human_readable_date = get_human_readable_date(start_datetime, end_datetime,
current_day, current_week)
active_template = active_template.replace("%DATE%", human_readable_date)
active_template = active_template.replace("%TYPE%", get_name_of_lesson_type(lesson['type']))
active_template = active_template.replace("%NAME_PREFIX%", custom_name_prefix)
return active_template
elif lesson.__class__ == list:
total_result = load_template(template, "date")
human_readable_date = get_human_readable_date(start_datetime, end_datetime,
current_day, current_week)
total_result = total_result.replace("%DATE%", human_readable_date)
for l in lesson:
active_template = load_template(template, "multiple")
for i in ['name', 'teacher', 'link']:
active_template = active_template.replace(f"%{i.upper()}%", l[i])
active_template = active_template.replace("%DATE%", human_readable_date)
active_template = active_template.replace("%TYPE%", get_name_of_lesson_type(l['type']))
active_template = active_template.replace("%NAME_PREFIX%", custom_name_prefix)
total_result += active_template + "\n"
return total_result
def get_schedule_data_from(filename):
@@ -76,8 +232,15 @@ def get_schedule_data_from(filename):
timestamp = day_number * 86400 + int(lesson_time.split(":")[0]) * 3600 \
+ int(lesson_time.split(":")[1]) * 60
new_record = dict(raw_schedule[day_number][lesson_time])
new_record["source"] = filename.split(".json")[0]
new_record = raw_schedule[day_number][lesson_time]
item_source = filename.split(".json")[0]
if new_record.__class__ == list:
for item in new_record:
item["source"] = item_source
else:
new_record["source"] = item_source
baked_schedule[timestamp] = new_record
return baked_schedule
@@ -105,14 +268,16 @@ def process_arguments(args, base_day):
return preferences, selected_day
def get_lesson_description(schedule, reference_time, lesson_time, current_day, current_week, overrides={}):
def get_lesson_description(schedule, reference_time, lesson_time, current_day, current_week, overrides={},
custom_name_prefix="Назва", template="legacy-vibrant", force_date_at_top=False):
lesson_record = schedule[lesson_time]
lesson_start_datetime = datetime.fromtimestamp(reference_time + lesson_time)
lesson_end_datetime = datetime.fromtimestamp(reference_time + lesson_time + 5400)
return generate_lesson_description(lesson_record, lesson_start_datetime, lesson_end_datetime, current_day,
current_week, overrides=overrides)
current_week, overrides=overrides, custom_name_prefix=custom_name_prefix, template=template,
force_date_at_top=force_date_at_top)
def process(message, path):
@@ -124,14 +289,14 @@ def process(message, path):
# one printable symbol, so this is already protected
base_command = full_command[0].lower()
if base_command not in ["!пара", "!пари"]:
return ""
if base_command not in ["!пара", "!пари", "!schedule-ctl"]:
return None, None
global module_path
module_path = path
schedule = get_schedule_data_from("schedule.json")
schedule.update(get_schedule_data_from("additions.json"))
schedule = get_schedule_data_from("schedule-v2.json")
schedule.update(get_schedule_data_from("additions-v2.json"))
current_time = datetime.now()
@@ -144,6 +309,18 @@ def process(message, path):
reference_time = int(current_time.strftime("%s")) - current_seconds
if base_command == "!пара":
# easter egg
study_begin_ts = int(datetime(year=2023, month=9, day=4).strftime("%s"))
current_ts = int(datetime.now().strftime("%s"))
if -3600*4 < study_begin_ts - current_ts < 0:
return "Навчання от-от розпочнеться!", None
elif 0 <= study_begin_ts - current_ts < 1209600:
return f"До навчання залишилося {study_begin_ts - current_ts} секунд...", None
elif study_begin_ts - current_ts >= 1209600:
return "Ви маєте законне право відпочити, пари почнуться не скоро", None
# actual lesson finding code
upcoming_lessons = [timestamp for timestamp in schedule if timestamp > current_seconds - 5400]
if len(upcoming_lessons) > 0:
@@ -151,8 +328,34 @@ def process(message, path):
else:
closest_lesson_time = min(schedule)
return "Актуальна пара: " + get_lesson_description(schedule, reference_time, closest_lesson_time, current_day,
current_week)
# shifting lesson pointer if requested to do so
if len(full_command) >= 2:
possible_times = list(schedule.keys())
current_pointer_position = possible_times.index(closest_lesson_time)
total_list_length = len(possible_times)
if len(full_command[1]) > 1 and full_command[1][1:].isdigit():
if full_command[1][0] == "+":
current_pointer_position = (current_pointer_position + int(full_command[1][1:])) % total_list_length
else:
current_pointer_position = (current_pointer_position - int(full_command[1][1:])) % total_list_length
closest_lesson_time = possible_times[current_pointer_position]
# getting corrent style
output_style_preference = "legacy-vibrant"
general_output_style_preference = get_preference_by_id(message.from_user.id, "output-style")
if general_output_style_preference != None:
output_style_preference = general_output_style_preference
specific_output_style_preference = get_preference_by_id(message.from_user.id, "output-style-lesson")
if specific_output_style_preference != None:
output_style_preference = specific_output_style_preference
# returning generated pair description
return get_lesson_description(schedule, reference_time, closest_lesson_time, current_day,
current_week, custom_name_prefix="Актуальна пара", template=output_style_preference), "HTML"
elif base_command == "!пари":
base_day = current_week * 7 + current_day
@@ -166,8 +369,52 @@ def process(message, path):
lesson_list = [i for i in schedule if selected_day * 86400 <= i < (selected_day + 1) * 86400]
lesson_descriptions_list = ["Назва: " + get_lesson_description(schedule, reference_time, lesson_time,
current_day, current_week, overrides=preferences)
output_style_preference = "legacy-vibrant"
general_output_style_preference = get_preference_by_id(message.from_user.id, "output-style")
if general_output_style_preference != None:
output_style_preference = general_output_style_preference
specific_output_style_preference = get_preference_by_id(message.from_user.id, "output-style-lookup")
if specific_output_style_preference != None:
output_style_preference = specific_output_style_preference
lesson_descriptions_list = [get_lesson_description(schedule, reference_time, lesson_time, current_day,
current_week, overrides=preferences, custom_name_prefix="Назва", template=output_style_preference, force_date_at_top=True)
for lesson_time in lesson_list]
return f"Пари у {WEEKDAYS_ACCUSATIVE[selected_day % 7]}:\n" + "\n\n".join(lesson_descriptions_list)
return f"<b><u>Пари у {WEEKDAYS_ACCUSATIVE[selected_day % 7]}</u></b>:\n\n\n" + "\n".join(lesson_descriptions_list), "HTML"
elif base_command == "!schedule-ctl" and len(full_command) >= 2:
if full_command[1] == "list":
prefs = get_all_preferences_by_id(message.from_user.id)
return "Ваші персональні налаштування:\n" + '\n'.join([f"- {k} = {v}" for k, v in prefs.items()]), "HTML"
elif full_command[1] == "set" and len(full_command) == 4:
prefs = get_all_preferences_by_id(message.from_user.id)
if full_command[2] in prefs:
if full_command[2] in ["output-style", "output-style-lesson", "output-style-lookup"]:
if full_command[3] not in os.listdir(module_path + "templates/"):
return f"Стилю {full_command[3]} не існує; доступні варіанти: " \
+ ', '.join(os.listdir(module_path + "templates/")), "HTML"
previous_value = prefs[full_command[2]]
prefs[full_command[2]] = full_command[3]
set_preference_by_id(message.from_user.id, full_command[2], full_command[3])
return f"Змінено значення {full_command[2]}: {previous_value} -> {full_command[3]}", "HTML"
else:
return f"Такого налаштування не існує; переглянути наявні налаштування можна за допомогою команди <u>!schedule-ctl list</u>", "HTML"
elif full_command[1] == "get" and len(full_command) == 3:
requested_preference = get_preference_by_id(message.from_user.id, full_command[2])
return f"Налаштування {full_command[2]} має значення {requested_preference}", "HTML"
elif full_command[1] == "clear" and len(full_command) == 3:
clear_preference_by_id(message.from_user.id, full_command[2])
return f"Очищено значення для налаштування {full_command[2]}, надалі для нього використовуватиметься стандартне значення", "HTML"
else:
return "Такої команди не існує (або був використаний помилковий синтаксис)", "HTML"

View File

@@ -0,0 +1,286 @@
[
{
"8:30": {
"name": "Політична наука: конфліктологічний підхід",
"teacher": "Багінський Андрій Владиславович",
"link": "(посилання відсутнє!)",
"type": "lec",
"selectable": true
},
"10:25": [
{
"name": "Захист персональних даних: стандарти ЄС та Ради Європи",
"teacher": "Дубняк М. В.",
"link": "https://us04web.zoom.us/j/7423381732?pwd=c1pJclU2ZDRUWDgyUE10dmhJUDhiZz09",
"type": "lec",
"selectable": true
},
{
"name": "Психологія",
"teacher": "Волянюк Н. Ю.",
"link": "https://us04web.zoom.us/j/6762396563?pwd=L1EvTmpFZHBSdkRHUjZyRG95SFl4QT0",
"type": "lec",
"selectable": true
},
{
"name": "Психологія конфлікту",
"teacher": "Москаленко О. В.",
"link": "https://zoom.us/j/5175581158?pwd=UlhFY3lBOUUrNG9pclRVNndTNTZzQT09",
"type": "prac",
"selectable": true
}
],
"14:15": {
"name": "Основи електронного урядування",
"teacher": "Чукут Світлана Анатоліївна",
"link": "(посилання відсутнє!)",
"type": "lec",
"selectable": true
}
},
{
"12:20": {
"name": "Інженерія програмного забезпечення",
"teacher": "Васильєва Марія Давидівна",
"link": "https://zoom.us/wc/88696149166/join?from=join&_x_zm_rtaid=qhdJKhYLQNakh-zwxMG4lg.1693903841334.ad606145c892a54a4b450526e2394cbe&_x_zm_rhtaid=531",
"type": "lab",
"selectable": false,
"notice": "Код: 4VHkdw"
},
"14:15": {
"name": "Теорія електричних кіл та сигналів",
"teacher": "Лободзинський В. Ю. & Ілліна О. О.",
"link": "https://meet.google.com/gwx-sshq-sqb",
"type": "lab",
"selectable": false
}
},
{
"8:30": {
"name": "Теорія ймовірності та математична статистика",
"teacher": "Марковський Олександр Петрович",
"link": "https://bbb.comsys.kpi.ua/b/ole-9ru-7vc",
"type": "lec",
"selectable": false
},
"10:25": {
"name": "Вступ до операційної системи Linux",
"teacher": "Роковий Олександр Петрович",
"link": "https://bbb.comsys.kpi.ua/b/ole-knq-z9h-pyl",
"type": "lec",
"selectable": false
},
"12:20": {
"name": "Інженерія програмного забезпечення",
"teacher": "Васильєва Марія Давидівна",
"link": "(посилання відсутнє!)",
"type": "lec",
"selectable": false
}
},
{
"10:25": {
"name": "Вища математика. Частина 3. Ряди. Теорія функцій комплексної змінної. Операційне числення",
"teacher": "Стаматієва Вікторія В'ячеславівна",
"link": "(посилання відсутнє!)",
"type": "prac",
"selectable": false
},
"12:20": {
"name": "Практичний курс іноземної мови. Частина 2",
"teacher": "Шевченко Ольга Миколаївна",
"link": "(старе посилання!) https://meet.google.com/bwg-pdnr-evh",
"type": "prac",
"selectable": false
},
"14:15": {
"name": "Соціальна психологія",
"teacher": "Блохіна Ірина Олександрівна",
"link": "(посилання відсутнє!)",
"type": "prac",
"selectable": true
},
"16:10": {
"name": "Основи електронного урядування",
"teacher": "Чукут Світлана Анатоліївна",
"link": "(посилання відсутнє!)",
"type": "prac",
"selectable": true
}
},
{
"8:30": {
"name": "Вступ до філософії",
"teacher": "Руденко Тамара Петрівна",
"link": "(посилання відсутнє!)",
"type": "lec",
"selectable": false
},
"10:25": {
"name": "Теорія електричних кіл та сигналів",
"teacher": "Лободзинський Вадим Юрійович",
"link": "https://meet.google.com/gwx-sshq-sqb",
"type": "lec",
"selectable": false
},
"12:20": {
"name": "Вища математика. Частина 3. Ряди. Теорія функцій комплексної змінної. Операційне числення",
"teacher": "Овчар Раїса Федорівна",
"link": "(посилання відсутнє!)",
"type": "lec",
"selectable": false
}
},
{},
{},
{
"10:25": [
{
"name": "Психологія",
"teacher": "Сербова О. В.",
"link": "https://us04web.zoom.us/j/6762396563?pwd=L1EvTmpFZHBSdkRHUjZyRG95SFl4QT09",
"type": "prac",
"selectable": true
},
{
"name": "Психологія конфлікту",
"teacher": "Кононець М. О.",
"link": "https://zoom.us/j/5175581158?pwd=UlhFY3lBOUUrNG9pclRVNndTNTZzQT09",
"type": "lec",
"selectable": true
}
],
"12:20": [
{
"name": "Політична наука: конфліктологічний підхід",
"teacher": "Северинчик О. П.",
"link": "https://zoom.us/j/5175581158?pwd=UlhFY3lBOUUrNG9pclRVNndTNTZzQT09",
"type": "prac",
"selectable": true
},
{
"name": "Захист персональних даних: стандарти ЄС та Ради Європи",
"teacher": "Самчинська О. А.",
"link": "(посилання відсутнє!)",
"type": "prac",
"selectable": true
}
],
"14:15": {
"name": "Розумні міста",
"teacher": "Чукут Світлана Анатоліївна",
"link": "(посилання відсутнє!)",
"type": "lec",
"selectable": true
}
},
{
"10:25": {
"name": "Вступ до філософії",
"teacher": "Руденко Тамара Петрівна",
"link": "(посилання відсутнє!)",
"type": "prac",
"selectable": false
},
"14:15": {
"name": "Теорія ймовірності та математична статистика",
"teacher": "Марковський Олександр Петрович",
"link": "https://bbb.comsys.kpi.ua/b/ole-9ru-7vc",
"type": "prac",
"selectable": false
}
},
{
"8:30": {
"name": "Теорія ймовірності та математична статистика",
"teacher": "Марковський Олександр Петрович",
"link": "https://bbb.comsys.kpi.ua/b/ole-9ru-7vc",
"type": "lec",
"selectable": false
},
"10:25": {
"name": "Вступ до операційної системи Linux",
"teacher": "Роковий Олександр Петрович",
"link": "https://bbb.comsys.kpi.ua/b/ole-knq-z9h-pyl",
"type": "lec",
"selectable": false
},
"12:20": {
"name": "Інженерія програмного забезпечення",
"teacher": "Васильєва Марія Давидівна",
"link": "(посилання відсутнє!)",
"type": "lec",
"selectable": false
},
"14:15": {
"name": "Інженерія програмного забезпечення",
"teacher": "Васильєва Марія Давидівна",
"link": "(посилання відсутнє!)",
"type": "lec",
"selectable": false
}
},
{
"8:30": {
"name": "Вступ до операційної системи Linux",
"teacher": "Алєнін Олег Ігорович",
"link": "(посилання відсутнє!)",
"type": "lab",
"selectable": false
},
"10:25": {
"name": "Вища математика. Частина 3. Ряди. Теорія функцій комплексної змінної. Операційне числення",
"teacher": "Стаматієва Вікторія В'ячеславівна",
"link": "(старе посилання!) https://us04web.zoom.us/j/2313886209?pwd=dnZHanV3cU9LUXJBVWYyYVArUFg5dz09",
"type": "prac",
"selectable": false
},
"12:20": {
"name": "Практичний курс іноземної мови. Частина 2",
"teacher": "Шевченко Ольга Миколаївна",
"link": "(старе посилання!) https://meet.google.com/bwg-pdnr-evh",
"type": "prac",
"selectable": false
},
"14:15": [
{
"name": "Соціальна психологія",
"teacher": "Винославська О. В.",
"link": "(посилання відсутнє!)",
"type": "lec",
"selectable": true
},
{
"name": "Розумні міста",
"teacher": "Чукут С. А.",
"link": "(посилання відсутні!)",
"type": "prac",
"selectable": true
}
]
},
{
"10:25": {
"name": "Теорія електричних кіл та сигналів",
"teacher": "Лободзинський Вадим Юрійович",
"link": "https://meet.google.com/gwx-sshq-sqb",
"type": "lec",
"selectable": false
},
"12:20": {
"name": "Вища математика. Частина 3. Ряди. Теорія функцій комплексної змінної. Операційне числення",
"teacher": "Овчар Раїса Федорівна",
"link": "(посилання відсутнє!)",
"type": "lec",
"selectable": false
}
},
{},
{}
]

View File

@@ -0,0 +1 @@
<b><u>%DATE%</u></b>:

View File

@@ -0,0 +1,3 @@
<b>%NAME_PREFIX%</b>: %NAME% (%TYPE%)
<b>Викладач</b>: %TEACHER%
<b>Посилання</b>: %LINK%

View File

@@ -0,0 +1,4 @@
<b>%NAME_PREFIX%</b>: %NAME% (%TYPE%)
<b>Дата</b>: %DATE%
<b>Викладач</b>: %TEACHER%
<b>Посилання</b>: %LINK%

View File

@@ -0,0 +1 @@
<u>%DATE%</u>:

View File

@@ -0,0 +1,3 @@
%NAME_PREFIX%: %NAME% (%TYPE%)
Викладач: %TEACHER%
Посилання: %LINK%

View File

@@ -0,0 +1,4 @@
%NAME_PREFIX%: %NAME% (%TYPE%)
Дата: %DATE%
Викладач: %TEACHER%
Посилання: %LINK%

View File

@@ -0,0 +1 @@
<b><u>%DATE%</u></b>:

View File

@@ -0,0 +1,3 @@
<b>%NAME%</b> (%TYPE%)
<i>Викладач</i>: %TEACHER%
<i>Посилання</i>: %LINK%

View File

@@ -0,0 +1,4 @@
<b>%NAME%</b> (%TYPE%)
<i>Дата</i>: %DATE%
<i>Викладач</i>: %TEACHER%
<i>Посилання</i>: %LINK%

View File

@@ -1,6 +1,5 @@
[
{
"12:20": {"name": "Культура мовлення та ділове мовлення", "teacher": "Кушлаба М. П.", "link": "https://bbb.comsys.kpi.ua/b/myk-0iw-red-p01"}
},
{
},

View File

@@ -1,52 +1,55 @@
[
{
"8:30": {"name": "Дискретна математика (лекція)", "teacher": "Новотарський М. А.", "link": "https://us02web.zoom.us/j/87578307057?pwd=UGwyVGlwc3M4Q0Q0Q0NLWUt6bmVpUT09"},
"10:25": {"name": "Комп'ютерна логіка (лекція)", "teacher": "Жабін В. І.", "link": "https://bbb.comsys.kpi.ua/b/val-2vb-o7w-y5y АБО https://bbb.ugrid.org/b/val-osi-lup-ou8"},
"12:20": {"name": "Культура мовлення та ділове мовлення (лекція)", "teacher": "Онуфрієнко О. П.", "link": "В житті не буває нічого вічного. Життя мінливе, як і посилання на кожну нову пару. Щасти вам його віднайти!"}
"8:30": {"name": "Політична наука: конфліктологічний підхід (лекція)", "teacher": "Багінський Андрій Владиславович", "link": "(посилання відсутнє!)"},
"10:25": {"name": "Захист персональних даних: стандарти ЄС та Ради Європи & Психологія & Психологія конфлікту (лекції/практики)", "teacher": "Дубняк М. В. & Волянюк Н. Ю. & Москаленко О. В.", "link": "https://us04web.zoom.us/j/7423381732?pwd=c1pJclU2ZDRUWDgyUE10dmhJUDhiZz09 & https://us04web.zoom.us/j/6762396563?pwd=L1EvTmpFZHBSdkRHUjZyRG95SFl4QT09 & https://zoom.us/j/5175581158?pwd=UlhFY3lBOUUrNG9pclRVNndTNTZzQT09"},
"14:15": {"name": "Основи електронного урядування (лекція)", "teacher": "Чукут Світлана Анатоліївна", "link": "(посилання відсутнє!)"}
},
{
"12:20": {"name": "Англійська мова I (практика)", "teacher": "Шевченко О. М.", "link": "https://meet.google.com/bwg-pdnr-evh"},
"14:15": {"name": "Фізика (лабораторна)", "teacher": "Федотов В. В. & Іванова І. М.", "link": "В житті не буває нічого вічного. Життя мінливе, як і посилання на кожну нову пару. Щасти вам його віднайти!"}
"12:20": {"name": "Інженерія програмного забезпечення (лабораторна)", "teacher": "Васильєва Марія Давидівна", "link": "https://zoom.us/wc/88696149166/join?from=join&_x_zm_rtaid=qhdJKhYLQNakh-zwxMG4lg.1693903841334.ad606145c892a54a4b450526e2394cbe&_x_zm_rhtaid=531"},
"14:15": {"name": "Теорія електричних кіл та сигналів (лабораторна)", "teacher": "Лободзинський В. Ю. & Ілліна О. О.", "link": "https://meet.google.com/gwx-sshq-sqb"}
},
{
"8:30": {"name": "Програмування II. Об'єктно-орієнтоване програмування (лабораторна)", "teacher": "Алещенко О. В.", "link": "https://us02web.zoom.us/j/2711546637?pwd=Ry82RHp3SjV6WTZRMXl6WUNod25hUT09"},
"10:25": {"name": "Вища математика (практика)", "teacher": "Ординська З. П.", "link": "https://us04web.zoom.us/j/2684350438?pwd=kiOi3BrgbJHeYvkrx7qaSxa08J8m8O.1"}
"8:30": {"name": "Теорія ймовірності та математична статистика (лекція)", "teacher": "Марковський Олександр Петрович", "link": "https://bbb.comsys.kpi.ua/b/ole-9ru-7vc"},
"10:25": {"name": "Вступ до операційної системи Linux (лекція)", "teacher": "Роковий Олександр Петрович", "link": "https://bbb.comsys.kpi.ua/b/ole-knq-z9h-pyl"},
"12:20": {"name": "Інженерія програмного забезпечення (лекція)", "teacher": "Васильєва Марія Давидівна", "link": "(посилання відсутнє!)"}
},
{
"10:25": {"name": "Вища математика (лекція)", "teacher": "Ординська З. П.", "link": "https://us04web.zoom.us/j/2684350438?pwd=kiOi3BrgbJHeYvkrx7qaSxa08J8m8O.1"},
"12:20": {"name": "Фізика (лекція)", "teacher": "Русаков В. Ф.", "link": "В житті не буває нічого вічного. Життя мінливе, як і посилання на кожну нову пару. Щасти вам його віднайти!", "container_id": "1"},
"14:15": {"name": "Програмування II. Об'єктно-орієнтоване програмування (лекція)", "teacher": "Алещенко О. В.", "link": "https://us02web.zoom.us/j/2711546637?pwd=Ry82RHp3SjV6WTZRMXl6WUNod25hUT09"}
"10:25": {"name": "Вища математика. Частина 3. Ряди. Теорія функцій комплексної змінної. Операційне числення (практика)", "teacher": "Стаматієва Вікторія В'ячеславівна", "link": "(посилання відсутнє!)"},
"12:20": {"name": "Практичний курс іноземної мови. Частина 2 (практика)", "teacher": "Шевченко Ольга Миколаївна", "link": "(старе посилання!) https://meet.google.com/bwg-pdnr-evh"},
"14:15": {"name": "Соціальна психологія (практика)", "teacher": "Блохіна Ірина Олександрівна", "link": "(посилання відсутнє!)"},
"16:10": {"name": "Основи електронного урядування (практика)", "teacher": "Чукут Світлана Анатоліївна", "link": "(посилання відсутнє!)"}
},
{
"10:25": {"name": "Фізика (практика)", "teacher": "Русаков В. Ф.", "link": "В житті не буває нічого вічного. Життя мінливе, як і посилання на кожну нову пару. Щасти вам його віднайти!", "container_id": "1"},
"12:20": {"name": "Дискретна математика (лабораторна)", "teacher": "Пономаренко А. М.", "link": "https://us05web.zoom.us/j/7089075754?pwd=TWRlZmxyVlFiTWU1UGlVVU1XcFE0Zz09"},
"14:15": {"name": "Основи здорового способу життя (практика)", "teacher": "Соболенко А. І.", "link": "https://zoom.us/j/2035574145?pwd=bk1wTVhGbjJsQTR4WmVQMlROWFBCZz09"}
"8:30": {"name": "Вступ до філософії (лекція)", "teacher": "Руденко Тамара Петрівна", "link": "(посилання відсутнє!)"},
"10:25": {"name": "Теорія електричних кіл та сигналів (лекція)", "teacher": "Лободзинський Вадим Юрійович", "link": "https://meet.google.com/gwx-sshq-sqb"},
"12:20": {"name": "Вища математика. Частина 3. Ряди. Теорія функцій комплексної змінної. Операційне числення (лекція)", "teacher": "Овчар Раїса Федорівна", "link": "(посилання відсутнє!)"}
},
{},
{},
{
"8:30": {"name": "Дискретна математика (лекція)", "teacher": "Новотарський М. А.", "link": "https://us02web.zoom.us/j/87578307057?pwd=UGwyVGlwc3M4Q0Q0Q0NLWUt6bmVpUT09"},
"10:25": {"name": "Комп'ютерна логіка (лекція)", "teacher": "Жабін В. І.", "link": "https://bbb.comsys.kpi.ua/b/val-2vb-o7w-y5y АБО https://bbb.ugrid.org/b/val-osi-lup-ou8"},
"12:20": {"name": "Вища математика (лекція)", "teacher": "Ординська З. П.", "link": "https://us04web.zoom.us/j/2684350438?pwd=kiOi3BrgbJHeYvkrx7qaSxa08J8m8O.1"}
"10:25": {"name": "Психологія & Психологія конфлікту (практики)", "teacher": "Сербова О. В. & Кононець М. О.", "link": "https://us04web.zoom.us/j/6762396563?pwd=L1EvTmpFZHBSdkRHUjZyRG95SFl4QT09 & https://zoom.us/j/5175581158?pwd=UlhFY3lBOUUrNG9pclRVNndTNTZzQT09"},
"12:20": {"name": "Політична наука: конфліктологічний підхід & Захист персональних даних: стандарти ЄС та Ради Європи (практики)", "teacher": "Северинчик О. П. & Самчинська О. А.", "link": "https://zoom.us/j/5175581158?pwd=UlhFY3lBOUUrNG9pclRVNndTNTZzQT09 & (посилання відсутнє!)"},
"14:15": {"name": "Розумні міста (лекція)", "teacher": "Чукут Світлана Анатоліївна", "link": "(посилання відсутнє!)"}
},
{
"8:30": {"name": "Комп'ютерна логіка (лабораторна)", "teacher": "Верба О. А.", "link": "https://us04web.zoom.us/j/7382214783?pwd=RnZ3SWgwK1JoVkZtNndnKzdPZjFGdz09"},
"10:25": {"name": "Вища математика (практика)", "teacher": "Ординська З. П.", "link": "https://us04web.zoom.us/j/2684350438?pwd=kiOi3BrgbJHeYvkrx7qaSxa08J8m8O.1"},
"12:20": {"name": "Англійська мова I (практика)", "teacher": "Шевченко О. М.", "link": "https://meet.google.com/bwg-pdnr-evh"},
"14:15": {"name": "Фізика (лабораторна)", "teacher": "Федотов В. В. & Іванова І. М.", "link": "В житті не буває нічого вічного. Життя мінливе, як і посилання на кожну нову пару. Щасти вам його віднайти!"}
"10:25": {"name": "Вступ до філософії (практика)", "teacher": "Руденко Тамара Петрівна", "link": "(посилання відсутнє!)"},
"14:15": {"name": "Теорія ймовірності та математична статистика (практика)", "teacher": "Марковський Олександр Петрович", "link": "(посилання відсутнє!)"}
},
{
"10:25": {"name": "Вища математика (практика)", "teacher": "Ординська З. П.", "link": "https://us04web.zoom.us/j/2684350438?pwd=kiOi3BrgbJHeYvkrx7qaSxa08J8m8O.1"}
"8:30": {"name": "Теорія ймовірності та математична статистика (лекція)", "teacher": "Марковський Олександр Петрович", "link": "https://bbb.comsys.kpi.ua/b/ole-9ru-7vc"},
"10:25": {"name": "Вступ до операційної системи Linux (лекція)", "teacher": "Роковий Олександр Петрович", "link": "https://bbb.comsys.kpi.ua/b/ole-knq-z9h-pyl"},
"12:20": {"name": "Інженерія програмного забезпечення (лекція)", "teacher": "Васильєва Марія Давидівна", "link": "(посилання відсутнє!)"},
"14:15": {"name": "Інженерія програмного забезпечення (лекція)", "teacher": "Васильєва Марія Давидівна", "link": "(посилання відсутнє!)"}
},
{
"10:25": {"name": "Вища математика (лекція)", "teacher": "Ординська З. П.", "link": "https://us04web.zoom.us/j/2684350438?pwd=kiOi3BrgbJHeYvkrx7qaSxa08J8m8O.1"},
"12:20": {"name": "Фізика (лекція)", "teacher": "Русаков В. Ф.", "link": "В житті не буває нічого вічного. Життя мінливе, як і посилання на кожну нову пару. Щасти вам його віднайти!", "container_id": "1"},
"14:15": {"name": "Програмування II. Об'єктно-орієнтоване програмування (лекція)", "teacher": "Алещенко О. В.", "link": "https://us02web.zoom.us/j/2711546637?pwd=Ry82RHp3SjV6WTZRMXl6WUNod25hUT09"}
"8:30": {"name": "Вступ до операційної системи Linux (лабораторна)", "teacher": "Алєнін Олег Ігорович", "link": "(посилання відсутнє!)"},
"10:25": {"name": "Вища математика. Частина 3. Ряди. Теорія функцій комплексної змінної. Операційне числення (практика)", "teacher": "Стаматієва Вікторія В'ячеславівна", "link": "(старе посилання!) https://us04web.zoom.us/j/2313886209?pwd=dnZHanV3cU9LUXJBVWYyYVArUFg5dz09"},
"12:20": {"name": "Практичний курс іноземної мови. Частина 2 (практика)", "teacher": "Шевченко Ольга Миколаївна", "link": "(старе посилання!) https://meet.google.com/bwg-pdnr-evh"},
"14:15": {"name": "Соціальна психологія (лекція) & Розумні міста (практика)", "teacher": "Винославська О. В. & Чукут С. А.", "link": "(посилання відсутні!)"}
},
{
"10:25": {"name": "Фізика (практика)", "teacher": "Русаков В. Ф.", "link": "В житті не буває нічого вічного. Життя мінливе, як і посилання на кожну нову пару. Щасти вам його віднайти!", "container_id": "1"},
"12:20": {"name": "Культура мовлення та ділове мовлення (практика)", "teacher": "Кушлаба М. П.", "link": "https://bbb.comsys.kpi.ua/b/myk-0iw-red-p01"},
"14:15": {"name": "Основи здорового способу життя (практика)", "teacher": "Соболенко А. І.", "link": "https://zoom.us/j/2035574145?pwd=bk1wTVhGbjJsQTR4WmVQMlROWFBCZz09"}
"10:25": {"name": "Теорія електричних кіл та сигналів (лекція)", "teacher": "Лободзинський Вадим Юрійович", "link": "https://meet.google.com/gwx-sshq-sqb"},
"12:20": {"name": "Вища математика. Частина 3. Ряди. Теорія функцій комплексної змінної. Операційне числення (лекція)", "teacher": "Овчар Раїса Федорівна", "link": "(посилання відсутнє!)"}
},
{},
{}

View File

@@ -1,5 +1,6 @@
import datetime
import json
import time
import os
current_time = datetime.datetime.now()
@@ -84,7 +85,7 @@ if next_pair_time == None:
#print("test3.1.5")
if 'container_id' in p:
try:
cont = json.decode(open(f"../containers/{p['container_id']}", 'r').read())
cont = json.loads(open(f"../containers/{p['container_id']}", 'r').read())
if (time.time() - cont['update_ts']) > 43200:
if ("QUERY_STRING" in os.environ) and ("force" in os.environ['QUERY_STRING'].lower()):
print(f"Location: {cont['link']}\n\n", end = '')
@@ -102,7 +103,7 @@ if next_pair_time == None:
new_seed = os.environ['REMOTE_ADDR'] + datetime.datetime.now().replace(minute = 0, second = 0).strftime("%s")
random.seed(new_seed)
surprise_pool = ["Йой!", "От халепа!", "Ой лишенько!"]
print(f"Content-Type: text/html; charset=UTF-8\n\n<h2>{random.choice(surprise_pool)}</h2><br><p>Під час спроби отримання посилання на пару {p['name']} сталася непередбачена помилка. Ви можете оновлювати сторінку, поки проблема не зникне (перенаправлення відбудеться, щойно все запрацює), або пошукати посилання де-інде.</p><p>Вибачте за тимчасові незручності(</p>")
print(f"Content-Type: text/html; charset=UTF-8\n\n<h2>{random.choice(surprise_pool)}</h2><br><p>Під час спроби отримання посилання на пару {p['name']} сталася непередбачена помилка. Ви можете оновлювати сторінку, поки проблема не зникне (перенаправлення відбудеться, щойно все запрацює), або пошукати посилання де-інде.</p><p>Вибачте за тимчасові незручності(</p><p>(технічна інформація про помилку: {e}</p>")
else:
print(f"Location: {p['link'].split()[0]}\n\n", end = '')
@@ -139,7 +140,7 @@ else:
if 'container_id' in p:
try:
cont = json.decode(open(f"../containers/{p['container_id']}", 'r').read())
cont = json.loads(open(f"../containers/{p['container_id']}", 'r').read())
if (time.time() - cont['update_ts']) > 43200:
if ("QUERY_STRING" in os.environ) and ("force" in os.environ['QUERY_STRING'].lower()):
print(f"Location: {cont['link']}\n\n", end = '')
@@ -157,7 +158,7 @@ else:
new_seed = os.environ['REMOTE_ADDR'] + datetime.datetime.now().replace(minute = 0, second = 0).strftime("%s")
random.seed(new_seed)
surprise_pool = ["Йой!", "От халепа!", "Ой лишенько!"]
print(f"Content-Type: text/html; charset=UTF-8\n\n<h2>{random.choice(surprise_pool)}</h2><br><p>Під час спроби отримання посилання на пару {p['name']} сталася непередбачена помилка. Ви можете оновлювати сторінку, поки проблема не зникне (перенаправлення відбудеться, щойно все запрацює), або пошукати посилання де-інде.</p><p>Вибачте за тимчасові незручності(</p>")
print(f"Content-Type: text/html; charset=UTF-8\n\n<h2>{random.choice(surprise_pool)}</h2><br><p>Під час спроби отримання посилання на пару {p['name']} сталася непередбачена помилка. Ви можете оновлювати сторінку, поки проблема не зникне (перенаправлення відбудеться, щойно все запрацює), або пошукати посилання де-інде.</p><p>Вибачте за тимчасові незручності(</p><p>(технічна інформація про помилку: {e}</p>")
else:
print(f"Location: {p['link'].split()[0]}\n\n", end = '')

View File

@@ -13,4 +13,6 @@ def get_num():
def process(message, path):
if message.text == "!v2-testing":
return f"Testing successful - call number {get_num()}"
return f"Testing successful - call number {get_num()}", None
else:
return None, None

View File

@@ -0,0 +1,34 @@
command = self.MESSAGE['text'].split(" ", 2)
command_length = len(command)
if (command[0] in self.aliases) and (1 <= command_length <= 3):
try:
import requests
if command_length == 1:
chosen_model = "auto-uk"
else:
chosen_model = command[1]
source, target = chosen_model.split("-")
if command_length == 3:
text_to_translate = command[2]
else:
text_to_translate = self.MESSAGE['reply_to_message']['text']
data = {"q": text_to_translate,
"source": source,
"target": target,
"format": "text"}
res = requests.post("http://127.0.0.1:5000/translate", data = data)
result = json.loads(res.text)
if source == "auto":
self.RESPONSE = f"Результат ({result['detectedLanguage']['language']} - {result['detectedLanguage']['confidence']}%): {result['translatedText']}"
else:
self.RESPONSE = f"Результат: {result['translatedText']}"
except Exception as e:
print(f"[translit-decoder] Got exception: {e}")

View File

@@ -0,0 +1,7 @@
{
"version": 1,
"index_file": "index.py",
"start_on_boot": true,
"alias": "translator",
"predefine": "predefine.py"
}

View File

@@ -0,0 +1 @@
self.aliases = ["!translate", "!t"]

View File

@@ -1,8 +1,15 @@
command = self.MESSAGE['text'].split(" ", 2)
command_length = len(command)
def escaped_string(unescaped_string):
result_string = str(unescaped_string)
for i in ["<", ">"]:
result_string = result_string.replace(i, f"\\{i}")
return result_string
if (command[0] in self.aliases) and (1 <= command_length <= 3):
try:
models = json.loads(readfile(self.path + "translate_models.json"))
if command_length == 1:
@@ -13,7 +20,10 @@ if (command[0] in self.aliases) and (1 <= command_length <= 3):
if command_length == 3:
text_to_decode = command[2]
else:
text_to_decode = self.MESSAGE['reply_to_message']['text']
if self.MESSAGE['reply_to_message'].caption:
text_to_decode = self.MESSAGE['reply_to_message'].caption
elif self.MESSAGE['reply_to_message'].text:
text_to_decode = self.MESSAGE['reply_to_message'].text
decoded_text = text_to_decode
if chosen_model not in models:
@@ -25,7 +35,5 @@ if (command[0] in self.aliases) and (1 <= command_length <= 3):
decoded_text = decoded_text.replace(i[0].capitalize(), i[1].capitalize())
decoded_text = decoded_text.replace(i[0].upper(), i[1].upper())
self.RESPONSE = f"Результат: {decoded_text}"
except Exception as e:
print(f"[translit-decoder] Got exception: {e}")
self.RESPONSE = f"<b><u>Результат</u></b>\n{escaped_string(decoded_text)}"
self.FORMAT = "HTML"