hyper-bot 0.741__tar.gz → 0.772__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {hyper-bot-0.741 → hyper-bot-0.772}/Hyper/Adapters/OneBot.py +31 -43
- {hyper-bot-0.741 → hyper-bot-0.772}/Hyper/Adapters/OneBotLib/Manager.py +43 -9
- hyper-bot-0.772/Hyper/Adapters/OneBotLib/Res.py +90 -0
- hyper-bot-0.772/Hyper/Adapters/Satori.py +94 -0
- {hyper-bot-0.741 → hyper-bot-0.772}/Hyper/Configurator.py +5 -3
- {hyper-bot-0.741 → hyper-bot-0.772}/Hyper/Errors.py +6 -0
- {hyper-bot-0.741 → hyper-bot-0.772}/Hyper/Events.py +5 -1
- {hyper-bot-0.741 → hyper-bot-0.772}/Hyper/Listener.py +2 -0
- {hyper-bot-0.741 → hyper-bot-0.772}/Hyper/Manager.py +2 -0
- hyper-bot-0.772/Hyper/Network.py +156 -0
- {hyper-bot-0.741 → hyper-bot-0.772}/Hyper/Segments.py +32 -85
- hyper-bot-0.772/Hyper/Utils/Logic.py +333 -0
- hyper-bot-0.772/Hyper/Utils/TypeExt.py +177 -0
- {hyper-bot-0.741 → hyper-bot-0.772}/PKG-INFO +1 -1
- {hyper-bot-0.741 → hyper-bot-0.772}/hyper_bot.egg-info/PKG-INFO +1 -1
- {hyper-bot-0.741 → hyper-bot-0.772}/hyper_bot.egg-info/SOURCES.txt +4 -3
- {hyper-bot-0.741 → hyper-bot-0.772}/setup.py +2 -2
- hyper-bot-0.741/Hyper/Logic.py +0 -167
- hyper-bot-0.741/Hyper/ModuleClass.py +0 -67
- hyper-bot-0.741/Hyper/Network.py +0 -77
- hyper-bot-0.741/Hyper/WordSafety.py +0 -40
- {hyper-bot-0.741 → hyper-bot-0.772}/Hyper/DataBase.py +0 -0
- {hyper-bot-0.741 → hyper-bot-0.772}/Hyper/Logger.py +0 -0
- {hyper-bot-0.741 → hyper-bot-0.772}/LICENSE +0 -0
- {hyper-bot-0.741 → hyper-bot-0.772}/hyper_bot.egg-info/dependency_links.txt +0 -0
- {hyper-bot-0.741 → hyper-bot-0.772}/hyper_bot.egg-info/top_level.txt +0 -0
- {hyper-bot-0.741 → hyper-bot-0.772}/setup.cfg +0 -0
|
@@ -1,15 +1,15 @@
|
|
|
1
1
|
import json
|
|
2
|
-
import queue
|
|
3
2
|
import threading
|
|
4
3
|
import time
|
|
5
4
|
import asyncio
|
|
6
5
|
import os
|
|
7
6
|
from typing import Union
|
|
8
7
|
|
|
9
|
-
from Hyper import
|
|
8
|
+
from Hyper import Errors, Network, Events
|
|
9
|
+
from Hyper.Utils import Logic
|
|
10
|
+
from Hyper.Manager import reports
|
|
10
11
|
from Hyper.Events import *
|
|
11
12
|
|
|
12
|
-
reports = queue.Queue()
|
|
13
13
|
config = Configurator.cm.get_cfg()
|
|
14
14
|
logger = Logger.Logger()
|
|
15
15
|
logger.set_level(config.log_level)
|
|
@@ -24,20 +24,13 @@ class Actions:
|
|
|
24
24
|
self.connection = cnt_i
|
|
25
25
|
|
|
26
26
|
def __getattr__(self, item) -> callable:
|
|
27
|
-
def wrapper(
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
else:
|
|
35
|
-
packet = Manager.Packet(
|
|
36
|
-
str(item),
|
|
37
|
-
**kwargs
|
|
38
|
-
)
|
|
39
|
-
packet.send_to(self.connection)
|
|
40
|
-
return get_ret(packet.echo)
|
|
27
|
+
def wrapper(**kwargs) -> str:
|
|
28
|
+
packet = Manager.Packet(
|
|
29
|
+
str(item),
|
|
30
|
+
**kwargs
|
|
31
|
+
)
|
|
32
|
+
packet.send_to(self.connection)
|
|
33
|
+
return packet.echo
|
|
41
34
|
|
|
42
35
|
return wrapper
|
|
43
36
|
|
|
@@ -59,8 +52,17 @@ class Actions:
|
|
|
59
52
|
)
|
|
60
53
|
else:
|
|
61
54
|
raise Errors.ArgsInvalidError("'send' API requires 'group_id' or 'user_id' but none of them are provided.")
|
|
62
|
-
|
|
63
|
-
|
|
55
|
+
retried = 0
|
|
56
|
+
while 1:
|
|
57
|
+
packet.send_to(self.connection)
|
|
58
|
+
result = Manager.Ret.fetch(packet.echo)
|
|
59
|
+
if result.ret_code != 0 or (4 <= len(str(result.data.message_id)) <= 6):
|
|
60
|
+
retried += 1
|
|
61
|
+
if retried >= 5:
|
|
62
|
+
return result
|
|
63
|
+
await asyncio.sleep(1)
|
|
64
|
+
else:
|
|
65
|
+
return result
|
|
64
66
|
|
|
65
67
|
@Logger.AutoLogAsync.register(Logger.AutoLog.templates().recall, logger)
|
|
66
68
|
async def del_message(self, message_id: int) -> None:
|
|
@@ -90,13 +92,13 @@ class Actions:
|
|
|
90
92
|
async def get_login_info(self) -> Manager.Ret:
|
|
91
93
|
packet = Manager.Packet("get_login_info")
|
|
92
94
|
packet.send_to(self.connection)
|
|
93
|
-
return
|
|
95
|
+
return Manager.Ret.fetch(packet.echo)
|
|
94
96
|
|
|
95
97
|
@Logic.Cacher().cache_async
|
|
96
98
|
async def get_version_info(self) -> Manager.Ret:
|
|
97
99
|
packet = Manager.Packet("get_version_info")
|
|
98
100
|
packet.send_to(self.connection)
|
|
99
|
-
return
|
|
101
|
+
return Manager.Ret.fetch(packet.echo)
|
|
100
102
|
|
|
101
103
|
async def send_forward_msg(self, message: Manager.Message) -> Manager.Ret:
|
|
102
104
|
packet = Manager.Packet(
|
|
@@ -104,7 +106,7 @@ class Actions:
|
|
|
104
106
|
messages=await message.get()
|
|
105
107
|
)
|
|
106
108
|
packet.send_to(self.connection)
|
|
107
|
-
return
|
|
109
|
+
return Manager.Ret.fetch(packet.echo)
|
|
108
110
|
|
|
109
111
|
async def send_group_forward_msg(self, group_id: int, message: Manager.Message) -> Manager.Ret:
|
|
110
112
|
packet = Manager.Packet(
|
|
@@ -113,7 +115,7 @@ class Actions:
|
|
|
113
115
|
messages=await message.get()
|
|
114
116
|
)
|
|
115
117
|
packet.send_to(self.connection)
|
|
116
|
-
return
|
|
118
|
+
return Manager.Ret.fetch(packet.echo)
|
|
117
119
|
|
|
118
120
|
@Logger.AutoLogAsync.register(Logger.AutoLog.templates().set_req, logger)
|
|
119
121
|
async def set_group_add_request(self, flag: str, sub_type: str, approve: bool, reason: str = "Refused") -> None:
|
|
@@ -133,7 +135,7 @@ class Actions:
|
|
|
133
135
|
no_cache=True,
|
|
134
136
|
)
|
|
135
137
|
packet.send_to(self.connection)
|
|
136
|
-
return
|
|
138
|
+
return Manager.Ret.fetch(packet.echo)
|
|
137
139
|
|
|
138
140
|
@Logic.Cacher().cache_async
|
|
139
141
|
async def get_group_member_info(self, group_id: int, user_id: int) -> Manager.Ret:
|
|
@@ -144,7 +146,7 @@ class Actions:
|
|
|
144
146
|
no_cache=True
|
|
145
147
|
)
|
|
146
148
|
packet.send_to(self.connection)
|
|
147
|
-
return
|
|
149
|
+
return Manager.Ret.fetch(packet.echo)
|
|
148
150
|
|
|
149
151
|
@Logic.Cacher().cache_async
|
|
150
152
|
async def get_group_info(self, group_id: int) -> Manager.Ret:
|
|
@@ -154,12 +156,12 @@ class Actions:
|
|
|
154
156
|
no_cache=True
|
|
155
157
|
)
|
|
156
158
|
packet.send_to(self.connection)
|
|
157
|
-
return
|
|
159
|
+
return Manager.Ret.fetch(packet.echo)
|
|
158
160
|
|
|
159
161
|
async def get_status(self) -> Manager.Ret:
|
|
160
162
|
packet = Manager.Packet("get_status")
|
|
161
163
|
packet.send_to(self.connection)
|
|
162
|
-
return
|
|
164
|
+
return Manager.Ret.fetch(packet.echo)
|
|
163
165
|
|
|
164
166
|
@Logger.AutoLogAsync.register(Logger.AutoLog.templates().set_ess, logger)
|
|
165
167
|
async def set_essence_msg(self, message_id: int) -> None:
|
|
@@ -182,7 +184,7 @@ class Actions:
|
|
|
182
184
|
message_id=msg_id
|
|
183
185
|
)
|
|
184
186
|
packet.send_to(self.connection)
|
|
185
|
-
return
|
|
187
|
+
return Manager.Ret.fetch(packet.echo)
|
|
186
188
|
|
|
187
189
|
|
|
188
190
|
async def tester(message_data: Event, actions: Actions) -> None:
|
|
@@ -191,7 +193,7 @@ async def tester(message_data: Event, actions: Actions) -> None:
|
|
|
191
193
|
|
|
192
194
|
async def __handler(data: dict, actions: Actions) -> None:
|
|
193
195
|
if data.get("echo") is not None:
|
|
194
|
-
reports.put(
|
|
196
|
+
reports.put(data)
|
|
195
197
|
elif data.get("post_type") == "meta_event" or data.get("user_id") == data.get("self_id"):
|
|
196
198
|
pass
|
|
197
199
|
else:
|
|
@@ -208,7 +210,6 @@ async def __handler(data: dict, actions: Actions) -> None:
|
|
|
208
210
|
|
|
209
211
|
|
|
210
212
|
handler: callable = tester
|
|
211
|
-
connection: callable = tester
|
|
212
213
|
|
|
213
214
|
|
|
214
215
|
def reg(func: callable):
|
|
@@ -216,20 +217,7 @@ def reg(func: callable):
|
|
|
216
217
|
handler = func
|
|
217
218
|
|
|
218
219
|
|
|
219
|
-
def get_ret(echo: str) -> Manager.Ret:
|
|
220
|
-
old = None
|
|
221
|
-
while True:
|
|
222
|
-
content: Manager.Ret = reports.get()
|
|
223
|
-
if old is not None:
|
|
224
|
-
reports.put(old)
|
|
225
|
-
if content.echo == echo:
|
|
226
|
-
return content
|
|
227
|
-
else:
|
|
228
|
-
old = content
|
|
229
|
-
|
|
230
|
-
|
|
231
220
|
def run():
|
|
232
|
-
global connection
|
|
233
221
|
try:
|
|
234
222
|
if handler is tester:
|
|
235
223
|
raise Errors.ListenerNotRegisteredError("No handler registered")
|
|
@@ -1,11 +1,13 @@
|
|
|
1
|
-
|
|
2
|
-
from Hyper
|
|
3
|
-
from Hyper.
|
|
1
|
+
import Hyper.Utils.TypeExt
|
|
2
|
+
from Hyper import Configurator, Logger, Network, Segments
|
|
3
|
+
from Hyper.Utils import Logic
|
|
4
4
|
|
|
5
5
|
from typing import Union
|
|
6
|
-
import
|
|
6
|
+
import queue
|
|
7
7
|
import random
|
|
8
|
+
import json
|
|
8
9
|
|
|
10
|
+
reports = queue.Queue()
|
|
9
11
|
config = Configurator.cm.get_cfg()
|
|
10
12
|
logger = Logger.Logger()
|
|
11
13
|
logger.set_level(config.log_level)
|
|
@@ -33,7 +35,30 @@ class Packet:
|
|
|
33
35
|
connection.send(self.endpoint, payload, self.echo)
|
|
34
36
|
|
|
35
37
|
|
|
38
|
+
class MessageBuilder:
|
|
39
|
+
def __init__(self):
|
|
40
|
+
self.sgs = []
|
|
41
|
+
|
|
42
|
+
def __getattr__(self, item):
|
|
43
|
+
if item == "build":
|
|
44
|
+
def build() -> Message:
|
|
45
|
+
return Message(*self.sgs)
|
|
46
|
+
|
|
47
|
+
return build
|
|
48
|
+
|
|
49
|
+
elif item in Segments.message_types.keys():
|
|
50
|
+
def wrapper(*args, **kwargs):
|
|
51
|
+
self.sgs.append(Segments.message_types[item]["type"](*args, **kwargs))
|
|
52
|
+
return self
|
|
53
|
+
|
|
54
|
+
return wrapper
|
|
55
|
+
else:
|
|
56
|
+
return None
|
|
57
|
+
|
|
58
|
+
|
|
36
59
|
class Message:
|
|
60
|
+
builder = MessageBuilder()
|
|
61
|
+
|
|
37
62
|
def __init__(self, *args):
|
|
38
63
|
if len(args) == 1 and isinstance(args[0], list):
|
|
39
64
|
contents = args[0]
|
|
@@ -47,10 +72,7 @@ class Message:
|
|
|
47
72
|
self.contents.append(content)
|
|
48
73
|
|
|
49
74
|
async def get(self) -> list:
|
|
50
|
-
|
|
51
|
-
for i in self.contents:
|
|
52
|
-
ret.append(i.to_json())
|
|
53
|
-
return ret
|
|
75
|
+
return self.get_sync()
|
|
54
76
|
|
|
55
77
|
def get_sync(self) -> list:
|
|
56
78
|
ret = []
|
|
@@ -93,5 +115,17 @@ class Ret:
|
|
|
93
115
|
def __init__(self, json_data: dict):
|
|
94
116
|
self.status = json_data["status"]
|
|
95
117
|
self.ret_code = json_data["retcode"]
|
|
96
|
-
self.data = json_data.get("data")
|
|
118
|
+
self.data = Hyper.Utils.TypeExt.ObjectedDict(json_data.get("data"))
|
|
97
119
|
self.echo = json_data.get("echo")
|
|
120
|
+
|
|
121
|
+
@classmethod
|
|
122
|
+
def fetch(cls, echo: str) -> "Ret":
|
|
123
|
+
old = None
|
|
124
|
+
while True:
|
|
125
|
+
content = reports.get()
|
|
126
|
+
if old is not None:
|
|
127
|
+
reports.put(old)
|
|
128
|
+
if content["echo"] == echo:
|
|
129
|
+
return cls(content)
|
|
130
|
+
else:
|
|
131
|
+
old = content
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
message_types = {}
|
|
2
|
+
|
|
3
|
+
def segment_builder(sg_type: str, summary_tmp: str = None):
|
|
4
|
+
# print(inspect.get_annotations(cls))
|
|
5
|
+
def inner_builder(cls):
|
|
6
|
+
var = dict(vars(cls))
|
|
7
|
+
anns: dict = var.get("__annotations__", False) or dict()
|
|
8
|
+
|
|
9
|
+
def init(self, *args, **kwargs):
|
|
10
|
+
arg = {}
|
|
11
|
+
if len(args) > 0:
|
|
12
|
+
for i in args:
|
|
13
|
+
arg[list(anns.keys())[list(args).index(i)]] = i
|
|
14
|
+
|
|
15
|
+
if len(kwargs) > 0:
|
|
16
|
+
for i in kwargs:
|
|
17
|
+
try:
|
|
18
|
+
arg[i] = anns[i](kwargs[i])
|
|
19
|
+
except TypeError:
|
|
20
|
+
arg[i] = kwargs[i]
|
|
21
|
+
new_arg = arg.copy()
|
|
22
|
+
|
|
23
|
+
if len(anns) > len(arg):
|
|
24
|
+
for i in anns.keys():
|
|
25
|
+
if i not in arg.keys():
|
|
26
|
+
if i not in var.keys():
|
|
27
|
+
new_arg[i] = None
|
|
28
|
+
continue
|
|
29
|
+
if not isinstance(var[i], anns[i]):
|
|
30
|
+
new_arg[i] = anns[i](var[i])
|
|
31
|
+
else:
|
|
32
|
+
new_arg[i] = var[i]
|
|
33
|
+
|
|
34
|
+
for i in new_arg:
|
|
35
|
+
setattr(self, i, new_arg[i])
|
|
36
|
+
|
|
37
|
+
cls.__init__ = init
|
|
38
|
+
|
|
39
|
+
def to_json(self) -> dict:
|
|
40
|
+
base = {"type": sg_type, "data": {}}
|
|
41
|
+
for i in anns:
|
|
42
|
+
if getattr(self, i) is None:
|
|
43
|
+
continue
|
|
44
|
+
if not isinstance(getattr(self, i), anns[i]):
|
|
45
|
+
base["data"][i] = anns[i](getattr(self, i))
|
|
46
|
+
else:
|
|
47
|
+
base["data"][i] = getattr(self, i)
|
|
48
|
+
# try:
|
|
49
|
+
# base["data"][i] = anns[i](getattr(self, i))
|
|
50
|
+
# except TypeError:
|
|
51
|
+
# base["data"][i] = getattr(self, i)
|
|
52
|
+
return base
|
|
53
|
+
|
|
54
|
+
cls.to_json = to_json
|
|
55
|
+
|
|
56
|
+
def to_str(self) -> str:
|
|
57
|
+
text = summary_tmp
|
|
58
|
+
if text is None:
|
|
59
|
+
text = "[]"
|
|
60
|
+
if "<" not in text and ">" not in text:
|
|
61
|
+
return text
|
|
62
|
+
|
|
63
|
+
for i in anns:
|
|
64
|
+
if f"<{i}>" in summary_tmp:
|
|
65
|
+
try:
|
|
66
|
+
v = self.__getattribute__(i)
|
|
67
|
+
except AttributeError:
|
|
68
|
+
v = None
|
|
69
|
+
text = text.replace(f"<{i}>", str(v))
|
|
70
|
+
|
|
71
|
+
return text
|
|
72
|
+
|
|
73
|
+
cls.__str__ = to_str if cls().__str__() == "__not_set__" else cls.__str__
|
|
74
|
+
|
|
75
|
+
message_types[sg_type] = {
|
|
76
|
+
"type": cls,
|
|
77
|
+
"args": list(anns.keys())
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
return cls
|
|
81
|
+
|
|
82
|
+
return inner_builder
|
|
83
|
+
|
|
84
|
+
|
|
85
|
+
class Base:
|
|
86
|
+
def __init__(self, *args, **kwargs): ...
|
|
87
|
+
|
|
88
|
+
def to_json(self) -> dict: ...
|
|
89
|
+
|
|
90
|
+
def __str__(self) -> str: return "__not_set__"
|
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
from Hyper.Adapters.OneBot import *
|
|
2
|
+
from Hyper.Errors import *
|
|
3
|
+
|
|
4
|
+
|
|
5
|
+
class Actions(Actions):
|
|
6
|
+
def __init__(self, cnt: Union[Network.WebsocketConnection, Network.HTTPConnection, Network.SatoriConnection]):
|
|
7
|
+
self.connection = cnt
|
|
8
|
+
|
|
9
|
+
class CustomAction:
|
|
10
|
+
def __init__(self,
|
|
11
|
+
cnt_i: Union[Network.WebsocketConnection, Network.HTTPConnection, Network.SatoriConnection]):
|
|
12
|
+
self.connection = cnt_i
|
|
13
|
+
|
|
14
|
+
def __getattr__(self, item) -> callable:
|
|
15
|
+
def wrapper(**kwargs) -> str:
|
|
16
|
+
packet = Manager.Packet(
|
|
17
|
+
str(item),
|
|
18
|
+
**kwargs
|
|
19
|
+
)
|
|
20
|
+
packet.send_to(self.connection)
|
|
21
|
+
return packet.echo
|
|
22
|
+
|
|
23
|
+
return wrapper
|
|
24
|
+
|
|
25
|
+
self.custom = CustomAction(self.connection)
|
|
26
|
+
|
|
27
|
+
|
|
28
|
+
async def __handler(data: dict, actions: Actions) -> None:
|
|
29
|
+
if data["op"] == 2:
|
|
30
|
+
pass
|
|
31
|
+
else:
|
|
32
|
+
# task = asyncio.create_task(handler(Events.em.new(data), actions))
|
|
33
|
+
# timed = 0
|
|
34
|
+
#
|
|
35
|
+
# while not task.done():
|
|
36
|
+
# await asyncio.sleep(0.1)
|
|
37
|
+
# timed += 0.1
|
|
38
|
+
# if timed >= 30:
|
|
39
|
+
# task.cancel()
|
|
40
|
+
# logger.log(f"处理{task.get_name()}超时", level=Logger.levels.ERROR)
|
|
41
|
+
# break
|
|
42
|
+
print(data)
|
|
43
|
+
|
|
44
|
+
|
|
45
|
+
def reg(func: callable):
|
|
46
|
+
global handler
|
|
47
|
+
handler = func
|
|
48
|
+
|
|
49
|
+
|
|
50
|
+
def run():
|
|
51
|
+
try:
|
|
52
|
+
if handler is tester:
|
|
53
|
+
raise Errors.ListenerNotRegisteredError("No handler registered")
|
|
54
|
+
# connection = websocket.WebSocket()
|
|
55
|
+
if isinstance(config.connection, Configurator.WSConnectionC):
|
|
56
|
+
connection = Network.SatoriConnection(
|
|
57
|
+
config.connection.host, config.connection.port, config.connection.token
|
|
58
|
+
)
|
|
59
|
+
else:
|
|
60
|
+
raise ConfigError
|
|
61
|
+
retried = 0
|
|
62
|
+
while True:
|
|
63
|
+
try:
|
|
64
|
+
connection.connect()
|
|
65
|
+
except ConnectionRefusedError or TimeoutError:
|
|
66
|
+
if retried >= config.connection.retries:
|
|
67
|
+
logger.log(f"重试次数达到最大值({config.connection.retries}),退出", level=Logger.levels.CRITICAL)
|
|
68
|
+
break
|
|
69
|
+
|
|
70
|
+
logger.log(f"连接建立失败,3秒后重试({retried}/{config.connection.retries})",
|
|
71
|
+
level=Logger.levels.WARNING)
|
|
72
|
+
retried += 1
|
|
73
|
+
time.sleep(3)
|
|
74
|
+
continue
|
|
75
|
+
logger.log("成功建立连接", level=Logger.levels.INFO)
|
|
76
|
+
retried = 0
|
|
77
|
+
actions = Actions(connection)
|
|
78
|
+
while True:
|
|
79
|
+
try:
|
|
80
|
+
data = connection.recv()
|
|
81
|
+
except ConnectionResetError:
|
|
82
|
+
logger.log("连接断开", level=Logger.levels.ERROR)
|
|
83
|
+
break
|
|
84
|
+
except json.decoder.JSONDecodeError:
|
|
85
|
+
logger.log("收到错误的JSON内容", level=Logger.levels.ERROR)
|
|
86
|
+
threading.Thread(target=lambda: asyncio.run(__handler(data, actions))).start()
|
|
87
|
+
except KeyboardInterrupt:
|
|
88
|
+
logger.log("正在退出(Ctrl+C)", level=Logger.levels.WARNING)
|
|
89
|
+
try:
|
|
90
|
+
connection.close()
|
|
91
|
+
except:
|
|
92
|
+
pass
|
|
93
|
+
os._exit(0)
|
|
94
|
+
|
|
@@ -1,13 +1,14 @@
|
|
|
1
1
|
import typing
|
|
2
2
|
|
|
3
|
-
from Hyper import Logic
|
|
3
|
+
from Hyper.Utils import Logic
|
|
4
4
|
|
|
5
5
|
|
|
6
6
|
class WSConnectionC:
|
|
7
|
-
def __init__(self, host: str, port: int, retries: int = 0):
|
|
7
|
+
def __init__(self, host: str, port: int, retries: int = 0, satori_token: str = None):
|
|
8
8
|
self.host: str = host
|
|
9
9
|
self.port: int = port
|
|
10
10
|
self.retries: int = retries
|
|
11
|
+
self.token: str = satori_token
|
|
11
12
|
|
|
12
13
|
|
|
13
14
|
class HTTPConnectionC:
|
|
@@ -55,7 +56,8 @@ class Config:
|
|
|
55
56
|
self.connection = WSConnectionC(
|
|
56
57
|
config_json["Connection"]["host"],
|
|
57
58
|
config_json["Connection"]["port"],
|
|
58
|
-
config_json["Connection"]["retries"]
|
|
59
|
+
config_json["Connection"]["retries"],
|
|
60
|
+
config_json["Connection"]["satori_token"]
|
|
59
61
|
)
|
|
60
62
|
elif config_json["Connection"]["mode"] == "HTTP":
|
|
61
63
|
self.connection = HTTPConnectionC(
|
|
@@ -16,3 +16,9 @@ class ListenerNotRegisteredError(Exception):
|
|
|
16
16
|
class ArgsInvalidError(Exception):
|
|
17
17
|
def __init__(self, message: str = None):
|
|
18
18
|
super().__init__(message)
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
class ConfigError(Exception):
|
|
22
|
+
def __init__(self, message: str = None):
|
|
23
|
+
super().__init__(message)
|
|
24
|
+
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
from Hyper import Configurator, Logger, Manager
|
|
2
|
+
from Hyper.Utils.TypeExt import Integer
|
|
2
3
|
from Hyper.Segments import message_types
|
|
3
4
|
from Hyper.Logger import levels
|
|
4
5
|
|
|
@@ -14,10 +15,12 @@ class EventManager:
|
|
|
14
15
|
"notice": {},
|
|
15
16
|
"request": {}
|
|
16
17
|
}
|
|
18
|
+
self.events = []
|
|
17
19
|
|
|
18
20
|
def reg(self, type_of: str, str_eql: str) -> callable:
|
|
19
21
|
def wrapper(cls):
|
|
20
22
|
self.event_lis[type_of][str_eql] = cls
|
|
23
|
+
self.events.append(cls)
|
|
21
24
|
return cls
|
|
22
25
|
|
|
23
26
|
return wrapper
|
|
@@ -88,7 +91,7 @@ class Event:
|
|
|
88
91
|
self.user_id = data.get("user_id")
|
|
89
92
|
self.group_id = data.get("group_id")
|
|
90
93
|
|
|
91
|
-
self.is_owner =
|
|
94
|
+
self.is_owner = Integer.convert_from(self.user_id) in config.owner
|
|
92
95
|
self.servicing = False
|
|
93
96
|
self.blocked = True if self.user_id in config.black_list or self.group_id in config.black_list else False
|
|
94
97
|
self.is_silent = self.user_id in config.silents or self.group_id in config.silents or 0 in config.silents
|
|
@@ -103,6 +106,7 @@ class MessageEvent(Event):
|
|
|
103
106
|
self.sub_type = data.get("sub_type")
|
|
104
107
|
self.message_id = str(data.get("message_id"))
|
|
105
108
|
self.message = gen_message(data=data)
|
|
109
|
+
self.msg_str = str(self.message)
|
|
106
110
|
|
|
107
111
|
|
|
108
112
|
@em.reg("message", "private")
|
|
@@ -0,0 +1,156 @@
|
|
|
1
|
+
import asyncio
|
|
2
|
+
import time
|
|
3
|
+
import websocket
|
|
4
|
+
import httpx
|
|
5
|
+
import queue
|
|
6
|
+
import flask
|
|
7
|
+
import traceback
|
|
8
|
+
import json
|
|
9
|
+
import logging
|
|
10
|
+
import threading
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
class WebsocketConnection:
|
|
14
|
+
def __init__(self, url: str):
|
|
15
|
+
self.ws = websocket.WebSocket()
|
|
16
|
+
self.url = url
|
|
17
|
+
|
|
18
|
+
def connect(self) -> None:
|
|
19
|
+
self.ws.connect(self.url)
|
|
20
|
+
|
|
21
|
+
def send(self, message: str) -> None:
|
|
22
|
+
self.ws.send(message)
|
|
23
|
+
|
|
24
|
+
def close(self) -> None:
|
|
25
|
+
self.ws.close()
|
|
26
|
+
|
|
27
|
+
def recv(self) -> dict:
|
|
28
|
+
return json.loads(self.ws.recv())
|
|
29
|
+
|
|
30
|
+
|
|
31
|
+
class HTTPConnection:
|
|
32
|
+
def __init__(self, url: str, listener_url: str):
|
|
33
|
+
self.url = url
|
|
34
|
+
listener_url = listener_url.replace("http://", "")
|
|
35
|
+
listener_url = listener_url.replace("https://", "")
|
|
36
|
+
self.listener_url = listener_url.split(":")[0]
|
|
37
|
+
try:
|
|
38
|
+
self.port = int(listener_url.split(":")[1])
|
|
39
|
+
except IndexError:
|
|
40
|
+
self.port = 8080
|
|
41
|
+
self.app = flask.Flask(__name__)
|
|
42
|
+
self.app.config["LOGGER_HANDLER_POLICY"] = "never"
|
|
43
|
+
logging.getLogger("werkzeug").setLevel(logging.ERROR)
|
|
44
|
+
self.reports = queue.Queue()
|
|
45
|
+
|
|
46
|
+
self.listener_started = False
|
|
47
|
+
|
|
48
|
+
def __start_listener(self) -> None:
|
|
49
|
+
@self.app.route("/", methods=["POST"])
|
|
50
|
+
def listener():
|
|
51
|
+
self.reports.put(flask.request.json)
|
|
52
|
+
return {}
|
|
53
|
+
|
|
54
|
+
# self.app.run(host=self.listener_url, port=self.port)
|
|
55
|
+
|
|
56
|
+
threading.Thread(target=lambda: self.app.run(host=self.listener_url, port=self.port)).start()
|
|
57
|
+
self.listener_started = True
|
|
58
|
+
|
|
59
|
+
def connect(self) -> None:
|
|
60
|
+
if not self.listener_started:
|
|
61
|
+
self.__start_listener()
|
|
62
|
+
httpx.post(self.url)
|
|
63
|
+
traceback.print_exc()
|
|
64
|
+
|
|
65
|
+
def recv(self) -> dict:
|
|
66
|
+
return self.reports.get()
|
|
67
|
+
|
|
68
|
+
def send(self, endpoint: str, data: dict, echo: str) -> None:
|
|
69
|
+
response = httpx.post(f"{self.url}/{endpoint}", json=data)
|
|
70
|
+
res = response.json()
|
|
71
|
+
res["echo"] = echo
|
|
72
|
+
self.reports.put(res)
|
|
73
|
+
|
|
74
|
+
@staticmethod
|
|
75
|
+
def close() -> None:
|
|
76
|
+
shutdown_func = flask.request.environ.get('werkzeug.server.shutdown')
|
|
77
|
+
if shutdown_func is None:
|
|
78
|
+
raise RuntimeError('Not running with the Werkzeug Server')
|
|
79
|
+
shutdown_func()
|
|
80
|
+
|
|
81
|
+
|
|
82
|
+
class SatoriConnection:
|
|
83
|
+
def __init__(self, host: str, port: int, token: str = None):
|
|
84
|
+
self.ws = websocket.WebSocket()
|
|
85
|
+
self.host = host
|
|
86
|
+
self.port = port
|
|
87
|
+
self.token = token
|
|
88
|
+
self.reports = queue.Queue()
|
|
89
|
+
|
|
90
|
+
def heart_beat(self) -> None:
|
|
91
|
+
while 1:
|
|
92
|
+
time.sleep(10)
|
|
93
|
+
self.ws.send(json.dumps({"op": 1, "body": {}}))
|
|
94
|
+
|
|
95
|
+
def connect(self) -> None:
|
|
96
|
+
self.ws.connect(f"ws://{self.host}:{self.port}/v1/events")
|
|
97
|
+
payload = {
|
|
98
|
+
"op": 3,
|
|
99
|
+
"body": {
|
|
100
|
+
"token": self.token
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
self.ws.send(json.dumps(payload))
|
|
104
|
+
res = json.loads(self.ws.recv())
|
|
105
|
+
if res["op"] == 4:
|
|
106
|
+
threading.Thread(target=self.heart_beat).start()
|
|
107
|
+
else:
|
|
108
|
+
raise ConnectionError("连接失败")
|
|
109
|
+
|
|
110
|
+
def send(self, payload: dict, echo: str = None) -> None:
|
|
111
|
+
response = httpx.post(f"http://{self.host}:{self.port}", json=payload)
|
|
112
|
+
try:
|
|
113
|
+
data = response.json()
|
|
114
|
+
data["echo"] = echo
|
|
115
|
+
self.reports.put(data)
|
|
116
|
+
except:
|
|
117
|
+
pass
|
|
118
|
+
|
|
119
|
+
def close(self) -> None:
|
|
120
|
+
pass
|
|
121
|
+
|
|
122
|
+
def recv(self) -> dict:
|
|
123
|
+
return json.loads(self.ws.recv())
|
|
124
|
+
|
|
125
|
+
#
|
|
126
|
+
# class KritorConnection:
|
|
127
|
+
# def __init__(self, host: str, port: int, account: str, ticket: str):
|
|
128
|
+
# self.channel = grpc.insecure_channel(f"{host}:{port}")
|
|
129
|
+
# self.account = account
|
|
130
|
+
# self.ticket = ticket
|
|
131
|
+
#
|
|
132
|
+
# def connect(self) -> None:
|
|
133
|
+
# auth_stub = AuthenticationServiceStub(self.channel)
|
|
134
|
+
# response = auth_stub.Authenticate(
|
|
135
|
+
# AuthenticateRequest(
|
|
136
|
+
# account=self.account,
|
|
137
|
+
# ticket=self.ticket
|
|
138
|
+
# )
|
|
139
|
+
# )
|
|
140
|
+
# if response.AuthenticateResponseCode != 0:
|
|
141
|
+
# raise ConnectionError("鉴权失败")
|
|
142
|
+
#
|
|
143
|
+
# def send(self, stub, payload: dict, echo: str = None) -> None:
|
|
144
|
+
# response = httpx.post(f"http://{self.host}:{self.port}", json=payload)
|
|
145
|
+
# try:
|
|
146
|
+
# data = response.json()
|
|
147
|
+
# data["echo"] = echo
|
|
148
|
+
# self.reports.put(data)
|
|
149
|
+
# except:
|
|
150
|
+
# pass
|
|
151
|
+
#
|
|
152
|
+
# def close(self) -> None:
|
|
153
|
+
# pass
|
|
154
|
+
#
|
|
155
|
+
# def recv(self) -> dict:
|
|
156
|
+
# return json.loads(self.ws.recv())
|