Example #1
0
async def index(session: CommandSession):
    now = dt.beijing_now()
    year = session.get_optional('year', now.year)
    month = session.get_optional('month', math.ceil(now.month / 3) * 3 - 3 + 1)

    api_url = INDEX_API_URL.format(year=year, month=month)
    resp = await requests.get(api_url)
    payload = await resp.json()
    if not payload or payload.get('code') != 0:
        await session.send('查询失败了……')
        return

    anime_list = payload['result']['data']
    if not anime_list:
        await session.send('没有查询到相关番剧……')
        return

    reply = f'{year}年{month}月番剧\n按追番人数排序,前20部如下:\n\n'
    for anime in anime_list:
        title = anime.get('title')
        index_show = anime.get('index_show', '不详')
        if not title:
            continue

        reply += f'{title}  {index_show}\n'

    web_url = INDEX_WEB_URL.format(year=year, month=month)
    reply += f'\n更多详细资料见BiliBili官网 {web_url}'

    await session.send(reply)
Example #2
0
async def _(session: CommandSession):
    if session.current_key == 'message':
        text = session.current_arg_text.strip()
        if ('拜拜' in text or '再见' in text) and len(text) <= 4:
            session.finish(render(expr.BYE_BYE))
            return
        session.args[session.current_key] = session.current_arg
Example #3
0
async def weather(session: CommandSession):
    location = session.get('location', prompt_expr=expr.WHERE)
    # time = session.get_optional('time')

    if location.province and not location.city and not location.district:
        # there is no city or district, ask the user for more info!
        session.get('location_more',
                    prompt=render(expr.WHERE_IN_PROVINCE,
                                  province=location.province))

    final_loc = location.heweather_format()
    await session.send(f'位置:{final_loc}')
Example #4
0
async def parse_args(session: CommandSession, parser: ArgumentParser,
                     argv: Optional[List[str]], help_msg: str) -> Namespace:
    if not argv:
        await session.send(help_msg)
    else:
        try:
            return parser.parse_args(argv)
        except ParserExit as e:
            if e.status == 0:
                # --help
                await session.send(help_msg)
            else:
                await session.send('参数不足或不正确,请使用 --help 参数查询使用帮助')
    session.finish()  # this will stop the command session
Example #5
0
async def note_add(session: CommandSession):
    content = session.get('content', prompt_expr=expr.ADD_WHAT_CONTENT)
    new_note = await Note.create(content=content,
                                 context_id=context_id(session.ctx))
    await session.send_expr(expr.ADD_SUCCESS,
                            id=new_note.id,
                            content=new_note.content)
Example #6
0
async def weather(session: CommandSession):
    # 从 Session 对象中获取城市名称(city),如果当前不存在,则询问用户
    city = session.get('city', prompt='你想查询哪个城市的天气呢?')
    # 获取城市的天气预报
    weather_report = await get_weather_of_city(city)
    # 向用户发送天气预报
    await session.send(weather_report)
Example #7
0
async def _(session: CommandSession):
    text = session.current_arg_text.strip()

    if session.is_first_run and text:
        # first run, and there is an argument, we take it as the id
        session.current_key = 'id'

    if session.current_key == 'id':
        id_ = None
        try:
            # try parse the text message as an id
            id_ = int(text)
        except ValueError:
            # it's not directly a number
            if not session.is_first_run:
                # we are in and interactive session, do nlp

                # user may want to ask for all notes, check it
                match_score = await nlp.sentence_similarity(
                    session.current_arg_text.strip(), '现在有哪些呢?')
                if match_score > 0.70:
                    # we think it matches
                    await session.send_expr(expr.QUERYING_ALL)
                    # sleep to make conversation natural :)
                    await asyncio.sleep(1)
                    await call_command(session.bot,
                                       session.ctx, ('note', 'list'),
                                       check_perm=False,
                                       disable_interaction=True)

                    # pause the session and wait for further interaction
                    await session.pause()
                    return

                # user may also put the id in a natural sentence, check it
                m = re.search(r'\d+', text)
                if m:
                    possible_id = int(m.group(0))
                    match_score = await nlp.sentence_similarity(
                        session.current_arg_text.strip(), f'删掉笔记{possible_id}')
                    if match_score > 0.70:
                        # we think it matches
                        id_ = possible_id
        if id_ is not None:
            session.args['id'] = id_
        else:
            session.pause(render(expr.DEL_CANNOT_RECOGNIZE_ID))
Example #8
0
async def ffxivitem(session: CommandSession):
    # 从 Session 对象中获取城市名称(city),如果当前不存在,则询问用户
    item = session.get_optional('item', default='NULL')
    if item == 'NULL':
        await session.send('请输入道具名')
    else:
        weather_report = await get_ffxivitem(item)
        await session.send(weather_report)
Example #9
0
async def teach(session: CommandSession):
    text = session.get('text')
    msg = session.ctx
    if text == '':
        await session.send('请输入 /teach 关键词 说什么')
    else:
        text_report = await get_text(msg, text)
        await session.send(text_report)
Example #10
0
async def forget(session: CommandSession):
    text = session.get('text')
    msg = session.ctx
    if text == '':
        await session.send('请输入 /forget 关键词')
    else:
        text_report = await fg_text(msg, text)
        await session.send(text_report)
Example #11
0
async def logs(session: CommandSession):
    text = session.get('text')
    msg = session.ctx
    if text == '':
        await session.send('请正确输入 /进度 游戏版本 服务器 玩家ID (只支持查询3.0以后的版本)')
    else:
        text_report = await get_logs(text)
        await session.send(text_report)
Example #12
0
async def handle_cancellation(session: CommandSession) -> None:
    """
    Handle cancellation instructions.

    If the current arg text is a cancellation instruction,
    the command session will be made finished, so that
    the command will no long be run.

    This function is present for manually calling through
    the process of a command's args parser, which means
    the args parser can do something before handle cancellation.
    On contrary, @allow_cancellation decorator will handle
    cancellation at the very beginning of the args parser.

    :param session: command session to handle
    """
    if session.is_first_run:
        return

    # we are in an interactive session, waiting for user's input
    # handle possible cancellation

    # use current_arg_text, we don't mind losing rich text parts of message
    text = session.current_arg_text.strip()
    small_sentences = re.split(r'\W+', text)
    logger.debug(f'Split small sentences: {small_sentences}')

    should_cancel = False
    new_ctx_message = None
    for i, sentence in enumerate(filter(lambda x: x.strip(), small_sentences)):
        if await is_cancellation(sentence):
            logger.debug(f'Sentence "{sentence}" is a cancellation, continue')
            should_cancel = True
            continue

        # this small sentence is not a cancellation, we split before this
        new_ctx_message = ','.join(small_sentences[i:]).strip()
        break

    if should_cancel:
        if not new_ctx_message:
            session.finish(render(
                session.bot.config.SESSION_CANCEL_EXPRESSION))
        else:
            session.switch(new_ctx_message)
Example #13
0
async def _(session: CommandSession):
    # 去掉消息首尾的空白符
    stripped_arg = session.current_arg_text.strip()
    if session.current_key:
        # 如果当前正在向用户询问更多信息(本例中只有可能是要查询的城市),则直接赋值
        session.args[session.current_key] = stripped_arg
    elif stripped_arg:
        # 如果当前没有在询问,但用户已经发送了内容,则理解为要查询的城市
        # 这种情况通常是用户直接将城市名跟在命令名后面,作为参数传入
        session.args['city'] = stripped_arg
Example #14
0
async def tuling(session: CommandSession):
    message = session.get('message', prompt_expr=expr.I_AM_READY)

    ctx_id = context_id(session.ctx)
    if ctx_id in tuling_sessions:
        del tuling_sessions[ctx_id]

    tmp_msg = Message(message)
    text = tmp_msg.extract_plain_text()
    images = [s.data['url'] for s in tmp_msg
              if s.type == 'image' and 'url' in s.data]

    # call tuling api
    replies = await call_tuling_api(session, text, images)
    logger.debug(f'Got tuling\'s replies: {replies}')

    if replies:
        for reply in replies:
            await session.send(escape(reply))
            await asyncio.sleep(0.8)
    else:
        await session.send_expr(expr.I_DONT_UNDERSTAND)

    one_time = session.get_optional('one_time', False)
    if one_time:
        # tuling123 may opened a session, we should recognize the
        # situation that tuling123 want more information from the user.
        # for simplification, we only recognize named entities,
        # and since we will also check the user's input later,
        # here we can allow some ambiguity.
        ne_type = tuling_ne_type(replies, {
            'LOC': ('哪里', '哪儿', re.compile(r'哪\S城市'), '位置'),
            'TIME': ('什么时候',),
        })
        if ne_type:
            logger.debug(f'One time call, '
                         f'and there is a tuling session for {ne_type}')
            tuling_sessions[ctx_id] = ne_type
    else:
        session.pause()
Example #15
0
async def _(session: CommandSession):
    argv = session.current_arg_text.split()

    year = None
    month = None
    if len(argv) == 2 and \
            re.fullmatch(r'(?:20)?\d{2}', argv[0]) and \
            re.fullmatch(r'\d{1,2}', argv[1]):
        year = int(argv[0]) if len(argv[0]) > 2 else 2000 + int(argv[0])
        month = int(argv[1])
    elif len(argv) == 1 and re.fullmatch(r'\d{1,2}', argv[0]):
        month = int(argv[0])
    elif len(argv) == 1 and re.fullmatch(r'(?:20)?\d{2}-\d{1,2}', argv[0]):
        year, month = [int(x) for x in argv[0].split('-')]
        year = 2000 + year if year < 100 else year
    elif len(argv):
        await session.send('抱歉无法识别输入的参数,下面将给出本季度的番剧~')

    if year is not None:
        session.args['year'] = year
    if month is not None:
        session.args['month'] = month
Example #16
0
async def sched_remove(session: CommandSession):
    parser = ArgumentParser()
    parser.add_argument('name')
    args = await parse_args(session,
                            parser,
                            argv=session.get_optional('argv'),
                            help_msg=sched_remove_help)
    ok = await scheduler.remove_job(
        scheduler.make_job_id(PLUGIN_NAME, context_id(session.ctx), args.name))
    if ok:
        await session.send(f'成功删除计划任务 {args.name}')
    else:
        await session.send(f'没有找到计划任务 {args.name},请检查你的输入是否正确')
Example #17
0
async def _(session: CommandSession):
    striped_text_arg = session.current_arg_text.strip()
    if not striped_text_arg:
        # ignore empty argument
        return

    if not session.current_key:
        session.current_key = 'location'

    if session.current_key == 'location':
        location = await nlp.parse_location(striped_text_arg)
        if any((location.province, location.city, location.district)):
            session.args['location'] = location
    elif session.current_key == 'location_more':
        patched_loc = await nlp.parse_location(striped_text_arg)
        location: nlp.Location = session.args.get('location')
        assert location
        location.province = location.province or patched_loc.province
        location.city = location.city or patched_loc.city
        location.district = location.district or patched_loc.district
        session.args['location'] = location
    else:
        session.args[session.current_key] = striped_text_arg
Example #18
0
async def tuling(session: CommandSession):
    # 获取可选参数,这里如果没有 message 参数,命令不会被中断,message 变量会是 None
    message = session.get_optional('message')

    # 通过封装的函数获取图灵机器人的回复
    reply = await call_tuling_api(session, message)
    if reply:
        # 如果调用图灵机器人成功,得到了回复,则转义之后发送给用户
        # 转义会把消息中的某些特殊字符做转换,以避免酷 Q 将它们理解为 CQ 码
        await session.send(escape(reply))
    else:
        # 如果调用失败,或者它返回的内容我们目前处理不了,发送无法获取图灵回复时的「表达」
        # 这里的 render_expression() 函数会将一个「表达」渲染成一个字符串消息
        await session.send(render_expression(EXPR_DONT_UNDERSTAND))
Example #19
0
async def tuling(session: CommandSession):
    message = session.get('message', prompt='我已经准备好啦,来跟我聊天吧~')

    finish = message in ('结束', '拜拜', '再见')
    if finish:
        session.finish('拜拜啦,你忙吧,下次想聊天随时找我哦~')
        return

    # call tuling api
    reply = f'你说了:{message}'

    one_time = session.get_optional('one_time', False)
    if one_time:
        session.finish(reply)
    else:
        session.pause(reply)
Example #20
0
async def ss1(session: CommandSession):
    ss1 = session.get('ss1')
    if ss1 == '':
        await session.send('请输入 /咏速 咏速数值')
    elif ss1.isdigit():
        if int(ss1) > 364:
            text_report = await get_ss1(ss1)
            await session.send(text_report)
        else:
            await session.send('请输入 /咏速 咏速数值')
        if int(ss1) > 5000:
            await session.send('您咏唱速度要上天啊')
    else:
        await session.send('请输入 /咏速 咏速数值(数字)')
Example #21
0
async def dh(session: CommandSession):
    dh = session.get('dh')
    if dh == '':
        await session.send('请输入 /直击 直击数值')
    elif dh.isdigit():
        if int(dh) > 364:
            if int(dh) > 5000:
                await session.send('您直击要上天啊')
            else:
                text_report = await get_dh(dh)
                await session.send(text_report)
        else:
            await session.send('请输入大于初始直击的数值')
    else:
        await session.send('请输入 /直击 直击数值(数字)')
Example #22
0
async def sched_get(session: CommandSession):
    parser = ArgumentParser()
    parser.add_argument('name')
    args = await parse_args(session,
                            parser,
                            argv=session.get_optional('argv'),
                            help_msg=sched_get_help)
    job = await scheduler.get_job(
        scheduler.make_job_id(PLUGIN_NAME, context_id(session.ctx), args.name))
    if not job:
        await session.send(f'没有找到计划任务 {args.name},请检查你的输入是否正确')
        return

    await session.send('找到计划任务如下')
    await session.send(format_job(args.name, job))
Example #23
0
async def det(session: CommandSession):
    det = session.get('det')
    if det == '':
        await session.send('请输入 /信念 信念数值')
    elif det.isdigit():
        if int(det) > 364:
            if int(det) > 5000:
                await session.send('您信念要上天啊')
            else:
                text_report = await get_det(det)
                await session.send(text_report)
        else:
            await session.send('请输入大于初始信念的数值')
    else:
        await session.send('请输入 /信念 信念数值(数字)')
Example #24
0
async def fy(session: CommandSession):
    fy = session.get('fy')
    if fy == '':
        await sefyion.send('请输入 /防御 防御数值')
    elif fy.isdigit():
        if int(fy) > 364:
            if int(fy) > 20000:
                await session.send('您防御要上天啊')
            else:
                text_report = await get_fy(fy)
                await session.send(text_report)
        else:
            await session.send('请输入 /防御 防御数值')
    else:
        await session.send('请输入 /防御 防御数值(数字)')
Example #25
0
async def bq(session: CommandSession):
    bq = session.get('bq')
    if bq == '':
        await session.send('请输入 /不屈 不屈数值')
    elif bq.isdigit():
        if int(bq) > 364:
            if int(bq) > 5000:
                await session.send('您不屈要上天啊')
            else:
                text_report = await get_bq(bq)
                await session.send(text_report)
        else:
            await session.send('请输入 /不屈 不屈数值')
    else:
        await session.send('请输入 /不屈 不屈数值(数字)')
Example #26
0
async def tuling(session: CommandSession):
    # 获取可选参数,这里如果没有 message 参数,命令不会被中断,message 变量会是 None
    message = session.get_optional('message')

    # 通过封装的函数获取图灵机器人的回复
    reply = await call_tuling_api(session, message)
    if reply:
        # 如果调用图灵机器人成功,得到了回复,则转义之后发送给用户
        # 转义会把消息中的某些特殊字符做转换,以避免酷 Q 将它们理解为 CQ 码
        await session.send(escape(reply))
    else:
        # 如果调用失败,或者它返回的内容我们目前处理不了,发送无法获取图灵回复时的「表达」
        # session.send_expr() 内部会调用 none.expression.render()
        # 该函数会将一个「表达」渲染成一个字符串消息
        await session.send_expr(EXPR_DONT_UNDERSTAND)
Example #27
0
async def ss(session: CommandSession):
    ss = session.get('ss')
    if ss == '':
        await session.send('请输入 /技速 技速数值')
    elif ss.isdigit():
        if int(ss) > 364:
            if int(ss) > 5000:
                await session.send('您技能速度要上天啊')
            else:
                text_report = await get_ss(ss)
                await session.send(text_report)
        else:
            await session.send('请输入 /技速 技速数值')
    else:
        await session.send('请输入 /技速 技速数值(数字)')
Example #28
0
async def hit(session: CommandSession):
    hit = session.get('hit')
    if hit == '':
        await session.send('请输入 /暴击 暴击数值')
    elif hit.isdigit():
        if int(hit) > 364:
            if int(hit) > 5000:
                await session.send('您暴击要上天啊')
            else:
                text_report = await get_hit(hit)
                await session.send(text_report)
        else:
            await session.send('请输入大于初始暴击的数值')
    else:
        await session.send('请输入 /暴击 暴击数值(数字)')
Example #29
0
async def note_remove(session: CommandSession):
    ctx_id = context_id(session.ctx)
    count = await note_count(ctx_id)
    if count == 0:
        await session.send_expr(expr.LIST_EMPTY)
        return

    id_ = session.get('id', prompt_expr=expr.DEL_WHICH_ID)
    note_ = await Note.query.where((Note.context_id == ctx_id)
                                   & (Note.id == id_)).gino.first()
    if note_ is None:
        await session.send_expr(expr.DEL_ID_NOT_EXISTS, id=id_)
    else:
        await note_.delete()
        await session.send_expr(expr.DEL_SUCCESS,
                                id=id_,
                                content=note_.content)
Example #30
0
async def _(session: CommandSession):
    if session.current_key:
        if session.current_arg_text.strip() in {'算了', '不删了', '取消'}:
            session.finish('好的')
            return

    if not session.current_key and session.current_arg.strip():
        # initial interaction, and there is an argument, we take it as the id
        session.current_key = 'id'

    if session.current_key == 'id':
        try:
            id_ = int(session.current_arg.strip())
            session.args['id'] = id_
        except ValueError:
            session.pause('ID 不正确,应只包含数字,请重新输入')
Example #31
0
async def tuling(session: CommandSession):
    message = session.get('message', prompt='我已经准备好啦,来跟我聊天吧~')

    finish = message in ('结束', '拜拜', '再见')
    if finish:
        asyncio.ensure_future(session.send('拜拜啦,你忙吧,下次想聊天随时找我哦~'))
        return

    # call tuling api
    reply = f'你说了:{message}'

    one_time = session.get_optional('one_time', False)
    if one_time:
        asyncio.ensure_future(session.send(reply))
    else:
        del session.args['message']
        session.get('message', prompt=reply)
Example #32
0
async def tuling(session: CommandSession):
    message = session.get('message', prompt='我已经准备好啦,来跟我聊天吧~')

    finish = message in ('结束', '拜拜', '再见')
    if finish:
        asyncio.ensure_future(session.send('拜拜啦,你忙吧,下次想聊天随时找我哦~'))
        return

    # call tuling api
    reply = f'你说了:{message}'

    one_time = session.get_optional('one_time', False)
    if one_time:
        asyncio.ensure_future(session.send(reply))
    else:
        del session.args['message']
        session.get('message', prompt=reply)
Example #33
0
async def weather(session: CommandSession):
    city = session.get('city', prompt_expr=expr.WHICH_CITY)
    await session.send_expr(expr.REPORT, city=city)
Example #34
0
async def _(session: CommandSession):
    await session.send(
        unescape(session.get_optional('message') or session.current_arg))
Example #35
0
async def echo(session: CommandSession):
    await session.send(session.get_optional('message') or session.current_arg)
Example #36
0
async def _(session: CommandSession):
    stripped_arg = session.current_arg_text.strip()
    if session.current_key:
        session.args[session.current_key] = stripped_arg
    elif stripped_arg:
        session.args['city'] = stripped_arg
Example #37
0
async def weather(session: CommandSession):
    city = session.get('city', prompt='你想查询哪个城市的天气呢?')
    weather_report = await get_weather_of_city(city)
    await session.send(weather_report)