ayaka.deal

处理收到的消息,将其分割为cmd和args,设置上下文相关变量的值,并将消息传递给对应的群组

  1'''处理收到的消息,将其分割为cmd和args,设置上下文相关变量的值,并将消息传递给对应的群组'''
  2import asyncio
  3import datetime
  4from typing import List
  5
  6from .driver import Message, MessageSegment, Bot, MessageEvent, GroupMessageEvent
  7from .on import AyakaTrigger
  8from .config import ayaka_root_config
  9from .constant import _bot, _event, _group, _arg, _args, _message, _cmd, private_listener_dict
 10from .group import get_group
 11
 12
 13async def deal_event(bot: Bot, event: MessageEvent):
 14    if ayaka_root_config.exclude_old_msg:
 15        time_i = int(datetime.datetime.now().timestamp())
 16        if event.time < time_i - 60:
 17            return
 18
 19    _bot.set(bot)
 20    _event.set(event)
 21
 22    bot_id = int(bot.self_id)
 23
 24    if isinstance(event, GroupMessageEvent):
 25        group_id = event.group_id
 26        await deal_group(bot_id, group_id)
 27
 28    else:
 29        id = event.user_id
 30        group_ids = private_listener_dict.get(id, [])
 31        ts = [asyncio.create_task(deal_group(bot_id, group_id))
 32              for group_id in group_ids]
 33        await asyncio.gather(*ts)
 34
 35
 36async def deal_group(bot_id: int, group_id: int):
 37    # 群组
 38    group = get_group(bot_id, group_id)
 39    _group.set(group)
 40
 41    # 消息
 42    message = _event.get().message
 43    _message.set(message)
 44
 45    # 命令、参数
 46    cmd = get_cmd(message)
 47    _cmd.set(cmd)
 48
 49    # 让super先来
 50    triggers = []
 51    for app in group.apps:
 52        for t in app.super_triggers:
 53            triggers.append(t)
 54
 55    # 若执行了super命令,则退出
 56    if await deal_triggers(triggers):
 57        return
 58
 59    # 普通命令继续
 60    triggers = []
 61
 62    # 当前正在运行
 63    app = group.running_app
 64    if app:
 65        for t in app.state_triggers:
 66            if t.state == "*":
 67                triggers.append(t)
 68            else:
 69                # 子状态
 70                # s1 = 添加.
 71                # s2 = 添加.姓名.
 72                s1 = t.state + "."
 73                s2 = app.state + "."
 74                if s2.startswith(s1):
 75                    triggers.append(t)
 76
 77    # 其他桌面应用
 78    else:
 79        for app in group.apps:
 80            for t in app.no_state_triggers:
 81                triggers.append(t)
 82
 83    await deal_triggers(triggers)
 84
 85
 86async def deal_triggers(triggers: List[AyakaTrigger]):
 87    triggers.sort(key=lambda t: str(t.state), reverse=True)
 88
 89    cmd = _cmd.get()
 90    msg = _message.get()
 91
 92    # 命令
 93    if cmd:
 94        for t in triggers:
 95            if t.cmd == cmd:
 96                # 设置去掉命令后的消息
 97                arg = remove_cmd(cmd, msg)
 98                _arg.set(arg)
 99                _args.set(divide_message(arg))
100                await t.run()
101                return True
102
103    _arg.set(msg)
104    _args.set(divide_message(msg))
105
106    # 命令退化成消息
107    for t in triggers:
108        if not t.cmd:
109            await t.run()
110
111
112def get_cmd(message: Message):
113    '''返回命令'''
114    prefix = ayaka_root_config.prefix
115    sep = ayaka_root_config.separate
116    first = ""
117    for m in message:
118        if m.type == "text":
119            first += str(m)
120        else:
121            break
122        
123    if not first or not first.startswith(prefix):
124        return ""
125
126    if not sep:
127        return first
128    
129    first += sep
130    return first.split(sep, 1)[0][len(prefix):]
131
132
133def divide_message(message: Message) -> List[MessageSegment]:
134    args = []
135    sep = ayaka_root_config.separate
136
137    for m in message:
138        if m.is_text():
139            ss = str(m).split(sep)
140            args.extend(MessageSegment.text(s) for s in ss if s)
141        else:
142            args.append(m)
143
144    return args
145
146
147def remove_cmd(cmd: str, message: Message) -> Message:
148    prefix = ayaka_root_config.prefix
149    sep = ayaka_root_config.separate
150    m = message[0]
151    if m.is_text():
152        m_str = str(m)
153        m_str = m_str[len(prefix+cmd):].lstrip(sep)
154        if not m_str:
155            return Message(message[1:])
156        return Message([MessageSegment.text(m_str), *message[1:]])
157    return message
async def deal_event( bot: nonebot.adapters.onebot.v11.bot.Bot, event: nonebot.adapters.onebot.v11.event.MessageEvent):
14async def deal_event(bot: Bot, event: MessageEvent):
15    if ayaka_root_config.exclude_old_msg:
16        time_i = int(datetime.datetime.now().timestamp())
17        if event.time < time_i - 60:
18            return
19
20    _bot.set(bot)
21    _event.set(event)
22
23    bot_id = int(bot.self_id)
24
25    if isinstance(event, GroupMessageEvent):
26        group_id = event.group_id
27        await deal_group(bot_id, group_id)
28
29    else:
30        id = event.user_id
31        group_ids = private_listener_dict.get(id, [])
32        ts = [asyncio.create_task(deal_group(bot_id, group_id))
33              for group_id in group_ids]
34        await asyncio.gather(*ts)
async def deal_group(bot_id: int, group_id: int):
37async def deal_group(bot_id: int, group_id: int):
38    # 群组
39    group = get_group(bot_id, group_id)
40    _group.set(group)
41
42    # 消息
43    message = _event.get().message
44    _message.set(message)
45
46    # 命令、参数
47    cmd = get_cmd(message)
48    _cmd.set(cmd)
49
50    # 让super先来
51    triggers = []
52    for app in group.apps:
53        for t in app.super_triggers:
54            triggers.append(t)
55
56    # 若执行了super命令,则退出
57    if await deal_triggers(triggers):
58        return
59
60    # 普通命令继续
61    triggers = []
62
63    # 当前正在运行
64    app = group.running_app
65    if app:
66        for t in app.state_triggers:
67            if t.state == "*":
68                triggers.append(t)
69            else:
70                # 子状态
71                # s1 = 添加.
72                # s2 = 添加.姓名.
73                s1 = t.state + "."
74                s2 = app.state + "."
75                if s2.startswith(s1):
76                    triggers.append(t)
77
78    # 其他桌面应用
79    else:
80        for app in group.apps:
81            for t in app.no_state_triggers:
82                triggers.append(t)
83
84    await deal_triggers(triggers)
async def deal_triggers(triggers: List[ayaka.on.AyakaTrigger]):
 87async def deal_triggers(triggers: List[AyakaTrigger]):
 88    triggers.sort(key=lambda t: str(t.state), reverse=True)
 89
 90    cmd = _cmd.get()
 91    msg = _message.get()
 92
 93    # 命令
 94    if cmd:
 95        for t in triggers:
 96            if t.cmd == cmd:
 97                # 设置去掉命令后的消息
 98                arg = remove_cmd(cmd, msg)
 99                _arg.set(arg)
100                _args.set(divide_message(arg))
101                await t.run()
102                return True
103
104    _arg.set(msg)
105    _args.set(divide_message(msg))
106
107    # 命令退化成消息
108    for t in triggers:
109        if not t.cmd:
110            await t.run()
def get_cmd(message: nonebot.adapters.onebot.v11.message.Message):
113def get_cmd(message: Message):
114    '''返回命令'''
115    prefix = ayaka_root_config.prefix
116    sep = ayaka_root_config.separate
117    first = ""
118    for m in message:
119        if m.type == "text":
120            first += str(m)
121        else:
122            break
123        
124    if not first or not first.startswith(prefix):
125        return ""
126
127    if not sep:
128        return first
129    
130    first += sep
131    return first.split(sep, 1)[0][len(prefix):]

返回命令

def divide_message( message: nonebot.adapters.onebot.v11.message.Message) -> List[nonebot.adapters.onebot.v11.message.MessageSegment]:
134def divide_message(message: Message) -> List[MessageSegment]:
135    args = []
136    sep = ayaka_root_config.separate
137
138    for m in message:
139        if m.is_text():
140            ss = str(m).split(sep)
141            args.extend(MessageSegment.text(s) for s in ss if s)
142        else:
143            args.append(m)
144
145    return args
def remove_cmd( cmd: str, message: nonebot.adapters.onebot.v11.message.Message) -> nonebot.adapters.onebot.v11.message.Message:
148def remove_cmd(cmd: str, message: Message) -> Message:
149    prefix = ayaka_root_config.prefix
150    sep = ayaka_root_config.separate
151    m = message[0]
152    if m.is_text():
153        m_str = str(m)
154        m_str = m_str[len(prefix+cmd):].lstrip(sep)
155        if not m_str:
156            return Message(message[1:])
157        return Message([MessageSegment.text(m_str), *message[1:]])
158    return message