Ejemplo n.º 1
0
async def weather(session: CommandSession):
    location = session.get('location', prompt=__(e.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=__(e.WHERE_IN_PROVINCE, province=location.province))

    final_loc = location.heweather_format()
    await session.send(f'位置:{final_loc}')
Ejemplo n.º 2
0
async def _(session: CommandSession):
    count = await note_count(context_id(session.ctx))
    if count == 0:
        await session.send(__(e.LIST_EMPTY))
        return

    all_notes = await Note.query.where(
        Note.context_id == context_id(session.ctx)).gino.all()
    for n in all_notes:
        await session.send(f'ID:{n.id}\r\n内容:{n.content}')
        await asyncio.sleep(0.8)
    await session.send(__(e.LIST_COMPLETE, count=count))
Ejemplo n.º 3
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(__(e.LIST_EMPTY))
        return

    id_ = session.get('id', prompt=__(e.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(__(e.DEL_ID_NOT_EXISTS, id=id_))
    else:
        await note_.delete()
        await session.send(__(e.DEL_SUCCESS, id=id_, content=note_.content))
Ejemplo n.º 4
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(__(e.BYE_BYE))
            return
        session.args[session.current_key] = session.current_arg
Ejemplo n.º 5
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(__(e.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(__(e.DEL_CANNOT_RECOGNIZE_ID))
Ejemplo n.º 6
0
async def _(session: NLPSession):
    if not session.msg:
        # empty message body
        nicks = list(session.bot.config.NICKNAME)
        if nicks:
            nick = nicks[0]
        else:
            nick = None
        await session.send(__(EXPR_ACK, nick=nick))
Ejemplo n.º 7
0
async def _(session: NoticeSession):
    if session.ctx['group_id'] not in (230697355, 519698575, 865640538):
        return
    try:
        info = await session.bot.get_group_member_info(**session.ctx,
                                                       no_cache=True)
        name = info['card'] or info['nickname'] or '新成员'
        await session.send(__(GROUP_GREETING, name=name, **session.ctx))
    except CQHttpError:
        pass
Ejemplo n.º 8
0
async def tuling(session: CommandSession):
    message = session.get('message', prompt=__(e.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(__(e.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()
Ejemplo n.º 9
0
async def lunch(session: CommandSession):
    where = ['去一食堂', '去二食堂', '吃日夜', '点外卖', '出去吃']
    kind = ['面条', '饭', '炒饭', '早点', '砂锅']

    next1 = session.get_optional('next1')
    next2 = session.get_optional('next2')

    if next1 is None:
        # 先随机一个去处,问可不可以
        await session.send(__(EXPR_WAIT))
        await asyncio.sleep(1)
        session.get('next1', prompt=random.choice(where) + '吧,' + __(EXPR_HOW))

    if next2 is None and check_confirmation(next1) is not True:
        # 去处被否决
        session.finish(__(EXPR_CANCEL))

    # 去处 OK
    if next2 is None:
        session.get('next2', prompt=__(EXPR_REQU))

    if check_confirmation(next2) is not True:
        session.finish(__(EXPR_CANCEL))

    await asyncio.sleep(0.8)
    await session.send('经奶茶精选,今天' + random.choice(kind) + '与你更配哦🤔')
    await asyncio.sleep(0.3)
    await session.send(__(EXPR_EMOJI))
Ejemplo n.º 10
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(__(session.bot.config.SESSION_CANCEL_EXPRESSION))
        else:
            session.switch(new_ctx_message)
Ejemplo n.º 11
0
async def weather(session: CommandSession):
    city = session.get('city', prompt=__(e.WHICH_CITY))
    await session.send(__(e.REPORT, city=city))
Ejemplo n.º 12
0
async def note_add(session: CommandSession):
    content = session.get('content', prompt=__(e.ADD_WHAT_CONTENT))
    new_note = await Note.create(content=content,
                                 context_id=context_id(session.ctx))
    await session.send(
        __(e.ADD_SUCCESS, id=new_note.id, content=new_note.content))