nonebot-plugin-l4d2-server 1.0.0a1__py3-none-any.whl → 1.0.0a2__py3-none-any.whl

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.
Files changed (136) hide show
  1. nonebot_plugin_l4d2_server/__init__.py +4 -4
  2. nonebot_plugin_l4d2_server/__main__.py +64 -14
  3. nonebot_plugin_l4d2_server/config.py +6 -1
  4. nonebot_plugin_l4d2_server/l4_anne/__init__.py +124 -0
  5. nonebot_plugin_l4d2_server/l4_anne/ranne.py +18 -0
  6. nonebot_plugin_l4d2_server/l4_help/Help.json +59 -22
  7. nonebot_plugin_l4d2_server/l4_help/__init__.py +2 -2
  8. nonebot_plugin_l4d2_server/l4_help/icon//344/273/213/347/273/215.png +0 -0
  9. nonebot_plugin_l4d2_server/l4_help/icon//344/273/273/345/212/241.png +0 -0
  10. nonebot_plugin_l4d2_server/l4_help/icon//344/277/241/346/201/257.png +0 -0
  11. nonebot_plugin_l4d2_server/l4_help/icon//345/205/254/345/221/212.png +0 -0
  12. nonebot_plugin_l4d2_server/l4_help/icon//345/210/200/345/211/221.png +0 -0
  13. nonebot_plugin_l4d2_server/l4_help/icon//345/210/207/346/215/242.png +0 -0
  14. nonebot_plugin_l4d2_server/l4_help/icon//345/210/240/351/231/244.png +0 -0
  15. nonebot_plugin_l4d2_server/l4_help/icon//345/210/267/346/226/260.png +0 -0
  16. nonebot_plugin_l4d2_server/l4_help/icon//345/215/241/347/273/204.png +0 -0
  17. nonebot_plugin_l4d2_server/l4_help/icon//345/223/252/351/207/214.png +0 -0
  18. nonebot_plugin_l4d2_server/l4_help/icon//345/234/260/345/233/276.png +0 -0
  19. nonebot_plugin_l4d2_server/l4_help/icon//345/257/274/345/205/245.png +0 -0
  20. nonebot_plugin_l4d2_server/l4_help/icon//345/257/274/345/207/272.png +0 -0
  21. nonebot_plugin_l4d2_server/l4_help/icon//345/275/261.png +0 -0
  22. nonebot_plugin_l4d2_server/l4_help/icon//346/213/274/345/233/276.png +0 -0
  23. nonebot_plugin_l4d2_server/l4_help/icon//346/216/242/347/264/242.png +0 -0
  24. nonebot_plugin_l4d2_server/l4_help/icon//346/216/250/351/200/201.png +0 -0
  25. nonebot_plugin_l4d2_server/l4_help/icon//346/224/266/351/233/206.png +0 -0
  26. nonebot_plugin_l4d2_server/l4_help/icon//346/224/273/347/225/245.png +0 -0
  27. nonebot_plugin_l4d2_server/l4_help/icon//346/233/264/346/226/260.png +0 -0
  28. nonebot_plugin_l4d2_server/l4_help/icon//346/235/220/346/226/231.png +0 -0
  29. nonebot_plugin_l4d2_server/l4_help/icon//346/237/245/350/257/242.png +0 -0
  30. nonebot_plugin_l4d2_server/l4_help/icon//346/240/241/351/252/214.png +0 -0
  31. nonebot_plugin_l4d2_server/l4_help/icon//346/257/217/346/234/210.png +0 -0
  32. nonebot_plugin_l4d2_server/l4_help/icon//346/267/261/346/270/212.png +0 -0
  33. nonebot_plugin_l4d2_server/l4_help/icon//346/267/273/345/212/240.png +0 -0
  34. nonebot_plugin_l4d2_server/l4_help/icon//346/270/205/351/231/244.png +0 -0
  35. nonebot_plugin_l4d2_server/l4_help/icon//347/212/266/346/200/201.png +0 -0
  36. nonebot_plugin_l4d2_server/l4_help/icon//347/255/276/345/210/260.png +0 -0
  37. nonebot_plugin_l4d2_server/l4_help/icon//347/273/221/345/256/232.png +0 -0
  38. nonebot_plugin_l4d2_server/l4_help/icon//350/241/250.png +0 -0
  39. nonebot_plugin_l4d2_server/l4_help/icon//350/241/250/346/203/205.png +0 -0
  40. nonebot_plugin_l4d2_server/l4_help/icon//350/247/222/350/211/262.png +0 -0
  41. nonebot_plugin_l4d2_server/l4_help/icon//350/256/260/345/275/225.png +0 -0
  42. nonebot_plugin_l4d2_server/l4_help/icon//351/205/215/347/275/256.png +0 -0
  43. nonebot_plugin_l4d2_server/l4_help/icon//351/207/215/345/220/257.png +0 -0
  44. nonebot_plugin_l4d2_server/l4_help/texture2d/badge.png +0 -0
  45. nonebot_plugin_l4d2_server/l4_help/texture2d/banner.png +0 -0
  46. nonebot_plugin_l4d2_server/l4_help/texture2d/bg.jpg +0 -0
  47. nonebot_plugin_l4d2_server/l4_help/texture2d/button.png +0 -0
  48. nonebot_plugin_l4d2_server/l4_help/texture2d/icon.png +0 -0
  49. nonebot_plugin_l4d2_server/l4_image/__init__.py +4 -4
  50. nonebot_plugin_l4d2_server/l4_image/anne_pil.py +17 -0
  51. nonebot_plugin_l4d2_server/l4_image/convert.py +1 -1
  52. nonebot_plugin_l4d2_server/l4_image/download.py +5 -5
  53. nonebot_plugin_l4d2_server/l4_image/html_img.py +45 -74
  54. nonebot_plugin_l4d2_server/l4_image/image_tools.py +11 -11
  55. nonebot_plugin_l4d2_server/l4_image/img/anne/back.png +0 -0
  56. nonebot_plugin_l4d2_server/l4_image/img/anne/back1.jpg +0 -0
  57. nonebot_plugin_l4d2_server/l4_image/img/head/head.png +0 -0
  58. nonebot_plugin_l4d2_server/l4_image/img/header/logo.png +0 -0
  59. nonebot_plugin_l4d2_server/l4_image/img/header/player1.jpg +0 -0
  60. nonebot_plugin_l4d2_server/l4_image/img/template/Bocchi_The_Rock.html +17 -30
  61. nonebot_plugin_l4d2_server/l4_image/img/template/Bocchi_The_Rock.png +0 -0
  62. nonebot_plugin_l4d2_server/l4_image/img/template/Pixel.html +17 -26
  63. nonebot_plugin_l4d2_server/l4_image/img/template/Pixel.png +0 -0
  64. nonebot_plugin_l4d2_server/l4_image/img/template/Rainbow.html +48 -14
  65. nonebot_plugin_l4d2_server/l4_image/img/template/Rainbow.png +0 -0
  66. nonebot_plugin_l4d2_server/l4_image/img/template/normal.html +14 -24
  67. nonebot_plugin_l4d2_server/{data/img → l4_image/img/template}/vac.png +0 -0
  68. nonebot_plugin_l4d2_server/l4_image/img/template/vac_white.png +0 -0
  69. nonebot_plugin_l4d2_server/l4_image/vtfs.py +3 -3
  70. nonebot_plugin_l4d2_server/l4_request/__init__.py +68 -9
  71. nonebot_plugin_l4d2_server/l4_request/draw_msg.py +38 -43
  72. nonebot_plugin_l4d2_server/l4_request/utils.py +0 -0
  73. nonebot_plugin_l4d2_server/utils/api/api.py +8 -2
  74. nonebot_plugin_l4d2_server/utils/api/models.py +108 -0
  75. nonebot_plugin_l4d2_server/utils/api/request.py +257 -39
  76. nonebot_plugin_l4d2_server/utils/database/models.py +12 -23
  77. nonebot_plugin_l4d2_server/utils/utils.py +10 -10
  78. {nonebot_plugin_l4d2_server-1.0.0a1.dist-info → nonebot_plugin_l4d2_server-1.0.0a2.dist-info}/METADATA +19 -11
  79. nonebot_plugin_l4d2_server-1.0.0a2.dist-info/RECORD +96 -0
  80. nonebot_plugin_l4d2_server/data/L4D2/image/head/head.png +0 -0
  81. nonebot_plugin_l4d2_server/data/L4D2/image/header/logo.png +0 -0
  82. nonebot_plugin_l4d2_server/data/L4D2/image/header/player1.jpg +0 -0
  83. nonebot_plugin_l4d2_server/data/L4D2/image/template/anne.html +0 -68
  84. nonebot_plugin_l4d2_server/data/L4D2/image/template/back.png +0 -0
  85. nonebot_plugin_l4d2_server/data/L4D2/image/template/fingerprint.svg +0 -15
  86. nonebot_plugin_l4d2_server/data/L4D2/image/template/group_ip.html +0 -258
  87. nonebot_plugin_l4d2_server/data/L4D2/image/template/help.html +0 -262
  88. nonebot_plugin_l4d2_server/data/L4D2/image/template/help_dack.html +0 -269
  89. nonebot_plugin_l4d2_server/data/L4D2/image/template/ip.html +0 -54
  90. nonebot_plugin_l4d2_server/data/L4D2/image/template/l.svg +0 -10
  91. nonebot_plugin_l4d2_server/data/L4D2/image/template/m.svg +0 -1
  92. nonebot_plugin_l4d2_server/data/L4D2/image/template/vue.css +0 -531
  93. nonebot_plugin_l4d2_server/data/L4D2/image/template/w.svg +0 -1
  94. nonebot_plugin_l4d2_server/data/icon//344/273/213/347/273/215.png +0 -0
  95. nonebot_plugin_l4d2_server/data/icon//344/273/273/345/212/241.png +0 -0
  96. nonebot_plugin_l4d2_server/data/icon//344/277/241/346/201/257.png +0 -0
  97. nonebot_plugin_l4d2_server/data/icon//345/205/254/345/221/212.png +0 -0
  98. nonebot_plugin_l4d2_server/data/icon//345/210/200/345/211/221.png +0 -0
  99. nonebot_plugin_l4d2_server/data/icon//345/210/207/346/215/242.png +0 -0
  100. nonebot_plugin_l4d2_server/data/icon//345/210/240/351/231/244.png +0 -0
  101. nonebot_plugin_l4d2_server/data/icon//345/210/267/346/226/260.png +0 -0
  102. nonebot_plugin_l4d2_server/data/icon//345/215/241/347/273/204.png +0 -0
  103. nonebot_plugin_l4d2_server/data/icon//345/223/252/351/207/214.png +0 -0
  104. nonebot_plugin_l4d2_server/data/icon//345/234/260/345/233/276.png +0 -0
  105. nonebot_plugin_l4d2_server/data/icon//345/257/274/345/205/245.png +0 -0
  106. nonebot_plugin_l4d2_server/data/icon//345/257/274/345/207/272.png +0 -0
  107. nonebot_plugin_l4d2_server/data/icon//345/275/261.png +0 -0
  108. nonebot_plugin_l4d2_server/data/icon//346/213/274/345/233/276.png +0 -0
  109. nonebot_plugin_l4d2_server/data/icon//346/216/242/347/264/242.png +0 -0
  110. nonebot_plugin_l4d2_server/data/icon//346/216/250/351/200/201.png +0 -0
  111. nonebot_plugin_l4d2_server/data/icon//346/224/266/351/233/206.png +0 -0
  112. nonebot_plugin_l4d2_server/data/icon//346/224/273/347/225/245.png +0 -0
  113. nonebot_plugin_l4d2_server/data/icon//346/233/264/346/226/260.png +0 -0
  114. nonebot_plugin_l4d2_server/data/icon//346/235/220/346/226/231.png +0 -0
  115. nonebot_plugin_l4d2_server/data/icon//346/237/245/350/257/242.png +0 -0
  116. nonebot_plugin_l4d2_server/data/icon//346/240/241/351/252/214.png +0 -0
  117. nonebot_plugin_l4d2_server/data/icon//346/257/217/346/234/210.png +0 -0
  118. nonebot_plugin_l4d2_server/data/icon//346/267/261/346/270/212.png +0 -0
  119. nonebot_plugin_l4d2_server/data/icon//346/267/273/345/212/240.png +0 -0
  120. nonebot_plugin_l4d2_server/data/icon//346/270/205/351/231/244.png +0 -0
  121. nonebot_plugin_l4d2_server/data/icon//347/212/266/346/200/201.png +0 -0
  122. nonebot_plugin_l4d2_server/data/icon//347/255/276/345/210/260.png +0 -0
  123. nonebot_plugin_l4d2_server/data/icon//347/273/221/345/256/232.png +0 -0
  124. nonebot_plugin_l4d2_server/data/icon//350/241/250.png +0 -0
  125. nonebot_plugin_l4d2_server/data/icon//350/241/250/346/203/205.png +0 -0
  126. nonebot_plugin_l4d2_server/data/icon//350/247/222/350/211/262.png +0 -0
  127. nonebot_plugin_l4d2_server/data/icon//350/256/260/345/275/225.png +0 -0
  128. nonebot_plugin_l4d2_server/data/icon//351/205/215/347/275/256.png +0 -0
  129. nonebot_plugin_l4d2_server/data/icon//351/207/215/345/220/257.png +0 -0
  130. nonebot_plugin_l4d2_server/data/img/l4d2.png +0 -0
  131. nonebot_plugin_l4d2_server/data/img/linux.png +0 -0
  132. nonebot_plugin_l4d2_server/data/img/white.png +0 -0
  133. nonebot_plugin_l4d2_server/l4_image/img/template//345/276/256/350/275/257/351/233/205/351/273/221.ttf +0 -0
  134. nonebot_plugin_l4d2_server-1.0.0a1.dist-info/RECORD +0 -144
  135. {nonebot_plugin_l4d2_server-1.0.0a1.dist-info → nonebot_plugin_l4d2_server-1.0.0a2.dist-info}/WHEEL +0 -0
  136. {nonebot_plugin_l4d2_server-1.0.0a1.dist-info → nonebot_plugin_l4d2_server-1.0.0a2.dist-info}/licenses/LICENSE +0 -0
@@ -1,14 +1,28 @@
1
- import json as js
1
+ import asyncio
2
+ import contextlib
3
+ import socket
2
4
  from copy import deepcopy
3
- from typing import Any, Dict, List, Literal, Optional, Union
5
+ from typing import Any, Dict, List, Literal, Optional, Tuple, cast
4
6
 
5
7
  import a2s
8
+ import ujson as js
9
+ from bs4 import BeautifulSoup
6
10
  from httpx import AsyncClient
7
- from lxml import etree
8
11
 
12
+ # from nonebot.log import logger
9
13
  from ..utils import split_maohao
10
- from .api import anne_ban
11
- from .models import SourceBansInfo
14
+ from .api import AnnePlayerApi, AnneSearchApi, anne_ban
15
+ from .models import (
16
+ AnnePlayer2,
17
+ AnnePlayerDetail,
18
+ AnnePlayerError,
19
+ AnnePlayerInf,
20
+ AnnePlayerInfAvg,
21
+ AnnePlayerInfo,
22
+ AnnePlayerSur,
23
+ AnneSearch,
24
+ SourceBansInfo,
25
+ )
12
26
 
13
27
 
14
28
  class L4D2Api:
@@ -18,23 +32,75 @@ class L4D2Api:
18
32
  "(KHTML, like Gecko)"
19
33
  "Chrome/126.0.0.0"
20
34
  "Safari/537.36 Edg/126.0.0.0",
35
+ "Content-Type": "application/x-www-form-urlencoded",
21
36
  }
22
37
 
23
38
  async def a2s_info(
24
39
  self,
25
- host: str,
26
- port: int,
27
- ) -> a2s.SourceInfo:
28
- msg: a2s.SourceInfo = await a2s.ainfo((host, port))
29
- return msg
40
+ ip_list: List[Tuple[str, int]],
41
+ is_server: bool = True,
42
+ is_player: bool = False,
43
+ ) -> List[Tuple[a2s.SourceInfo, List[a2s.Player]]]:
44
+ msg_list: List[Tuple[a2s.SourceInfo, List[a2s.Player]]] = []
45
+ sorted_msg_list = []
46
+ tasks = [] # 用来保存异步任务
47
+ if ip_list != []:
48
+ for index, i in enumerate(ip_list):
49
+ try:
50
+ tasks.append(
51
+ asyncio.create_task(
52
+ self.process_message(
53
+ i,
54
+ index,
55
+ is_server,
56
+ is_player,
57
+ ),
58
+ ),
59
+ )
60
+ except ValueError:
61
+ continue # 处理异常情况
62
+
63
+ msg_list = await asyncio.gather(*tasks)
64
+ sorted_msg_list = sorted(msg_list, key=lambda x: x[0].steam_id)
65
+
66
+ return sorted_msg_list
30
67
 
31
- async def a2s_players(
68
+ async def process_message(
32
69
  self,
33
- host: str,
34
- port: int,
35
- ) -> List[a2s.Player]:
36
- msg: List[a2s.Player] = await a2s.aplayers((host, port))
37
- return msg
70
+ ip: Tuple[str, int],
71
+ index: int,
72
+ is_server: bool,
73
+ is_player: bool,
74
+ ):
75
+ server: a2s.SourceInfo = a2s.SourceInfo()
76
+ play: List[a2s.Player] = []
77
+ if is_server:
78
+ try:
79
+ server = await a2s.ainfo(ip)
80
+ if server is not None:
81
+ server.steam_id = index
82
+
83
+ except (
84
+ asyncio.exceptions.TimeoutError,
85
+ ConnectionRefusedError,
86
+ socket.gaierror,
87
+ ):
88
+ server.steam_id = index
89
+ server.player_count = 0
90
+ server.max_players = 0
91
+ server.server_name = "服务器无响应"
92
+ server.map_name = "无"
93
+ server.folder = "m"
94
+ server.vac_enabled = False
95
+
96
+ if is_player:
97
+ with contextlib.suppress(
98
+ asyncio.exceptions.TimeoutError,
99
+ ConnectionRefusedError,
100
+ socket.gaierror,
101
+ ):
102
+ play = await a2s.aplayers(ip)
103
+ return server, play
38
104
 
39
105
  async def _server_request(
40
106
  self,
@@ -45,7 +111,7 @@ class L4D2Api:
45
111
  json: Optional[Dict[str, Any]] = None,
46
112
  data: Optional[Dict[str, Any]] = None,
47
113
  is_json: bool = True,
48
- ) -> Union[Dict, int]:
114
+ ):
49
115
  header = deepcopy(self._HEADER)
50
116
 
51
117
  if json is not None:
@@ -85,35 +151,187 @@ class L4D2Api:
85
151
  ):
86
152
  return raw_data["result"]["error_code"]
87
153
  return raw_data
88
- html_content = resp.text
89
- return etree.HTML(html_content)
154
+ html_content = resp.content
155
+ return BeautifulSoup(html_content, "lxml")
90
156
 
91
- async def get_sourceban(self, name: str, url: str = anne_ban):
92
- tree = await self._server_request(
157
+ async def get_sourceban(self, url: str = anne_ban):
158
+ """从sourceban++获取服务器列表,目前未做名称处理"""
159
+ soup = await self._server_request(
93
160
  url=url,
94
161
  is_json=False,
95
- ) # type: ignore
96
- name = name
97
- # 检查响应状态码
162
+ )
98
163
 
99
- target_element = tree.xpath(
100
- "/html/body/main/div[3]/div[5]/div/div/table/tbody/tr",
164
+ if not isinstance(soup, BeautifulSoup):
165
+ return []
166
+ server_list = []
167
+ tbody = soup.select_one("tbody")
168
+ if tbody is None:
169
+ return []
170
+ tr_tags = tbody.select("tr")
171
+ for index, tr in enumerate(tr_tags):
172
+ td_tags = tr.select("td")
173
+ for num, td in enumerate(td_tags):
174
+ if num == 4:
175
+ host, port = split_maohao(td.text)
176
+ server_list.append(
177
+ SourceBansInfo(index=index, host=host, port=port),
178
+ )
179
+
180
+ return server_list
181
+
182
+ async def get_anne_steamid(self, name: str):
183
+ """从电信anne服搜索昵称获取steamid"""
184
+ soup = await self._server_request(
185
+ url=AnneSearchApi,
186
+ data={"search": name},
187
+ method="POST",
188
+ is_json=False,
101
189
  )
190
+ if not isinstance(soup, BeautifulSoup):
191
+ return None
102
192
  server_list = []
103
- # for tr in target_element:
104
- for tr in target_element:
105
- if tr.get("class") != "collapse":
193
+ tbody = soup.select_one("tbody")
194
+ if tbody is None:
195
+ return None
196
+ tr_tags = tbody.select("tr")
197
+ for tr in tr_tags:
198
+ onclick = tr.get("onclick")
199
+ if onclick is None or isinstance(onclick, list):
106
200
  continue
107
- index = 0
108
- for td in tr.xpath("./td"):
109
- if td.get("id") is not None or td.text == "\n":
110
- continue
111
- index += 1
112
- host, port = split_maohao(td.text)
113
- server_list.append(SourceBansInfo(index=index, host=host, port=port))
114
-
115
- # 通过一次请求,确定服务器的序号
116
- return server_list
201
+ steamid = onclick.split("steamid=")[1].replace("'", "")
202
+ td_tags = tr.select("td")
203
+ server_list.append(
204
+ {
205
+ "steamid": steamid,
206
+ "rank": td_tags[0].text.strip(),
207
+ "name": td_tags[1].text.strip(),
208
+ "score": td_tags[2].text.strip(),
209
+ "play_time": td_tags[3].text.strip(),
210
+ "last_time": td_tags,
211
+ },
212
+ )
213
+ print(server_list)
214
+ return cast(List[AnneSearch], server_list)
215
+
216
+ async def get_anne_playerdetail(self, steamid: str):
217
+ """从电信anne服通过steamid获取战绩"""
218
+ soup = await self._server_request(
219
+ url=AnnePlayerApi,
220
+ method="GET",
221
+ params={"steamid": steamid},
222
+ is_json=False,
223
+ )
224
+ if not isinstance(soup, BeautifulSoup):
225
+ return None
226
+
227
+ tbody = soup.find(
228
+ "div",
229
+ class_="content text-center text-md-left",
230
+ style="background-color: #f2f2f2;",
231
+ )
232
+ if tbody is None:
233
+ return None
234
+ kill_tag = tbody.find(
235
+ "div",
236
+ class_="card-body worldmap d-flex flex-column justify-content-center text-center",
237
+ )
238
+
239
+ tbody_tags = tbody.find_all(
240
+ "table",
241
+ class_="table content-table-noborder text-left",
242
+ )
243
+ print(len(tbody_tags))
244
+ info_tag = tbody_tags[0]
245
+ detail_tag = tbody_tags[1]
246
+ error_tag = tbody_tags[2]
247
+ inf_avg_tag = tbody_tags[3]
248
+ sur_tag = tbody_tags[4]
249
+ inf_tag = tbody_tags[5]
250
+
251
+ info_tr = info_tag.select("tr")
252
+ info_dict = {
253
+ "name": info_tr[0].select("td")[1].text.strip(),
254
+ "avatar": info_tr[1].select("td")[1].text.strip(),
255
+ "steamid": info_tr[2].select("td")[1].text.strip(),
256
+ "playtime": info_tr[3].select("td")[1].text.strip(),
257
+ "lasttime": info_tr[4].select("td")[1].text.strip(),
258
+ }
259
+ detail_tag = {
260
+ "rank": detail_tag.select("tr")[0].select("td")[1].text.strip(),
261
+ "source": detail_tag.select("tr")[1].select("td")[1].text.strip(),
262
+ "avg_source": detail_tag.select("tr")[2].select("td")[1].text.strip(),
263
+ "kills": detail_tag.select("tr")[3].select("td")[1].text.strip(),
264
+ "kills_people": detail_tag.select("tr")[4].select("td")[1].text.strip(),
265
+ "headshots": detail_tag.select("tr")[5].select("td")[1].text.strip(),
266
+ "avg_headshots": detail_tag.select("tr")[6].select("td")[1].text.strip(),
267
+ "map_play": detail_tag.select("tr")[7].select("td")[1].text.strip(),
268
+ }
269
+ error_tag = {
270
+ "mistake_shout": error_tag.select("tr")[0].select("td")[1].text.strip(),
271
+ "kill_friend": error_tag.select("tr")[1].select("td")[1].text.strip(),
272
+ "down_friend": error_tag.select("tr")[2].select("td")[1].text.strip(),
273
+ "abandon_friend": error_tag.select("tr")[3].select("td")[1].text.strip(),
274
+ "put_into": error_tag.select("tr")[4].select("td")[1].text.strip(),
275
+ "agitate_witch": error_tag.select("tr")[5].select("td")[1].text.strip(),
276
+ }
277
+ inf_avg_dict = {
278
+ "avg_smoker": inf_avg_tag.select("tr")[0].select("td")[1].text.strip(),
279
+ "avg_boomer": inf_avg_tag.select("tr")[1].select("td")[1].text.strip(),
280
+ "avg_hunter": inf_avg_tag.select("tr")[2].select("td")[1].text.strip(),
281
+ "avg_charger": inf_avg_tag.select("tr")[3].select("td")[1].text.strip(),
282
+ "avg_spitter": inf_avg_tag.select("tr")[4].select("td")[1].text.strip(),
283
+ "avg_jockey": inf_avg_tag.select("tr")[5].select("td")[1].text.strip(),
284
+ "avg_tank": inf_avg_tag.select("tr")[6].select("td")[1].text.strip(),
285
+ }
286
+ sur_dict = {
287
+ "map_clear": sur_tag.select("tr")[0].select("td")[1].text.strip(),
288
+ "prefect_into": sur_tag.select("tr")[1].select("td")[1].text.strip(),
289
+ "get_oil": sur_tag.select("tr")[2].select("td")[1].text.strip(),
290
+ "ammo_arrange": sur_tag.select("tr")[3].select("td")[1].text.strip(),
291
+ "adrenaline_give": sur_tag.select("tr")[4].select("td")[1].text.strip(),
292
+ "pills_give": sur_tag.select("tr")[5].select("td")[1].text.strip(),
293
+ "first_aid_give": sur_tag.select("tr")[6].select("td")[1].text.strip(),
294
+ "friend_up": sur_tag.select("tr")[7].select("td")[1].text.strip(),
295
+ "diss_friend": sur_tag.select("tr")[8].select("td")[1].text.strip(),
296
+ "save_friend": sur_tag.select("tr")[9].select("td")[1].text.strip(),
297
+ "protect_friend": sur_tag.select("tr")[10].select("td")[1].text.strip(),
298
+ "pro_from_smoker": sur_tag.select("tr")[11].select("td")[1].text.strip(),
299
+ "pro_from_hunter": sur_tag.select("tr")[12].select("td")[1].text.strip(),
300
+ "pro_from_charger": sur_tag.select("tr")[13].select("td")[1].text.strip(),
301
+ "pro_from_jockey": sur_tag.select("tr")[14].select("td")[1].text.strip(),
302
+ "melee_charge": sur_tag.select("tr")[15].select("td")[1].text.strip(),
303
+ "tank_kill": sur_tag.select("tr")[16].select("td")[1].text.strip(),
304
+ "witch_instantly_kill": sur_tag.select("tr")[17]
305
+ .select("td")[1]
306
+ .text.strip(),
307
+ }
308
+ inf_dict = {
309
+ "sur_ace": inf_tag.select("tr")[0].select("td")[1].text.strip(),
310
+ "sur_down": inf_tag.select("tr")[1].select("td")[1].text.strip(),
311
+ "boommer_hit": inf_tag.select("tr")[2].select("td")[1].text.strip(),
312
+ "hunter_prefect": inf_tag.select("tr")[3].select("td")[1].text.strip(),
313
+ "hunter_success": inf_tag.select("tr")[4].select("td")[1].text.strip(),
314
+ "tank_damage": inf_tag.select("tr")[5].select("td")[1].text.strip(),
315
+ "charger_multiple": inf_tag.select("tr")[6].select("td")[1].text.strip(),
316
+ }
317
+ info_dict = cast(AnnePlayerInfo, info_dict)
318
+ detail_dict = cast(AnnePlayerDetail, detail_tag)
319
+ error_dict = cast(AnnePlayerError, error_tag)
320
+ inf_avg_dict = cast(AnnePlayerInfAvg, inf_avg_dict)
321
+ sur_dict = cast(AnnePlayerSur, sur_dict)
322
+ inf_dict = cast(AnnePlayerInf, inf_dict)
323
+
324
+ out_dict = {
325
+ "kill_msg": kill_tag.text if kill_tag is not None else "",
326
+ "info": info_dict,
327
+ "detail": detail_dict,
328
+ "inf_avg": inf_avg_dict,
329
+ "sur": sur_dict,
330
+ "inf": inf_dict,
331
+ "error": error_dict,
332
+ }
333
+
334
+ return cast(AnnePlayer2, out_dict)
117
335
 
118
336
 
119
337
  L4API = L4D2Api()
@@ -1,29 +1,18 @@
1
- from pathlib import Path
1
+ from nonebot_plugin_tortoise_orm import add_model
2
+ from tortoise import fields
3
+ from tortoise.models import Model
2
4
 
3
- from nonebot import on_command
4
- from nonebot_plugin_datastore import get_plugin_data
5
- from sqlalchemy.orm import Mapped, mapped_column
5
+ add_model(__name__)
6
6
 
7
- plugin_data = get_plugin_data()
8
7
 
9
- # 定义模型
10
- DATA = get_plugin_data()
11
- DATA.set_migration_dir(Path("data/L4D2/") / "sql")
12
-
13
-
14
- class SteamUser(DATA.Model):
8
+ class SteamUser(Model):
15
9
  """个人资料"""
16
10
 
17
- SteamID: Mapped[str] = mapped_column(primary_key=True)
18
- SteamID64: Mapped[str]
19
- Name: Mapped[str]
20
-
21
-
22
- matcher = on_command("test")
11
+ userid = fields.BigIntField(pk=True)
12
+ SteamID = fields.TextField(null=True)
13
+ SteamID64 = fields.TextField(null=True)
14
+ Name = fields.TextField(null=True)
23
15
 
24
- # 数据库相关操作
25
- # @matcher.handle()
26
- # async def handle(session: AsyncSession = Depends(get_session)):
27
- # example = SteamUser(message="matcher")
28
- # session.add(example)
29
- # await session.commit()
16
+ class Meta: # type: ignore
17
+ table = "steam_user"
18
+ table_description = "个人资料"
@@ -5,6 +5,7 @@ from pathlib import Path
5
5
  from typing import Any, Dict, List, Optional, Tuple
6
6
 
7
7
  import aiofiles
8
+ import aiohttp
8
9
  from nonebot.adapters.onebot.v11 import Bot, GroupMessageEvent, MessageEvent
9
10
  from nonebot.log import logger
10
11
 
@@ -37,7 +38,7 @@ def get_vpk(map_path: Path, file_: str = ".vpk") -> List[str]:
37
38
  def mes_list(mes: str, name_list: List[str]) -> str:
38
39
  if name_list:
39
40
  for idx, name in enumerate(name_list):
40
- mes += f"\n{idx+1}、{name}"
41
+ mes += f"\n{idx + 1}、{name}"
41
42
  return mes
42
43
 
43
44
 
@@ -72,16 +73,11 @@ def solve(msg: str):
72
73
  return "\n".join(lines)
73
74
 
74
75
 
75
- async def get_message_at(datas: str) -> List[int]:
76
- data: Dict[str, Any] = json.loads(datas)
77
- return [int(msg["data"]["qq"]) for msg in data["message"] if msg["type"] == "at"]
78
-
79
-
80
76
  def at_to_usrid(at: List[int]):
81
77
  return at[0] if at else None
82
78
 
83
79
 
84
- async def save_file(file: bytes, path_name):
80
+ async def save_file(file: bytes, path_name: str):
85
81
  """保存文件"""
86
82
  async with aiofiles.open(path_name, "wb") as files:
87
83
  await files.write(file)
@@ -149,7 +145,7 @@ def register_menu_func(
149
145
 
150
146
 
151
147
  def register_menu(*args, **kwargs):
152
- def decorator(f):
148
+ def decorator(f): # noqa: ANN001
153
149
  register_menu_func(*args, **kwargs)
154
150
  return f
155
151
 
@@ -177,8 +173,6 @@ def split_maohao(msg: str) -> Tuple[str, int]:
177
173
  return "", -1
178
174
 
179
175
 
180
- import aiohttp
181
-
182
176
  headers = {
183
177
  "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:107.0) Gecko/20100101 Firefox/107.0", # noqa: E501
184
178
  }
@@ -202,3 +196,9 @@ async def url_to_msg(url: str):
202
196
  if response.status == 200:
203
197
  return await response.text()
204
198
  return None
199
+
200
+
201
+ async def get_message_at(datas: str) -> Optional[int]: # noqa: F811
202
+ data: Dict[str, Any] = json.loads(datas)
203
+ at_list = [int(msg["data"]["qq"]) for msg in data["message"] if msg["type"] == "at"]
204
+ return at_list[0] if at_list else None
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: nonebot-plugin-l4d2-server
3
- Version: 1.0.0a1
3
+ Version: 1.0.0a2
4
4
  Summary: L4D2 server related operations plugin for NoneBot2
5
5
  Keywords: steam,game,l4d2,nonebot2,plugin
6
6
  Home-page: https://github.com/Agnes4m/nonebot_plugin_l4d2_server
@@ -19,12 +19,19 @@ Requires-Dist: nonebot2>=2.0.0
19
19
  Requires-Dist: nonebot-plugin-htmlrender>=0.3.0
20
20
  Requires-Dist: nonebot-adapter-onebot>=2.4.4
21
21
  Requires-Dist: nonebot-plugin-alconna>=0.50.0
22
+ Requires-Dist: nonebot_plugin_datastore>=1.3.0
23
+ Requires-Dist: nonebot-plugin-tortoise-orm>=0.1.4
22
24
  Requires-Dist: aiohttp>=3.8.4
23
25
  Requires-Dist: jinja2>=3.0.0
24
26
  Requires-Dist: srctools>=2.3.9
25
- Requires-Dist: bs4==0.0.1
26
- Requires-Dist: httpx>=0.22.0
27
+ Requires-Dist: httpx<0.24.1,>=0.22.0
28
+ Requires-Dist: msgspec>=0.18.0
27
29
  Requires-Dist: python-a2s>=1.3.0
30
+ Requires-Dist: ujson>=5.10.0
31
+ Requires-Dist: lxml>=5.2.2
32
+ Requires-Dist: rcon>=2.1.0
33
+ Requires-Dist: pillow>9
34
+ Requires-Dist: beautifulsoup4>=4.12.3
28
35
  Description-Content-Type: text/markdown
29
36
 
30
37
  <!-- markdownlint-disable MD026 MD031 MD033 MD036 MD041 MD046 MD051 -->
@@ -137,28 +144,29 @@ conda install nonebot-plugin-l4d2-server
137
144
 
138
145
  ## [数据结构](./docs/standand.md)
139
146
 
147
+ 暂未更新
148
+
140
149
  ## env设置
141
150
 
142
151
  """bash
143
- l4_anne: bool = False
152
+ l4_anne = False
144
153
  """是否启用anne电信服相关功能"""
145
- l4_enable: bool = True
154
+ l4_enable = True
146
155
  """是否全局启用求生功能"""
147
- l4_image: bool = False
156
+ l4_image = False
148
157
  """是否启用图片"""
149
- l4_connect: bool = True
158
+ l4_connect = True
150
159
  """是否在查服命令后加入connect ip"""
151
- l4_path: str = "data/L4D2"
160
+ l4_path = "data/L4D2"
152
161
  """插件数据路径"""
153
- l4_players: int = 4
162
+ l4_players = 4
154
163
  """查询总图的时候展示的用户数量"""
155
- l4_style: str = "default"
164
+ l4_style = "default"
156
165
  """图片风格,可选包括以下,默认简洁
157
166
  - 暗风格
158
167
  - 孤独摇滚
159
168
  - 电玩像素
160
169
  - 缤纷彩虹
161
- - 求生之路
162
170
  """
163
171
 
164
172
  ## 其他
@@ -0,0 +1,96 @@
1
+ nonebot_plugin_l4d2_server-1.0.0a2.dist-info/METADATA,sha256=XN33zbiVUs_p1FDQoUQroNZqyKfkj5F2dF1VdHYsr3c,6584
2
+ nonebot_plugin_l4d2_server-1.0.0a2.dist-info/WHEEL,sha256=rSwsxJWe3vzyR5HCwjWXQruDgschpei4h_giTm0dJVE,90
3
+ nonebot_plugin_l4d2_server-1.0.0a2.dist-info/licenses/LICENSE,sha256=OXLcl0T2SZ8Pmy2_dmlvKuetivmyPd5m1q-Gyd-zaYY,35149
4
+ nonebot_plugin_l4d2_server/__init__.py,sha256=PIufOk1bxOx-nYqdoinoB7BcntIETNFwfzqKnmu-teE,1624
5
+ nonebot_plugin_l4d2_server/__main__.py,sha256=AY5CWuPMcpD7aC1OyT3bqCpjq7lZuvpkNtLtjNrtKKU,4232
6
+ nonebot_plugin_l4d2_server/config.py,sha256=zPwEZoDYyzOCKnS6XE3JxBRw7LZazLE8_hSy-rntzfM,978
7
+ nonebot_plugin_l4d2_server/data/font/loli.ttf,sha256=Yrh-RPoCrn1-NG94DR0x20ASXYUt8g3Ep6BCt3CdOFk,11125812
8
+ nonebot_plugin_l4d2_server/l4_anne/__init__.py,sha256=lfTSVNO3tWvlnwLXTUVeOWI6JcDEdgTUnb0oDduzmnA,4119
9
+ nonebot_plugin_l4d2_server/l4_anne/ranne.py,sha256=vtNQJ-74rJiwVI3IYS3ZgFk_LaCviKU1yxrGk3DFvQs,532
10
+ nonebot_plugin_l4d2_server/l4_help/Help.json,sha256=cT57SgJhFeunZoNMUwoJyqWzVaAYP_Er1-fw8gTyImk,2455
11
+ nonebot_plugin_l4d2_server/l4_help/__init__.py,sha256=2d7Tcncf2FBMfj1s8rWvhNEQNTnFoQSj75wurefQOtk,1537
12
+ nonebot_plugin_l4d2_server/l4_help/draw.py,sha256=y6yDPUnoZFvwly8cf7g9HRpT1JXTxyA9DC1TuvUinTM,6448
13
+ nonebot_plugin_l4d2_server/l4_help/icon/介绍.png,sha256=67JXA7JZjVNo5FoPF_mKlRq30uzc30b7DxDasteiMOA,3179
14
+ nonebot_plugin_l4d2_server/l4_help/icon/任务.png,sha256=FWvlRKgxUO6yypKSC0ROXy3JcrM3hzUPNMTibiJlYD8,3155
15
+ nonebot_plugin_l4d2_server/l4_help/icon/信息.png,sha256=ZQJU-u4a4r-yrYmHbM-b9oi44xB-KEscx0ohlZiTobY,3502
16
+ nonebot_plugin_l4d2_server/l4_help/icon/公告.png,sha256=TQLVFTD4Wi2Zsya6p27SIxDwlnCNUv8hLTnwHTlNpns,3100
17
+ nonebot_plugin_l4d2_server/l4_help/icon/刀剑.png,sha256=qD9x7bXLe5YqCXRK580iehXAgON52-uPDSoE15BNzkg,3378
18
+ nonebot_plugin_l4d2_server/l4_help/icon/切换.png,sha256=1o1a4nkBvu1VeJ1wcPmYys3RLit1LhzZi6hzmzJWzik,3293
19
+ nonebot_plugin_l4d2_server/l4_help/icon/删除.png,sha256=numLbz8zbKj8MKJhYOLbvO77lKVp9Aj9scH0Agrdmkg,3146
20
+ nonebot_plugin_l4d2_server/l4_help/icon/刷新.png,sha256=H2C2tWo9I2HxzYf0Atiw9R6F3W2RchOuF5A_SPHER9M,3278
21
+ nonebot_plugin_l4d2_server/l4_help/icon/卡组.png,sha256=Cju_SBdoLSZrKLrutsmQ9ViYssC8Ol95_YQ34n1OFio,3864
22
+ nonebot_plugin_l4d2_server/l4_help/icon/哪里.png,sha256=BFxEBhnNRrDsL9C-yN8TM_Khgs3hu6n6SNDeMca9Fwc,3296
23
+ nonebot_plugin_l4d2_server/l4_help/icon/地图.png,sha256=oN-IA4rn6Uy91mnG6-Z5sbzmCz3VpL4gCn-lp0cCwNI,3296
24
+ nonebot_plugin_l4d2_server/l4_help/icon/导入.png,sha256=s0oOG1eB-9QX1nktkcZfDp7MTdKzI80nLLBkm1_JB4w,2966
25
+ nonebot_plugin_l4d2_server/l4_help/icon/导出.png,sha256=ZpRGubMwxmhkPlWRsFkN6t0KlaqbeL3q_pHTgVS-xPU,3047
26
+ nonebot_plugin_l4d2_server/l4_help/icon/影.png,sha256=dMeiCD6AzhIdP1kayyTS6rKgwOy3pdhuNb3OGWfNzfc,3024
27
+ nonebot_plugin_l4d2_server/l4_help/icon/拼图.png,sha256=D8iGE0quwvQ6TFzgTi9sWS3MiEj64y5le2gFlOIaskA,3320
28
+ nonebot_plugin_l4d2_server/l4_help/icon/探索.png,sha256=p5JJti50I1c9NAZwDkumIKCLeHBrIb70tdTMWjU7w34,3791
29
+ nonebot_plugin_l4d2_server/l4_help/icon/推送.png,sha256=Ps9J2qEWcFKGki7_eVno_kHzcewXNvLglUf6_alkMRw,3172
30
+ nonebot_plugin_l4d2_server/l4_help/icon/收集.png,sha256=MPRZ2cI0F7_6ezBYddIx1J7Zf1Ljbfu9M0DPXi-g_Wo,3522
31
+ nonebot_plugin_l4d2_server/l4_help/icon/攻略.png,sha256=Pk-hnGW2gpPzmvANLiWYkeOK3B-bAFjqq62VwraVTtc,3722
32
+ nonebot_plugin_l4d2_server/l4_help/icon/更新.png,sha256=gfVGEO1fdg5QdHV-w5XF4TWNCsxCQNU2M8yBVDqbt1M,3285
33
+ nonebot_plugin_l4d2_server/l4_help/icon/材料.png,sha256=FEcU_jbJhPhNNNMu1rJ3nV-Rvjfn9EhihGXVesG1a8I,3351
34
+ nonebot_plugin_l4d2_server/l4_help/icon/查询.png,sha256=T4Wq6MTc5qf1B6UpEmQH7s4cL09kaQ0OyK5Bv5KdfXM,3242
35
+ nonebot_plugin_l4d2_server/l4_help/icon/校验.png,sha256=wHvYcXd8L7ZdgNbH-4BVZiltwF60eVXfORETVBp6cE0,3472
36
+ nonebot_plugin_l4d2_server/l4_help/icon/每月.png,sha256=jDNeSJQ7NWqbwGd4k4H7E8gVw2Ok3473zm-zSzrovwM,3170
37
+ nonebot_plugin_l4d2_server/l4_help/icon/深渊.png,sha256=X0Q5yU_FPYfTGQvf-A26UiPWxRdwuotZnWnXWVeqbyI,3407
38
+ nonebot_plugin_l4d2_server/l4_help/icon/添加.png,sha256=ceW1U5LWji5Mc4Lr6oHaTy6Q6bQeToYeEo3nIEXu9mg,3233
39
+ nonebot_plugin_l4d2_server/l4_help/icon/清除.png,sha256=DtMlluPWtQYEZLBPHDyFwWB5ZR01zM9XfdD3beCTJcg,3046
40
+ nonebot_plugin_l4d2_server/l4_help/icon/状态.png,sha256=ztzyrAz98NSnFMpfRc-HHzBsecKDNGit8dhT51glDXA,3163
41
+ nonebot_plugin_l4d2_server/l4_help/icon/签到.png,sha256=d-zp3wphrAVXtxaCpop1R7gjdwCyA4mHjy1w3iW4UiM,3174
42
+ nonebot_plugin_l4d2_server/l4_help/icon/绑定.png,sha256=Nyfb2VHuD9CicsXN4oBlJ20Uvz_RLMtXorjVvmX_35A,3238
43
+ nonebot_plugin_l4d2_server/l4_help/icon/表.png,sha256=8HZCqdfLUc-f-yrz0XAvAFAwsQnszwW7bCY1tf5l7YQ,2939
44
+ nonebot_plugin_l4d2_server/l4_help/icon/表情.png,sha256=ouFr_gRq-bCa1_aGgXqvVhreZa-8NawRThIlekozgcw,3267
45
+ nonebot_plugin_l4d2_server/l4_help/icon/角色.png,sha256=akMfHCei0CI65HMmDhbdD0sLaRLkjFls-ahU4OaPsoQ,3030
46
+ nonebot_plugin_l4d2_server/l4_help/icon/记录.png,sha256=HmIi53yXgvbkjSI8ZTTJW-3HkeJs7vLBw-GCVZIU5XM,2831
47
+ nonebot_plugin_l4d2_server/l4_help/icon/配置.png,sha256=oxqe8WwRUv_Z_d5gie6HaEi8qW-zgV-pFY2N4SocNyw,3588
48
+ nonebot_plugin_l4d2_server/l4_help/icon/重启.png,sha256=51XKc-RBHv3D_kfT3AciyB1Fz-ujF6vX7D-s7SyJ3r4,3392
49
+ nonebot_plugin_l4d2_server/l4_help/texture2d/badge.png,sha256=TJScC5Mt5jKypq8U1UFISlkH8yB4ynvnyoIDn7Luj00,7559
50
+ nonebot_plugin_l4d2_server/l4_help/texture2d/banner.png,sha256=sDwq7DbCORC1vRp8JD1hgQlKrasrfqtxm24zqGUgmGM,31703
51
+ nonebot_plugin_l4d2_server/l4_help/texture2d/bg.jpg,sha256=BE2kEc9y--B7UJtHR5h_Q8rk5yeEiLbtsbMFj9xl8Tg,245400
52
+ nonebot_plugin_l4d2_server/l4_help/texture2d/button.png,sha256=8wOFPbWUFfkGY7CNUx4fV1CaRA30oWz3YUBUtQq-Jpo,12084
53
+ nonebot_plugin_l4d2_server/l4_help/texture2d/icon.png,sha256=hkkkTOv1fjAFbpS3f3bdg6BGReeLmUcMkSwUo9-N32Y,634032
54
+ nonebot_plugin_l4d2_server/l4_image/__init__.py,sha256=-GWXUDv_z_cfJ-wyvx5J3wB9P7ng4NzRHfCq-GZD6XQ,431
55
+ nonebot_plugin_l4d2_server/l4_image/anne_pil.py,sha256=A4eU68zdcHEhDnD0hctPtv27kWCul6rs-dHoWoJHMFY,483
56
+ nonebot_plugin_l4d2_server/l4_image/convert.py,sha256=_mhFnMUFXGzVvseFIdu2R3bFrnZhShhkLOhKL0AYP6I,3879
57
+ nonebot_plugin_l4d2_server/l4_image/download.py,sha256=rospgp7OnOwOCCO4A-hE5LNKBSNcCpEcgHFVjowlLqs,3104
58
+ nonebot_plugin_l4d2_server/l4_image/html_img.py,sha256=TO-9uhahS3D140PlTHN68UvXHVftBflBL6dMmZWVKYY,3391
59
+ nonebot_plugin_l4d2_server/l4_image/image_tools.py,sha256=Km9S10Q_MHNLo6MQUtkhNaVTQKB5PpFFDeUv0TKI5og,14516
60
+ nonebot_plugin_l4d2_server/l4_image/img/anne/anne.html,sha256=8JOUXoWdulhoP2Axy_omuSDafbduKDZ9Y8Rz2VZWTso,1590
61
+ nonebot_plugin_l4d2_server/l4_image/img/anne/back.png,sha256=H8gRdpJy69X-WbuwZ0AhSdPuL0rN61Dfhq4uMjbRdAs,244861
62
+ nonebot_plugin_l4d2_server/l4_image/img/anne/back1.jpg,sha256=kD5tM58b2oZ_BpJa2G4fJhvOJ1LM0O4uGc-zLmcVj6Q,112995
63
+ nonebot_plugin_l4d2_server/l4_image/img/anne/group_ip.html,sha256=0RCWB0q8Wx0NcKdVmGeVr2odaNzODNVCJK0jiQ826U8,7222
64
+ nonebot_plugin_l4d2_server/l4_image/img/anne/ip.html,sha256=hvKDc7ASbuaGxtx5Doavg5qa82K1vGq4bSapjrwrTy8,1611
65
+ nonebot_plugin_l4d2_server/l4_image/img/head/head.png,sha256=8toEieoMkcJE8xD2NaSLOJ5TddWFOCwoI3mpbv4kbp4,159682
66
+ nonebot_plugin_l4d2_server/l4_image/img/header/logo.png,sha256=2Onm6-veRaO11MqpNOuKXnwufhKNKTHm8wlmKJciRZU,632955
67
+ nonebot_plugin_l4d2_server/l4_image/img/header/player1.jpg,sha256=8WBV0N_rADaJwBIniL_oo2PIecdwiuBxwBvQtrXW39I,406679
68
+ nonebot_plugin_l4d2_server/l4_image/img/template/Bocchi_The_Rock.html,sha256=9qriDKJJuTmvtp7T0lQ1Om22aoRzUipViCFq2IcoWWc,8707
69
+ nonebot_plugin_l4d2_server/l4_image/img/template/Bocchi_The_Rock.png,sha256=zFfEePTB5Qx3_8P_m7J-C6A7OEeK4bGmQPFUYtWcocI,455575
70
+ nonebot_plugin_l4d2_server/l4_image/img/template/HYPixel11pxU-2.ttf,sha256=RGJai1Y8AP8toBwIqq2EZyaBmRbRYPUpNu7f2ZWeDuk,2446828
71
+ nonebot_plugin_l4d2_server/l4_image/img/template/Pixel.html,sha256=STw3WKRsMuX94PfcYTk_aRl8RtjTiLKj2ABpQcGKeXA,17756
72
+ nonebot_plugin_l4d2_server/l4_image/img/template/Pixel.png,sha256=ej2z6qmWvxth3wzTOdhxZrAErDhuCfEuY4w8cYLzekk,1274995
73
+ nonebot_plugin_l4d2_server/l4_image/img/template/Rainbow.html,sha256=8YfS0MPp5zsdCQrZIuXM3izF0h2RTwXHs63C5w-1C2c,20656
74
+ nonebot_plugin_l4d2_server/l4_image/img/template/Rainbow.png,sha256=aKKtkWth49FzAxpsDeDtqkrO1HPbGAGqSMqi__4F-CE,314056
75
+ nonebot_plugin_l4d2_server/l4_image/img/template/Tutumianhuatang-Bold-2.ttf,sha256=rX7HSHSCpQ4mJYsGghvm3btXLabxcCEbLF52wKNDNAE,3090420
76
+ nonebot_plugin_l4d2_server/l4_image/img/template/bilibili.svg,sha256=v3u6R-HLoTHVI1qPCNopPWd_WYZ9L2YSqvvB-L6RZY8,1336
77
+ nonebot_plugin_l4d2_server/l4_image/img/template/fingerprint.svg,sha256=qtbdXb-5o62YQU2-LR4S9b7-ddKC1UOpJG4w8xDrytw,2135
78
+ nonebot_plugin_l4d2_server/l4_image/img/template/github.svg,sha256=Ev2CdWEyL4G-_bhZJ9vBZr5MEWjcgSR819mracoXjqc,1175
79
+ nonebot_plugin_l4d2_server/l4_image/img/template/l.svg,sha256=YbahWPd7uau6edcATiWrA8apYyrlKeTejuvRHwXkmLI,5484
80
+ nonebot_plugin_l4d2_server/l4_image/img/template/m.svg,sha256=JKosfpA8Jncw018dWHVzVR8orC48u3mMdzQovWAa91s,2428
81
+ nonebot_plugin_l4d2_server/l4_image/img/template/normal.html,sha256=TbHKy4cV-7rEVuE3dx75P1Pf9YKTIp8KW5JoaJFMenY,6610
82
+ nonebot_plugin_l4d2_server/l4_image/img/template/vac.png,sha256=qCZsUYRcIgnHEWGir0mSOJ0qWhax5oNX200A5NUgDiI,6114
83
+ nonebot_plugin_l4d2_server/l4_image/img/template/vac_white.png,sha256=fjqCsOSxCLZs3OOzEs5gItK3dR1RgcBMH5JC8hY_BGw,5418
84
+ nonebot_plugin_l4d2_server/l4_image/img/template/vue.css,sha256=2sGjCFrR-3tFMB_x7l4K6k40tZ5JVzhWqD759cagYBA,7874
85
+ nonebot_plugin_l4d2_server/l4_image/img/template/w.svg,sha256=LnctC2mVwjdhRMiS9ffrjUX-9KGwqb6OMmpJXvVXl70,486
86
+ nonebot_plugin_l4d2_server/l4_image/model.py,sha256=FGsCvf_BKbRNJUVy6I5BKnArMY-3JEIdqeX2gs93E5o,231
87
+ nonebot_plugin_l4d2_server/l4_image/vtfs.py,sha256=He_7zzEIOip8MXP55TS7aWPbzo6ac0wPf602nN3GWZM,1461
88
+ nonebot_plugin_l4d2_server/l4_request/__init__.py,sha256=WQ4hvUY8Vw3-TlLz2OQylP_crLy_2yNTUaSHa-sLe2c,4710
89
+ nonebot_plugin_l4d2_server/l4_request/draw_msg.py,sha256=yUlCfWj4p4F0Du3gyhyGdL64DuFBTQ_pBuLPm7JEy2o,2490
90
+ nonebot_plugin_l4d2_server/l4_request/utils.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
91
+ nonebot_plugin_l4d2_server/utils/api/api.py,sha256=auvDicCEKwvnm6EJYeCxCtugFby61K-zAmmaRWWEwtM,296
92
+ nonebot_plugin_l4d2_server/utils/api/models.py,sha256=EKAAM5RsFK-hV-a80tc4r35ToNRhnCWVuQ-7imwBjwE,2386
93
+ nonebot_plugin_l4d2_server/utils/api/request.py,sha256=N38sZ5FLrlh939Al8jlLfbvAG5WaGTC9xLKP0YHXjYI,13036
94
+ nonebot_plugin_l4d2_server/utils/database/models.py,sha256=SLdcgwsn39r_ZkcBoqf4MLX1EfpCOjGBwWcR16u9Bqo,454
95
+ nonebot_plugin_l4d2_server/utils/utils.py,sha256=B697gPxEUs5HFojhHlv6ZybB4lujSXKQghqOT2zBlPY,5696
96
+ nonebot_plugin_l4d2_server-1.0.0a2.dist-info/RECORD,,