新增入群欢迎远程处理好友、群请求

This commit is contained in:
CMHopeSunshine 2022-09-06 22:05:30 +08:00
parent 4ec9af1bb8
commit fec8beba1d
8 changed files with 259 additions and 6 deletions

View File

@ -45,4 +45,8 @@ JSON_DATA = Path(__file__).parent / 'data'
PLUGIN_CONFIG = Path() / 'config' / 'plugins'
PLUGIN_CONFIG.mkdir(parents=True, exist_ok=True)
PAIMON_CONFIG = Path() / 'config' / 'paimon_config.yml'
# 问候语配置文件
GREET_CONFIG = Path() / 'config' / 'paimon_greet.yml'
GREET_CONFIG_DEFAULT = Path() / 'config' / 'paimon_greet_default.yml'

View File

@ -59,7 +59,7 @@ class PluginManager:
"""
if config_name not in self.config.dict(by_alias=True).keys():
return f'没有配置项为{config_name}'
if '启用' in config_name or '开关' in config_name:
if '启用' in config_name or '开关' in config_name or config_name in {'自动接受好友请求', '自动接受群邀请'}:
if value not in ['', '', 'true', 'false', 'on', 'off']:
return '参数错误'
value = value in ['', 'true', 'on']

View File

@ -58,9 +58,14 @@ class Config(BaseModel):
AI_voice_cooldown: int = Field(10, alias='原神语音合成冷却')
ys_auto_update: int = Field(24, alia='ys自动更新小时')
ysa_auto_update: int = Field(24, alia='ysa自动更新小时')
ysd_auto_update: int = Field(6, alia='ysd自动更新小时')
ys_auto_update: int = Field(24, alias='ys自动更新小时')
ysa_auto_update: int = Field(24, alias='ysa自动更新小时')
ysd_auto_update: int = Field(6, alias='ysd自动更新小时')
cloud_genshin_enable: bool = Field(True, alias='云原神自动签到开关')
cloud_genshin_hour: int = Field(7, alias='云原神签到时间(小时)')
request_event: bool = Field(True, alias='启用好友和群请求通知')
auto_add_friend: bool = Field(False, alias='自动接受好友请求')
auto_add_group: bool = Field(False, alias='自动接受群邀请')
notice_event: bool = Field(True, alias='启用好友和群欢迎消息')

View File

@ -0,0 +1,174 @@
import asyncio
import random
import datetime
from typing import Dict
from nonebot import on_command, on_regex, on_notice, on_request
from nonebot.rule import Rule
from nonebot.permission import SUPERUSER
from nonebot.params import CommandArg, ArgPlainText, RegexDict
from nonebot.adapters.onebot.v11 import Bot, Message, MessageEvent, PrivateMessageEvent, FriendRequestEvent, GroupRequestEvent, \
RequestEvent, NoticeEvent, \
GroupIncreaseNoticeEvent, FriendAddNoticeEvent
from nonebot.typing import T_State
from LittlePaimon import NICKNAME, SUPERUSERS
from LittlePaimon.utils import scheduler, logger
from LittlePaimon.utils.message import format_message
from LittlePaimon.manager.plugin_manager import plugin_manager as pm
from .config import config
requests_list: Dict[str, Dict[str, Dict[str, any]]] = {
'好友': {},
'': {}
}
done: Dict[str, datetime.datetime] = {} # 防止gocq重复上报事件导致多次处理
async def InviteRule(event: RequestEvent) -> bool:
if not pm.config.request_event:
return False
if isinstance(event, FriendRequestEvent):
return f'add_friend_{event.user_id}' not in done.keys()
elif isinstance(event, GroupRequestEvent) and event.sub_type == 'invite':
return f'add_group_{event.group_id}' not in done.keys()
return False
async def IncreaseRule(event: NoticeEvent) -> bool:
if not pm.config.notice_event:
return False
if isinstance(event, FriendAddNoticeEvent):
return f'new_friend_{event.user_id}' not in done.keys()
elif isinstance(event, GroupIncreaseNoticeEvent):
return f'new_group_{event.group_id}' not in done.keys() and f'new_member_{event.group_id}_{event.user_id}' not in done.keys()
return False
approve_request = on_command('同意', priority=1, block=True, permission=SUPERUSER)
ban_greet = on_regex(r'(?P<type>开启|启用|关闭|禁用)(?P<target>.*)', priority=1, block=True, permission=SUPERUSER)
requests = on_request(priority=1, rule=Rule(InviteRule), block=True)
notices = on_notice(priority=1, rule=Rule(IncreaseRule), block=True)
@approve_request.handle()
async def _(event: PrivateMessageEvent, state: T_State, msg: Message = CommandArg()):
msg = msg.extract_plain_text().strip()
if not msg:
await approve_request.finish('用法:同意<好友/群>[群号/qq号]例如同意好友123456')
if msg.startswith('好友'):
state['type'] = '好友'
msg = msg.replace('好友', '').strip()
elif msg.startswith(''):
state['type'] = ''
msg = msg.replace('', '').strip()
if not requests_list[state['type']]:
await approve_request.finish(f'没有待处理的{state["type"]}请求')
elif msg in requests_list[state['type']].keys():
state['id'] = Message(msg)
else:
state['id_list'] = '\n'.join([f'{v["name"]}({k})' for k, v in requests_list[state['type']].items()])
@approve_request.got('id', prompt=Message.template('你要同意的是以下哪个{type}:\n{id_list}\n请发送{type}号码'))
async def _(event: PrivateMessageEvent, bot: Bot, state: T_State, id_: str = ArgPlainText('id')):
if id_ not in requests_list[state['type']].keys():
await approve_request.reject(Message.template('请发送要同意的{type}号码:\n{id_list}'))
else:
flag = requests_list[state['type']][id_]['flag']
if state['type'] == '好友':
await bot.set_friend_add_request(flag=flag, approve=True)
del requests_list['好友'][id_]
logger.info('好友添加请求', '', {'好友': id_}, '已同意', True)
await approve_request.finish(f'已同意{id_}的好友请求')
elif state['type'] == '':
await bot.set_group_add_request(flag=flag, sub_type='invite', approve=True)
del requests_list[''][id_]
logger.info('群邀请请求', '', {'': id_}, '已同意', True)
await approve_request.finish(f'已同意{id_}的群邀请')
@requests.handle()
async def _(bot: Bot, event: FriendRequestEvent):
done[f'add_friend_{event.user_id}'] = datetime.datetime.now()
user_info = await bot.get_stranger_info(user_id=event.user_id)
base_msg = f'{user_info["nickname"]}({event.user_id})请求添加好友,验证信息为"{event.comment or ""}"'
if pm.config.auto_add_friend:
await asyncio.sleep(random.randint(10, 20))
await bot.send_private_msg(user_id=SUPERUSERS[0], message=f'{base_msg},已自动同意')
await event.approve(bot)
logger.info('好友添加请求', '', {'好友': event.user_id}, '申请添加好友,已自动同意', True)
else:
requests_list['好友'][str(event.user_id)] = {'name': user_info['nickname'], 'flag': event.flag}
await bot.send_private_msg(user_id=SUPERUSERS[0], message=f'{base_msg},可发送"同意好友{event.user_id}"来同意')
logger.info('好友添加请求', '', {'好友': event.user_id}, '申请添加好友', True)
@requests.handle()
async def _(bot: Bot, event: GroupRequestEvent):
done[f'add_group_{event.group_id}'] = datetime.datetime.now()
user_info = await bot.get_stranger_info(user_id=event.user_id)
group_info = await bot.get_group_info(group_id=event.group_id)
base_msg = f'{user_info["nickname"]}({event.user_id})邀请{NICKNAME}加入群{group_info["group_name"]}({event.group_id})'
if pm.config.auto_add_group:
await asyncio.sleep(random.randint(10, 20))
await bot.send_private_msg(user_id=SUPERUSERS[0], message=f'{base_msg},已自动同意')
await event.approve(bot)
logger.info('群邀请请求', '', {'': event.group_id}, '邀请进群,已自动同意', True)
else:
requests_list[''][str(event.group_id)] = {'name': group_info['group_name'], 'flag': event.flag}
await bot.send_private_msg(user_id=SUPERUSERS[0], message=f'{base_msg},可发送"同意群{event.group_id}"来同意')
logger.info('群邀请请求', '', {'': event.group_id}, '邀请进群', True)
@notices.handle()
async def _(bot: Bot, event: FriendAddNoticeEvent):
done[f'new_friend_{event.user_id}'] = datetime.datetime.now()
await asyncio.sleep(random.randint(10, 20))
await bot.send_private_msg(user_id=event.user_id, message=format_message(config.new_friend))
@notices.handle()
async def _(bot: Bot, event: GroupIncreaseNoticeEvent):
if event.user_id == event.self_id:
done[f'new_group_{event.group_id}'] = datetime.datetime.now()
await asyncio.sleep(random.randint(10, 20))
await bot.send_group_msg(group_id=event.group_id, message=format_message(config.new_group))
elif str(event.group_id) not in config.group_ban and config.group_ban[0] != '全部':
done[f'new_member_{event.user_id}'] = datetime.datetime.now()
await asyncio.sleep(random.randint(10, 20))
if str(event.group_id) in config.group_greet:
msg = config.group_greet[str(event.group_id)]
else:
msg = config.group_greet['默认']
await bot.send_group_msg(group_id=event.group_id, message=format_message(msg, user_id=event.user_id))
@ban_greet.handle()
async def _(event: MessageEvent, regex_dict: dict = RegexDict()):
type = regex_dict['type']
target = regex_dict['target'].split(' ')
if not target:
target = [str(event.group_id)]
if any(i in target for i in {'全部', 'all', '所有'}):
target = ['全部']
for t in target:
if not t.isdigit() and t != '全部':
await ban_greet.finish('请输入要禁用|启用群欢迎的正确的群号')
if t == '全部':
config.group_ban = ['全部'] if type in {'禁用', '关闭'} else []
elif type in {'禁用', '关闭'}:
if t not in config.group_ban:
config.group_ban.append(int(t))
elif t in config.group_ban:
config.group_ban.remove(int(t))
config.save()
await ban_greet.finish(f'{type}{" ".join(target)}的群欢迎')
@scheduler.scheduled_job('cron', hour='*/1')
def _():
# 删除done中超过1小时的记录
for k, v in done.copy().items():
if (datetime.datetime.now() - v).seconds > 3600:
del done[k]

View File

@ -0,0 +1,30 @@
from typing import Dict
from LittlePaimon.config import GREET_CONFIG, GREET_CONFIG_DEFAULT
from LittlePaimon.utils.files import load_yaml, save_yaml
class GreetConfig:
def __init__(self):
if GREET_CONFIG.exists():
data = load_yaml(GREET_CONFIG)
elif GREET_CONFIG_DEFAULT.exists():
data = load_yaml(GREET_CONFIG_DEFAULT)
else:
data = {}
self.new_friend: str = data.get('新好友见面语', '旅行者你好呀,这里是{nickname}对我说“help”查看帮助吧~')
self.new_group: str = data.get('新群见面语', '旅行者们大家好呀,这里是{nickname}对我说“help”查看帮助吧~')
self.group_greet: Dict[str, str] = data.get('群新人欢迎语', {'默认': '欢迎新旅行者~{at_user}'})
self.group_ban = data.get('群欢迎语禁用列表', [])
self.save()
def save(self):
data = {
'新好友见面语': self.new_friend,
'新群见面语': self.new_group,
'群新人欢迎语': self.group_greet,
'群欢迎语禁用列表': self.group_ban
}
save_yaml(data, GREET_CONFIG)
config = GreetConfig()

View File

@ -92,6 +92,7 @@ show_abyss = on_command('深渊统计', priority=10, block=True, state={
'pm_priority': 10
})
@ys.handle()
async def _(event: MessageEvent, players=CommandPlayer()):
logger.info('原神信息查询', '开始执行')
@ -286,7 +287,8 @@ async def _(event: MessageEvent, msg: Message = CommandArg()):
@show_alias.handle()
async def _(event: MessageEvent):
if aliases := await PlayerAlias.filter(user_id=str(event.user_id)).all():
await show_alias.finish('你已设以下别名:' + '\n'.join(f'{alias.alias}->{alias.character}' for alias in aliases), at_sender=True)
await show_alias.finish('你已设以下别名:' + '\n'.join(f'{alias.alias}->{alias.character}' for alias in aliases),
at_sender=True)
else:
await show_alias.finish('你还没有设置过角色别名哦', at_sender=True)
@ -294,4 +296,4 @@ async def _(event: MessageEvent):
@show_abyss.handle()
async def _(event: GroupMessageEvent):
result = await get_statistics(event.group_id)
await show_abyss.finish(result)
await show_abyss.finish(result)

View File

@ -12,6 +12,7 @@ from nonebot.matcher import Matcher
from nonebot.params import CommandArg, Depends
from nonebot.typing import T_State
from LittlePaimon import NICKNAME
from LittlePaimon.database.models import LastQuery, PrivateCookie, Player, PlayerAlias
from LittlePaimon.utils import aiorequests, load_image
from LittlePaimon.utils.alias import get_match_alias
@ -360,3 +361,32 @@ async def recall_message(event: MessageEvent) -> bool:
return False
await bot.delete_msg(message_id=event.message_id)
return True
def format_message(text: str, **kwargs) -> Message:
msg = Message()
texts = re.split(r'({(?:\w+|(?:img|voice|video):[^{}]+|face:\d+)})', text)
for text in texts:
if text == '{nickname}':
msg += MessageSegment.text(NICKNAME)
elif text in '{at_user}':
msg += MessageSegment.at(kwargs['user_id']) if 'user_id' in kwargs else MessageSegment.text('{at_user}')
elif text.startswith(('{img', '{voice', '{video')):
url = text.split(':', 1)[1].strip('}')
if url.startswith('.'):
url = Path().cwd().as_uri() + url[1:].replace('\\', '/')
if text.startswith('{img'):
msg += MessageSegment.image(url)
elif text.startswith('{voice'):
msg += MessageSegment.record(url)
elif text.startswith('{video'):
msg += MessageSegment.video(url)
elif text.startswith('{face:'):
face_id = text.split(':', 1)[1].strip('}')
msg += MessageSegment.face(int(face_id))
elif text.startswith('{') and text.endswith('}'):
type_ = text.strip('{').strip('}')
msg += MessageSegment.text(kwargs.get(type_, text))
else:
msg += MessageSegment.text(text)
return msg

View File

@ -0,0 +1,8 @@
新好友见面语: 旅行者你好呀,这里是{nickname}对我说“help”查看帮助吧~
新群见面语: 旅行者们大家好呀,这里是{nickname}对我说“help”查看帮助吧~
群新人欢迎语:
默认: 欢迎新旅行者~{at_user}{img:.\resources\LittlePaimon\emoticons\派蒙-交给我吧.png}
123456789: 针对群123456789的欢迎语
群欢迎语禁用列表:
- 123456789
- 987654321