Example #1
0
def _action_battle_report(cid, user, content, update, context):
    """
    Update user info from battle report
    """
    if settings.VERBOSE:
        print("            Battle report")
    try:
        user.cw_name = content.split(settings.GUILD_NAME)[1].split(
            b' \\u2694:')[0].decode("unicode_escape")
        user.cw_level = int(
            content.split(b' Lvl: ')[1].split(b'\\n')[0].decode(
                "unicode_escape"))
        if user.cw_name and user.cw_level:
            if model.user_by_id(update.effective_user.id):
                status = model.update_user(user)
            else:
                status = model.subscribe(user)
            if settings.VERBOSE:
                print("            {0} Lvl: {1} Status: {2}".format(
                    user.cw_name, user.cw_level, status))
    except Exception as e:
        utils._admin_error(context,
                           "_action_battle_report: battle report",
                           user=user,
                           error=str(e))
Example #2
0
def _action_roster(cid, user, content, update, context):
    """
    Show sleepy members
    """
    content = content.split(b'\\n')[1:]
    # check UTC battle
    utcnow = datetime.datetime.utcnow()
    time_list = []
    for t in settings.BATTLES:
        time_list.append(
            (utcnow - datetime.datetime(year=utcnow.year,
                                        month=utcnow.month,
                                        day=utcnow.day,
                                        hour=int(t[0:2]),
                                        minute=int(t[3:5]))).total_seconds() /
            60.0)
    delta = int(model.get_data("BATTLE_TIME_DELTA_MINUTES", 20))
    time_list = [t > -delta and t < 0 for t in time_list]
    print("            Roster", time_list, delta)
    # call to the battle
    if True in time_list:
        i = 0
        tmp = ""
        header = u'\U0001F4E2 The battle is coming\n'
        for player in content:
            if b' [\\u2694] ' not in player and b' [\\U0001f6e1] ' not in player and b' [\\U0001f4a4] ' not in player:
                cw_name = b' '.join(player.split(b' ')[3:]).decode()
                user = model.user_by_cw_name(cw_name)
                if user:
                    tmp += "@{0} ".format(user.username)
                    i += 1
                if not i % 3:
                    i = 0
                    try:
                        if tmp:
                            context.bot.send_message(
                                chat_id=cid,
                                text=header + tmp,
                                parse_mode=telegram.ParseMode.HTML,
                                disable_web_page_preview=True)
                    except Exception as e:
                        utils._admin_error(context,
                                           "_action_roster: attention",
                                           user=user,
                                           error=str(e))
                    tmp = ""
        if tmp:
            try:
                context.bot.send_message(chat_id=cid,
                                         text=header + tmp,
                                         parse_mode=telegram.ParseMode.HTML,
                                         disable_web_page_preview=True)
            except Exception as e:
                utils._admin_error(context,
                                   "_action_roster: attention",
                                   user=user,
                                   error=str(e))
Example #3
0
def _error(update, context):
    logger.warning('Update "%s" caused error "%s"', update, context.error)
    # send the error message to the admin
    utils._admin_error(context, "INTERNAL ERROR", error=str(context.error))
    return
    # send the error message to current user if is valid
    try:
        context.bot.send_message(chat_id=update.effective_user.id, 
                                 text=settings.MESSAGES["application-error"].format(update._effective_message.text, context.error), 
                                 parse_mode=telegram.ParseMode.HTML)
    except Exception as e:
        print("[EXCEPTION] user _error", e)
Example #4
0
def message(update, context):
    """
    Send a message to each user
    """
    try:
        if str(update.effective_user.id) == settings.ADMIN_ID:
            # message hint
            if update.message.text == "/message":
                text = 'Use /message <i>text</i> for send the current text to each subscribed user\n\nThe text can be formatted:\n{0} user full name\n{1} admin link'
                context.bot.send_message(chat_id=settings.ADMIN_ID,
                                         text=text,
                                         parse_mode=telegram.ParseMode.HTML,
                                         disable_web_page_preview=True)
            # build and send message
            else:
                text = update.message.text[9:]
                text.format("", html.escape(settings.ADMIN_CONTACT))
                counter_success = 0
                counter_fail = 0
                list_fail = []
                users = model.users()
                for user in users:
                    try:
                        context.bot.send_message(
                            chat_id=user.id,
                            text=text.format(
                                html.escape(user.full_name),
                                html.escape(settings.ADMIN_CONTACT)),
                            parse_mode=telegram.ParseMode.HTML,
                            disable_web_page_preview=True)
                        counter_success += 1
                    except Exception as e:
                        counter_fail += 1
                        list_fail.append(user.full_name)
                # send report to the admin
                report_text = '<b>Message:</b> {0}\n\n<b>Subscribed users:</b> {1}\n<b>Successful deliveries:</b> {2}\n<b>Unsuccessful deliveries:</b> {3}'.format(
                    text.format("USER", html.escape(settings.ADMIN_CONTACT)),
                    len(users), counter_success, counter_fail)
                if list_fail:
                    report_text += "\n<b>Unsuccessful users:</b> {0}".format(
                        ", ".join(list_fail))
                context.bot.send_message(chat_id=settings.ADMIN_ID,
                                         text=report_text,
                                         parse_mode=telegram.ParseMode.HTML,
                                         disable_web_page_preview=True)
    except Exception as e:
        utils._admin_error(context, "/message", error=str(e), trace=False)
Example #5
0
def elite(update, context):
    """
    Mention the elite 
    """
    cid=update.message.chat.id
    
    # validate user
    if not utils._check_user(context, update.effective_user.id, cid):
        return 
        
    # telegram user
    user=model.User(id=update.effective_user.id,
                    username=update.effective_user.username,
                    full_name=update.effective_user.full_name,
                    link=update.effective_user.link,
                    is_bot=update.effective_user.is_bot)
    # mention users
    users=model.users()
    i=0
    tmp=""
    max_cw_level=0
    for u in users:
        if u.cw_level>max_cw_level:
            max_cw_level=u.cw_level
    for u in users:
        if u.id==str(update.effective_user.id) or u.cw_level<max_cw_level-model.get_data("MENTION_ELITE_DELTA", 15):
            continue
        tmp+="@{0} ".format(u.username)
        i+=1
        if not i%3:
            i=0
            try:
                context.bot.send_message(chat_id=cid, 
                                         text=u"\U0000270A Sir! Yes Sir!\n"+tmp,
                                         parse_mode=telegram.ParseMode.HTML,
                                         disable_web_page_preview=True)
            except Exception as e:
                utils._admin_error(context, "/elite", user=user, error=str(e))
            tmp=""
    if tmp:
        try:
            context.bot.send_message(chat_id=cid, 
                                     text=u"\U0000270A Sir! Yes Sir!\n"+tmp,
                                     parse_mode=telegram.ParseMode.HTML,
                                     disable_web_page_preview=True)
        except Exception as e:
            utils._admin_error(context, "/elite", user=user, error=str(e))
Example #6
0
def _action_deposit(cid, user, content, update, context):
    """
    Modify amount of items after deposit
    """
    item = b' '.join(content.split(b' ')[2:-1]).decode()[10:]
    amount = int(content.split(b' ')[-1][1:-1])
    print("            Deposit: {0} x ({1})".format(item, amount))
    item = utils.item_by_name(item)
    if item:
        item_type = ""
        if item["code"].startswith('r'):
            item_type = "recipes"
        elif item["code"].startswith('k'):
            item_type = "parts"
        # modify the crafting data
        if item_type:
            # guild warehouse
            if item["name"].lower() in CACHE["guild"][item_type]:
                CACHE["guild"][item_type][item["name"].lower()] += amount
            else:
                CACHE["guild"][item_type][item["name"].lower()] = amount
            # user
            u = model.user_by_id(update.effective_user.id)
            if u:
                crafting = json.loads(u.crafting)
                if crafting and len(crafting.keys()):
                    if item["name"].lower() in crafting[item_type]:
                        crafting[item_type][item["name"].lower()] -= amount
                        if crafting[item_type][item["name"].lower()] < 1:
                            del crafting[item_type][item["name"].lower()]
                    # store data
                    user.crafting = json.dumps(crafting)
                    if model.user_by_id(update.effective_user.id):
                        status = model.update_user(user)
                        if not status:
                            utils._admin_error(context,
                                               "_action_deposit",
                                               user=user,
                                               error="update: False",
                                               trace=False)
                    else:
                        utils._admin_error(context,
                                           "_action_deposit",
                                           user=user,
                                           error="no registered user",
                                           trace=False)
Example #7
0
def _action_crafting_list(cid, user, content, update, context):
    """
    Update crafting list
    """
    print("            Crafting tab")
    data = {"parts": {}, "recipes": {}, "datetime": None}
    today = datetime.datetime.today().isoformat()
    for c in content.split(b'\\n'):
        tmp = c
        # check false positive messages
        if b':' in tmp:
            continue
        # recipe
        if c.startswith(b'\\U0001f4c3'):
            # tmp=c.split(b'\\U0001f4c3')[1].split(b' /view_r')[0]
            tmp = c.split(b'\\U0001f4c3')[1].split(b' /i_r')[0]
            tmp = tmp.split(b' (')
            if len(tmp) == 2 and tmp[1].endswith(b')'):
                c_name = tmp[0].decode().lower()
                c_amount = int(tmp[1][:-1])
                data["recipes"][c_name] = c_amount
                data["datetime"] = today
        # part
        elif c.startswith(b'\\U0001f9e9'):
            tmp = c.split(b'\\U0001f9e9')[1].split(b' (')
            if len(tmp) == 2 and tmp[1].endswith(b')'):
                c_name = tmp[0].decode().lower()
                c_amount = int(tmp[1][:-1])
                data["parts"][c_name] = c_amount
                data["datetime"] = today
    if data["datetime"]:
        user.crafting = json.dumps(data)
        if model.user_by_id(update.effective_user.id):
            status = model.update_user(user)
            if not status:
                utils._admin_error(context,
                                   "_action_crafting_list",
                                   user=user,
                                   error="update: False",
                                   trace=False)
        else:
            utils._admin_error(context,
                               "_action_crafting_list",
                               user=user,
                               error="no registered user",
                               trace=False)
Example #8
0
def everybody(update, context):
    """
    Mention all subscribed users
    """
    cid=update.message.chat.id
    
    # validate user
    if not utils._check_user(context, update.effective_user.id, cid):
        return 
        
    # telegram user
    user=model.User(id=update.effective_user.id,
                    username=update.effective_user.username,
                    full_name=update.effective_user.full_name,
                    link=update.effective_user.link,
                    is_bot=update.effective_user.is_bot)
    # mention users 
    users=model.users()
    i=0
    tmp=""
    for u in users:
        if u.id==str(update.effective_user.id):
            continue
        tmp+="@{0} ".format(u.username)
        i+=1
        if not i%3:
            i=0
            try:
                context.bot.send_message(chat_id=cid, 
                                         text=tmp,
                                         parse_mode=telegram.ParseMode.HTML,
                                         disable_web_page_preview=True)
            except Exception as e:
                utils._admin_error(context, "/everybody", user=user, error=str(e))
            tmp=""
    if tmp:
        try:
            context.bot.send_message(chat_id=cid, 
                                     text=tmp,
                                     parse_mode=telegram.ParseMode.HTML,
                                     disable_web_page_preview=True)
        except Exception as e:
            utils._admin_error(context, "/everybody", user=user, error=str(e))
Example #9
0
def stomp(update, context):
    """
    Mention stronger users for stomp the hostile creatures
    """
    if settings.VERBOSE:
        print("[REGEX] help for stomp hostile creatures")
    cid=update.message.chat.id
    
    # validate user
    if not utils._check_user(context, update.effective_user.id, cid):
        return
        
    # telegram user
    user=model.User(id=update.effective_user.id,
                    username=update.effective_user.username,
                    full_name=update.effective_user.full_name,
                    link=update.effective_user.link,
                    is_bot=update.effective_user.is_bot)
    # parse message
    msg=update.message.text[7:].split("@")[0].split("_")
    if settings.VERBOSE:
        print("       ", msg)
    # validate the user
    if msg[1]==str(update.effective_user.id):
        # list users
        users=model.filtered_users(user, int(msg[0]), 20)
        i=0
        tmp=""
        for u in users[1]:
            if u.id==str(update.effective_user.id):
                continue
            tmp+="@{0} ".format(u.username)
            i+=1
            if not i%3:
                i=0
                try:
                    context.bot.send_message(chat_id=cid, 
                                             text="Someone needs your help for stomp the hostile creatures\n"+tmp,
                                             parse_mode=telegram.ParseMode.HTML,
                                             disable_web_page_preview=True)
                except Exception as e:
                    utils._admin_error(context, "regex stomp: accepted", user=user, error=str(e))
                tmp=""
        if tmp:
            try:
                context.bot.send_message(chat_id=cid, 
                                         text="Someone needs your help for stomp the hostile creatures\n"+tmp,
                                         parse_mode=telegram.ParseMode.HTML,
                                         disable_web_page_preview=True)
            except Exception as e:
                utils._admin_error(context, "regex stomp: accepted", user=user, error=str(e))
    else:
        try:
            context.bot.send_message(chat_id=cid, 
                                     text=u'\U0001F622 Only the owner of this encounter can request for help',
                                     parse_mode=telegram.ParseMode.HTML,
                                     disable_web_page_preview=True)
        except Exception as e:
            utils._admin_error(context, "regex stomp: denied", user=user, error=str(e))
Example #10
0
def check_outdata_crafting_list():
    while True:
        time.sleep(int(model.get_data("CRAFT_OUTDATE_INTERVAL_HOURS", 8*3600)))
        cid=model.get_data("CRAFTING_ROOM_CHAT_ID", None)
        print("[TIMER] check_outdata_crafting_list:", cid)
        if cid:
            today=datetime.datetime.today()
            try:
                for u in model.users():
                    crafting=json.loads(u.crafting)
                    if crafting and len(crafting.keys()):
                        # validate the date
                        t=datetime.datetime.fromisoformat(crafting["datetime"])
                        tmp=(datetime.datetime.today()-t).total_seconds()/(24.0*3600.0)
                        if tmp>int(model.get_data("CRAFT_OUTDATE_INTERVAL_DAYS", 3)):
                            BOT.send_message(chat_id=cid, 
                                             text=u'@{0}, your crafting data is outdated. Please, forward it here...'.format(html.escape(u.username)),
                                             parse_mode=telegram.ParseMode.HTML,
                                             disable_web_page_preview=True)
            except Exception as e:
                class Context:
                    bot=BOT
                context=Context()
                utils._admin_error(context, "timer.check_outdata_crafting_list", error=str(e))
Example #11
0
def users(update, context):
    """
    List the subscribed users
    """
    try:
        if str(update.effective_user.id) == settings.ADMIN_ID:
            users = model.users()
            # summary
            if update.message.text == "/users":
                text = u'<b>Subscribed users:</b> {0}\n\nUse /users_list for display the full list\nUse /users_detail for display detailed info (a lot of messages)'.format(
                    len(users))
                context.bot.send_message(chat_id=settings.ADMIN_ID,
                                         text=text,
                                         parse_mode=telegram.ParseMode.HTML,
                                         disable_web_page_preview=True)
            # full list
            elif update.message.text == "/users_list":
                text = ""
                for user in users:
                    tmp = u'\U0001F539 {0} {1}\n      @{2}\n'.format(
                        user.cw_level, html.escape(user.cw_name),
                        html.escape(user.username))
                    if len(text) + len(
                            tmp) < telegram.constants.MAX_MESSAGE_LENGTH - 5:
                        text += tmp
                    else:
                        context.bot.send_message(chat_id=settings.ADMIN_ID,
                                                 text=text,
                                                 disable_web_page_preview=True)
                        text = ""
                if text:
                    context.bot.send_message(chat_id=settings.ADMIN_ID,
                                             text=text,
                                             disable_web_page_preview=True)
            # detailed list
            elif update.message.text == "/users_detail":
                for user in users:
                    text = "<b>id:</b> {0}\n<b>username:</b> {1}\n<b>full_name:</b> {2}\n<b>link:</b> {3}\n<b>cw_name:</b> {4}\n<b>cw_level:</b> {5}\n<b>updated:</b> {6}\n<b>crafting:</b> {7}\n\n<code>/craft_reset {0}</code>\n<code>/users_delete {0}</code>".format(
                        user.id, html.escape(user.username),
                        html.escape(user.full_name), html.escape(user.link),
                        html.escape(user.cw_name), user.cw_level,
                        html.escape(user.updated), html.escape(user.crafting))
                    context.bot.send_message(
                        chat_id=settings.ADMIN_ID,
                        text=text,
                        parse_mode=telegram.ParseMode.HTML,
                        disable_web_page_preview=True)
            # delete user
            elif update.message.text.split(" ")[0] == "/users_delete" and len(
                    update.message.text.split(" ")) == 2:
                user = model.user_by_id(update.message.text.split(" ")[1])
                if user:
                    status = model.unsubscribe(user)
                    context.bot.send_message(
                        chat_id=settings.ADMIN_ID,
                        text="User unsubscription operation [{1}]... for @{0}".
                        format(html.escape(user.username), status),
                        parse_mode=telegram.ParseMode.HTML,
                        disable_web_page_preview=True)
    except Exception as e:
        utils._admin_error(context, "/users", error=str(e), trace=False)
Example #12
0
def forwarded(update, context):
    """
    Main handler function for forwarded messages
    """
    global CACHE
    cid = update.message.chat.id

    # validate user
    if not utils._check_user(context, update.effective_user.id, cid):
        return

    # process forward message from Chat Wars
    if update.message.forward_from and update.message.forward_from.id == settings.CW_BOT_ID:
        if settings.VERBOSE:
            print("[Forwarded] from Chat Wars")
        # telegram user
        user = model.User(id=update.effective_user.id,
                          username=update.effective_user.username,
                          full_name=update.effective_user.full_name,
                          link=update.effective_user.link,
                          is_bot=update.effective_user.is_bot)
        # create cache
        CACHE.setdefault(
            user.id, {
                "resources": {
                    "guild": {},
                    "reinforcement": {},
                    "datetime": datetime.datetime.today()
                }
            })
        CACHE.setdefault("guild", {
            "resources": {},
            "parts": {},
            "recipes": {}
        })
        # escape content
        try:
            content = update.message.text.encode(encoding="unicode_escape")
            # print(content)
        except Exception as e:
            utils._admin_error(context,
                               "encode message",
                               user=user,
                               error=str(e),
                               trace=False)
            return

        # hostile creatures
        if b'You met some hostile creatures. Be careful:' in content and b'/fight_' in content:
            _action_fight(cid, user, content, update, context)
            return

        # battle report
        if settings.GUILD_NAME in content and b' Lvl: ' in content and b'Your result on the battlefield' in content:
            _action_battle_report(cid, user, content, update, context)
            return

        # materials needed for reinforcement (blacksmith's store message)
        if content.split(b'\\n')[0].startswith(b'Materials needed for '):
            _action_reinforcement(cid, user, content, update, context)
            return

        # guild warehouse
        if content.split(b'\\n')[0].startswith(b'Guild Warehouse:'):
            _action_reinforcement(cid, user, content, update, context)
            return

        # guild roster
        if content.split(b'\\n')[0].startswith(
                settings.GUILD_NAME[:10]) and content.split(
                    b'\\n')[-1].startswith(b'#'):
            _action_roster(cid, user, content, update, context)
            return

        # guild deposit
        if content.startswith(b'Deposited successfully: '):
            _action_deposit(cid, user, content, update, context)
            return

        # parts and recipes
        if (content.startswith(b'\\U0001f4c3')
                or content.startswith(b'\\U0001f9e9')
            ) and not (b'Equipment' in content or b'Storage' in content
                       or b'/use_' in content or b'U0001f3f7' in content):
            _action_crafting_list(cid, user, content, update, context)
            return

        # alliances top
        if content.split(b'\\n')[0] == b'\\U0001f91dAlliances top:':
            _alliances_top(cid, user, content, update, context)
            return
Example #13
0
def _action_fight(cid, user, content, update, context):
    """
    Mention users for a fight
    """
    header = "Just another fight!\n"
    delta_upper = 10
    delta_lower = 20
    # forbidden champion
    if b"Forbidden Champion lvl." in content:
        header = u"\U000026A0 Defeat the \U0000269C CHAMPION!\n\U0001F534 Don't join if you can stomp\n"
        # delta_upper=1000
        delta_upper = 15
        delta_lower = 1000
    # ambush with loot locked
    elif b"It's an ambush! Loot is locked till the end of the fight" in content:
        header = u"\U0001F4E6 Ambush with loot locked!\n"
        delta_upper = 15
    # ambush without loot
    elif b"It's an ambush!" in content:
        header = "Ambush without loot!\n"
        delta_upper = 15
    # animals hunt
    elif b"Bear" in content or b"Boar" in content or b"Wolf" in content:
        header = u"\U0001F417 Wild animals hunt!\n"
    if settings.VERBOSE:
        print("            Hostile creatures:", delta_lower, delta_upper,
              header)
    # mention users
    users = model.filtered_users(user, delta_upper, delta_lower)
    i = 0
    tmp = ""
    for u in users[0]:
        if u.id == str(update.effective_user.id):
            continue
        tmp += "@{0} ".format(u.username)
        i += 1
        if not i % 3:
            i = 0
            try:
                context.bot.send_message(chat_id=cid,
                                         text=header + tmp,
                                         parse_mode=telegram.ParseMode.HTML,
                                         disable_web_page_preview=True)
            except Exception as e:
                utils._admin_error(context,
                                   "_action_fight: hostile creatures",
                                   user=user,
                                   error=str(e))
            tmp = ""
    if tmp:
        try:
            context.bot.send_message(chat_id=cid,
                                     text=header + tmp,
                                     parse_mode=telegram.ParseMode.HTML,
                                     disable_web_page_preview=True)
        except Exception as e:
            utils._admin_error(context,
                               "_action_fight: hostile creatures",
                               user=user,
                               error=str(e))
    # stomp message
    if len(users[1]):
        try:
            context.bot.send_message(
                chat_id=cid,
                text=
                "You can call for help from stronger players to stomp the hostile creatures\n/stomp_{0}_{1}"
                .format(delta_upper, user.id),
                parse_mode=telegram.ParseMode.HTML,
                disable_web_page_preview=True)
        except Exception as e:
            utils._admin_error(context,
                               "_action_fight: hostile creatures",
                               user=user,
                               error=str(e))