Skip to content

功能逻辑

Bluefissure edited this page May 10, 2019 · 7 revisions

功能的实现与修改。

处理逻辑

Event

  1. django-channels接受到websocket传来的消息
  2. 判断是否需要push到消息队列中,如果需要,则计算该消息的优先级后push到名为ffxivbot的queue中;如果不需要,判断是否是API的回调消息并进行数据更新
  3. pika_rabbit.py通过读取queue中的消息进行处理,通过读取数据库机器人的channel name调用redis中的channels name发送API调用请求

API

  1. django-channels接受到API请求
  2. 直接传输对应数据

Channels Consumer

代码

目前通过AsyncWebsocketConsumer实现,处理Event上报消息与API回调消息,同时可以通过这个连接调用API。

Django中设定的CHANNEL_LAYER为RedisChannelLayer使得可以在系统的其他位置调用channels,也可以开放api,具体代码可以参考 ffxivbot/views.py 中的api部分。

优先级相关设定为:

  1. 优先级默认为1
  2. /开头的消息,优先级+1
  3. event事件(加群邀请等),优先级为3

PS:没有开启复读等相关功能的群没必要检测所有聊天内容,因此不以/开头的命令不会加入消息队列。

PPS:消息队列中的消息60s后仍未调度会被自动清除。

功能修改与添加

pika_rabbit.py中通过handlers的模块提供不同的功能,具体调用方式参考对应代码(其实是简单的getattr

不同的功能的代码存储于ffxivbot/handlers文件夹下,如果有对功能的修改或是添加,需要修改功能的注册过程ffxivbot/__init__.py

架构很乱,即便已经重构过一次但是仍存在诸多问题,欢迎各位dalao批评指正/激情PR。

性能优化

主要的性能问题在于在数据库存储过多的沙雕聊天记录会导致下一次消息索引时间变长,目前优化了一下逻辑,但是最好也要在数据库层面操作定时清除聊天记录的事件。

目前的逻辑如下:

  • 数据库中不存在的聊天消息会被计算hash(目前采用md5)作为索引存储到数据库,不存储原消息(因此数据库ffxivbot_chatmessagemessage字段为空)。
  • 如果一分钟内出现了第二条hash相同的消息,则会更新message字段,并按照群内设定的复读规则进行复读/口球。

在数据库中添加以下两个事件,每十分钟定时清除空白消息,每小时清除所有消息:

CREATE EVENT `clear empty message` ON SCHEDULE EVERY 10 MINUTE STARTS '2019-05-01 00:00:00.000000' ENDS '2023-05-01 00:00:00.000000' ON COMPLETION PRESERVE ENABLE DO DELETE FROM `ffxivbot_chatmessage` WHERE `message` LIKE ""
CREATE EVENT `clear chatmessage` ON SCHEDULE EVERY 1 HOUR STARTS '2019-02-28 03:00:00' ENDS '2022-01-01 03:00:00' ON COMPLETION PRESERVE ENABLE DO TRUNCATE `ffxivbot_chatmessage`

添加后需要进入数据库通过SET GLOBAL event_scheduler="ON"命令启动数据库定时事件,请注意这个操作最好由root用户进行,否则很可能权限不足。