nonebot-plugin-l4d2-server 1.0.0b1__tar.gz → 1.0.2__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.
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/PKG-INFO +8 -7
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/README.md +2 -3
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/__main__.py +101 -1
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/__init__.py +1 -1
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//344/273/213/347/273/215.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//344/273/273/345/212/241.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//344/277/241/346/201/257.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//345/205/254/345/221/212.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//345/210/200/345/211/221.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//345/210/207/346/215/242.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//345/210/240/351/231/244.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//345/210/267/346/226/260.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//345/215/241/347/273/204.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//345/223/252/351/207/214.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//345/234/260/345/233/276.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//345/257/274/345/205/245.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//345/257/274/345/207/272.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//345/275/261.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//346/213/274/345/233/276.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//346/216/242/347/264/242.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//346/216/250/351/200/201.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//346/224/266/351/233/206.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//346/224/273/347/225/245.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//346/233/264/346/226/260.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//346/235/220/346/226/231.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//346/237/245/350/257/242.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//346/240/241/351/252/214.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//346/257/217/346/234/210.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//346/267/261/346/270/212.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//346/267/273/345/212/240.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//346/270/205/351/231/244.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//347/212/266/346/200/201.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//347/255/276/345/210/260.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//347/273/221/345/256/232.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//350/241/250.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//350/241/250/346/203/205.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//350/247/222/350/211/262.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//350/256/260/345/275/225.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//351/205/215/347/275/256.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/icon//351/207/215/345/220/257.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/texture2d/badge.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/texture2d/banner.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/texture2d/bg.jpg +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/texture2d/button.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/texture2d/icon.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/anne/back.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/anne/back1.jpg +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/head/head.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/header/logo.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/header/player1.jpg +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/Bocchi_The_Rock.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/Pixel.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/Rainbow.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/vac.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/vac_white.png +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_local/__init__.py +7 -1
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_request/__init__.py +72 -2
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_request/draw_msg.py +7 -2
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/utils/api/request.py +52 -4
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/pyproject.toml +6 -3
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/LICENSE +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/__init__.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/config.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/data/font/loli.ttf +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_anne/__init__.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_anne/ranne.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/Help.json +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_help/draw.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/__init__.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/anne_pil.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/convert.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/download.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/html_img.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/image_tools.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/anne/anne.html +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/anne/group_ip.html +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/anne/ip.html +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/Bocchi_The_Rock.html +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/HYPixel11pxU-2.ttf +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/Pixel.html +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/Rainbow.html +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/Tutumianhuatang-Bold-2.ttf +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/bilibili.svg +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/fingerprint.svg +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/github.svg +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/l.svg +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/m.svg +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/normal.html +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/vue.css +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/img/template/w.svg +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/model.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_image/vtfs.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_local/file.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/l4_request/utils.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/utils/api/api.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/utils/api/models.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/utils/database/models.py +0 -0
- {nonebot_plugin_l4d2_server-1.0.0b1 → nonebot_plugin_l4d2_server-1.0.2}/nonebot_plugin_l4d2_server/utils/utils.py +0 -0
@@ -1,9 +1,8 @@
|
|
1
1
|
Metadata-Version: 2.1
|
2
2
|
Name: nonebot-plugin-l4d2-server
|
3
|
-
Version: 1.0.
|
3
|
+
Version: 1.0.2
|
4
4
|
Summary: L4D2 server related operations plugin for NoneBot2
|
5
5
|
Keywords: steam,game,l4d2,nonebot2,plugin
|
6
|
-
Home-page: https://github.com/Agnes4m/nonebot_plugin_l4d2_server
|
7
6
|
Author-Email: Agnes_Digital <Z735803792@163.com>
|
8
7
|
License: GPLv3
|
9
8
|
Classifier: License :: OSI Approved :: GNU General Public License v3 (GPLv3)
|
@@ -13,7 +12,7 @@ Classifier: Programming Language :: Python :: 3.9
|
|
13
12
|
Classifier: Programming Language :: Python :: 3.10
|
14
13
|
Classifier: Programming Language :: Python :: 3.11
|
15
14
|
Classifier: Operating System :: OS Independent
|
16
|
-
Project-URL:
|
15
|
+
Project-URL: homepage, https://github.com/Agnes4m/nonebot_plugin_l4d2_server
|
17
16
|
Requires-Python: <4.0,>=3.9
|
18
17
|
Requires-Dist: nonebot2>=2.0.0
|
19
18
|
Requires-Dist: nonebot-plugin-htmlrender>=0.3.0
|
@@ -26,12 +25,15 @@ Requires-Dist: jinja2>=3.0.0
|
|
26
25
|
Requires-Dist: srctools>=2.3.9
|
27
26
|
Requires-Dist: httpx<0.24.1,>=0.22.0
|
28
27
|
Requires-Dist: msgspec>=0.18.0
|
29
|
-
Requires-Dist: python-a2s>=1.
|
28
|
+
Requires-Dist: python-a2s>=1.4.1
|
30
29
|
Requires-Dist: ujson>=5.10.0
|
31
30
|
Requires-Dist: lxml>=5.2.2
|
32
31
|
Requires-Dist: rcon>=2.1.0
|
33
32
|
Requires-Dist: pillow>9
|
34
33
|
Requires-Dist: beautifulsoup4>=4.12.3
|
34
|
+
Requires-Dist: rarfile>=4.2
|
35
|
+
Requires-Dist: pyunpack>=0.3
|
36
|
+
Requires-Dist: aiofiles>=24.1.0
|
35
37
|
Description-Content-Type: text/markdown
|
36
38
|
|
37
39
|
<!-- markdownlint-disable MD026 MD031 MD033 MD036 MD041 MD046 MD051 -->
|
@@ -87,7 +89,6 @@ _✨Nonebot & Left 4 Dead 2 server操作✨_
|
|
87
89
|
|
88
90
|
以下提到的方法 任选**其一** 即可
|
89
91
|
|
90
|
-
|
91
92
|
<details open>
|
92
93
|
<summary>[推荐] 使用 nb-cli 安装</summary>
|
93
94
|
在 nonebot2 项目的根目录下打开命令行, 输入以下指令即可安装
|
@@ -164,7 +165,7 @@ conda install nonebot-plugin-l4d2-server
|
|
164
165
|
l4_style = "default"
|
165
166
|
"""图片风格,可选包括以下,默认简洁
|
166
167
|
- 暗风格
|
167
|
-
- 孤独摇滚
|
168
|
+
- 孤独摇滚
|
168
169
|
- 电玩像素
|
169
170
|
- 缤纷彩虹
|
170
171
|
"""
|
@@ -185,7 +186,7 @@ conda install nonebot-plugin-l4d2-server
|
|
185
186
|
- 水果 - html图片优化
|
186
187
|
|
187
188
|
- 感谢以下服主大力支持
|
188
|
-
- Michaela's | 机器人功能测试反馈
|
189
|
+
- Michaela's | 机器人功能测试反馈
|
189
190
|
- 东 | 提供docker部署方法等建议 | [电信服anne游戏群](http://qm.qq.com/cgi-bin/qm/qr?_wv=1027&k=6i7r5aJ7Jyg0ejby4rt9GWmFRF53nV1K&authKey=ekMsWepBZPL26%2BfJAG%2F95JD0fhvH39%2BIGVyKOvNlXVDbpIclJlly4kXqukL7JhWR&noverify=0&group_code=883237206)
|
190
191
|
- 迷茫 | 催命更新byd
|
191
192
|
- ArcPav | 积极反馈bug,提供改进思路
|
@@ -51,7 +51,6 @@ _✨Nonebot & Left 4 Dead 2 server操作✨_
|
|
51
51
|
|
52
52
|
以下提到的方法 任选**其一** 即可
|
53
53
|
|
54
|
-
|
55
54
|
<details open>
|
56
55
|
<summary>[推荐] 使用 nb-cli 安装</summary>
|
57
56
|
在 nonebot2 项目的根目录下打开命令行, 输入以下指令即可安装
|
@@ -128,7 +127,7 @@ conda install nonebot-plugin-l4d2-server
|
|
128
127
|
l4_style = "default"
|
129
128
|
"""图片风格,可选包括以下,默认简洁
|
130
129
|
- 暗风格
|
131
|
-
- 孤独摇滚
|
130
|
+
- 孤独摇滚
|
132
131
|
- 电玩像素
|
133
132
|
- 缤纷彩虹
|
134
133
|
"""
|
@@ -149,7 +148,7 @@ conda install nonebot-plugin-l4d2-server
|
|
149
148
|
- 水果 - html图片优化
|
150
149
|
|
151
150
|
- 感谢以下服主大力支持
|
152
|
-
- Michaela's | 机器人功能测试反馈
|
151
|
+
- Michaela's | 机器人功能测试反馈
|
153
152
|
- 东 | 提供docker部署方法等建议 | [电信服anne游戏群](http://qm.qq.com/cgi-bin/qm/qr?_wv=1027&k=6i7r5aJ7Jyg0ejby4rt9GWmFRF53nV1K&authKey=ekMsWepBZPL26%2BfJAG%2F95JD0fhvH39%2BIGVyKOvNlXVDbpIclJlly4kXqukL7JhWR&noverify=0&group_code=883237206)
|
154
153
|
- 迷茫 | 催命更新byd
|
155
154
|
- ArcPav | 积极反馈bug,提供改进思路
|
@@ -15,8 +15,11 @@
|
|
15
15
|
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
16
16
|
"""
|
17
17
|
|
18
|
+
from pathlib import Path
|
18
19
|
from typing import TYPE_CHECKING, List, Optional
|
19
20
|
|
21
|
+
import aiofiles
|
22
|
+
import ujson as json
|
20
23
|
from nonebot.adapters import Message
|
21
24
|
from nonebot.log import logger
|
22
25
|
from nonebot.matcher import Matcher
|
@@ -33,6 +36,7 @@ from .l4_request import (
|
|
33
36
|
get_ip_server,
|
34
37
|
get_server_detail,
|
35
38
|
reload_ip,
|
39
|
+
tj_request,
|
36
40
|
)
|
37
41
|
from .utils.api.request import L4API
|
38
42
|
|
@@ -48,6 +52,11 @@ l4_all = on_command("l4all", aliases={"l4全服"})
|
|
48
52
|
l4_connect = on_command("connect", aliases={"l4连接"})
|
49
53
|
l4_find_player = on_command("l4find", aliases={"l4查找"})
|
50
54
|
|
55
|
+
ld_tj = on_command("tj", aliases={"探监"})
|
56
|
+
ld_zl = on_command("zl")
|
57
|
+
ld_kl = on_command("kl")
|
58
|
+
config_path = Path(config.l4_path) / "config.json"
|
59
|
+
|
51
60
|
|
52
61
|
@l4_help.handle()
|
53
62
|
async def _(matcher: Matcher):
|
@@ -136,6 +145,97 @@ async def _(args: Message = CommandArg()):
|
|
136
145
|
if not arg:
|
137
146
|
reload_ip()
|
138
147
|
logger.success("重载ip完成")
|
148
|
+
with (Path(config.l4_path) / "config.json").open("r", encoding="utf-8") as f:
|
149
|
+
content = f.read().strip()
|
150
|
+
ip_json = json.loads(content)
|
151
|
+
for tag, url in ip_json.items():
|
152
|
+
logger.info(f"重载{tag}的ip")
|
153
|
+
await L4API.get_sourceban(tag, url)
|
139
154
|
await UniMessage.text("重载ip完成").finish()
|
155
|
+
|
156
|
+
|
157
|
+
l4_add_ban = on_command("l4addban", aliases={"l4添加ban"})
|
158
|
+
|
159
|
+
|
160
|
+
@l4_add_ban.handle()
|
161
|
+
async def _(args: Message = CommandArg()):
|
162
|
+
arg = args.extract_plain_text().strip().split(" ")
|
163
|
+
|
164
|
+
if len(arg) != 2:
|
165
|
+
await UniMessage.text("请在命令后增加响应指令名和网址").finish()
|
166
|
+
|
167
|
+
if not config_path.is_file():
|
168
|
+
config_data = {}
|
140
169
|
else:
|
141
|
-
|
170
|
+
try:
|
171
|
+
with config_path.open("r") as f:
|
172
|
+
config_data = json.load(f)
|
173
|
+
except (json.JSONDecodeError, FileNotFoundError):
|
174
|
+
config_data = {}
|
175
|
+
|
176
|
+
config_data.update({arg[0]: arg[1]})
|
177
|
+
|
178
|
+
try:
|
179
|
+
with config_path.open("w") as f:
|
180
|
+
json.dump(config_data, f, ensure_ascii=False, indent=4)
|
181
|
+
except IOError as e:
|
182
|
+
await UniMessage.text(f"文件写入失败: {e}").finish()
|
183
|
+
|
184
|
+
await L4API.get_sourceban(arg[0], arg[1])
|
185
|
+
await UniMessage.text(f"添加成功\n组名: {arg[0]}\n网址: {arg[1]}").finish()
|
186
|
+
|
187
|
+
|
188
|
+
l4_del_ban = on_command("l4delban", aliases={"l4删除ban", "l4移除ban"})
|
189
|
+
|
190
|
+
|
191
|
+
@l4_del_ban.handle()
|
192
|
+
async def _(args: Message = CommandArg()):
|
193
|
+
arg = args.extract_plain_text().strip().split(" ")
|
194
|
+
if len(arg) not in [1, 2]:
|
195
|
+
await UniMessage.text("请在命令后增加响应指令名或者带响应网址").finish()
|
196
|
+
elif len(arg) == 1:
|
197
|
+
if not Path(Path(config.l4_path) / "config.json").is_file():
|
198
|
+
await UniMessage.text("没有添加过组名").finish()
|
199
|
+
else:
|
200
|
+
with (Path(config.l4_path) / "config.json").open(
|
201
|
+
"r",
|
202
|
+
encoding="utf-8",
|
203
|
+
) as f:
|
204
|
+
content = f.read().strip()
|
205
|
+
config_data = json.loads(content)
|
206
|
+
if arg[0] not in config_data:
|
207
|
+
await UniMessage.text("没有添加过这个组").finish()
|
208
|
+
else:
|
209
|
+
del config_data[arg[0]]
|
210
|
+
async with aiofiles.open(config_path, "w", encoding="utf-8") as f:
|
211
|
+
json.dump(config_data, f, ensure_ascii=False, indent=4)
|
212
|
+
await UniMessage.text(f"删除成功,组名:{arg[0]}").finish()
|
213
|
+
elif len(arg) == 2:
|
214
|
+
if not Path(Path(config.l4_path) / "config.json").is_file():
|
215
|
+
await UniMessage.text("没有添加过组名").finish()
|
216
|
+
else:
|
217
|
+
with (Path(config.l4_path) / "config.json").open(
|
218
|
+
"r",
|
219
|
+
encoding="utf-8",
|
220
|
+
) as f:
|
221
|
+
content = f.read().strip()
|
222
|
+
config_datas = json.loads(content)
|
223
|
+
if arg[0] not in config_datas:
|
224
|
+
await UniMessage.text("没有添加过这个组").finish()
|
225
|
+
else:
|
226
|
+
config_datas[arg[0]] = arg[1]
|
227
|
+
async with aiofiles.open(config_path, "w", encoding="utf-8") as f:
|
228
|
+
json.dump(config_datas, f, ensure_ascii=False, indent=4)
|
229
|
+
await UniMessage.text(f"修改成功,组名:{arg[0]},网址:{arg[1]}").finish()
|
230
|
+
|
231
|
+
|
232
|
+
@ld_tj.handle()
|
233
|
+
async def _(matcher: Matcher):
|
234
|
+
await matcher.send("正在寻找牢房信息")
|
235
|
+
await matcher.finish(await tj_request("云", "tj"))
|
236
|
+
|
237
|
+
|
238
|
+
@ld_zl.handle()
|
239
|
+
async def _(matcher: Matcher):
|
240
|
+
await matcher.send("正在寻找牢房信息")
|
241
|
+
await matcher.finish(await tj_request("云", "zl"))
|
@@ -10,7 +10,7 @@ from ..l4_image.convert import core_font
|
|
10
10
|
from ..l4_image.model import PluginHelp
|
11
11
|
from .draw import get_help
|
12
12
|
|
13
|
-
__version__ = "1.0.
|
13
|
+
__version__ = "1.0.2"
|
14
14
|
TEXT_PATH = Path(__file__).parent / "texture2d"
|
15
15
|
HELP_DATA = Path(__file__).parent / "Help.json"
|
16
16
|
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
@@ -10,7 +10,13 @@ from ..l4_image.convert import text2pic
|
|
10
10
|
from ..utils.utils import mes_list
|
11
11
|
from .file import updown_l4d2_vpk
|
12
12
|
|
13
|
-
|
13
|
+
try:
|
14
|
+
vpk_path = config.l4_local[map_index]
|
15
|
+
except IndexError:
|
16
|
+
logger.warning(
|
17
|
+
"未填写本地服务器路径,如果想要使用本地服务器功能,请填写本地服务器路径",
|
18
|
+
)
|
19
|
+
vpk_path = ""
|
14
20
|
|
15
21
|
local_path_list = config.l4_local
|
16
22
|
if not local_path_list:
|
@@ -1,3 +1,4 @@
|
|
1
|
+
import random
|
1
2
|
from typing import Dict, List, Optional, cast
|
2
3
|
|
3
4
|
from nonebot.log import logger
|
@@ -5,14 +6,16 @@ from nonebot.log import logger
|
|
5
6
|
from ..config import server_all_path
|
6
7
|
from ..l4_image import msg_to_image
|
7
8
|
from ..utils.api.models import AllServer, NserverOut, OutServer
|
9
|
+
from ..utils.api.request import L4API
|
8
10
|
from ..utils.utils import split_maohao
|
9
|
-
from .draw_msg import draw_one_ip, get_much_server
|
11
|
+
from .draw_msg import convert_duration, draw_one_ip, get_much_server
|
10
12
|
|
11
13
|
try:
|
12
14
|
import ujson as json
|
13
15
|
except ImportError:
|
14
16
|
import json
|
15
17
|
|
18
|
+
from ..config import config
|
16
19
|
|
17
20
|
# 获取全部服务器信息
|
18
21
|
ALLHOST: Dict[str, List[NserverOut]] = {}
|
@@ -47,7 +50,10 @@ async def get_all_server_detail():
|
|
47
50
|
# to do作图,先用文字凑合
|
48
51
|
out_msg = ""
|
49
52
|
for one in out_list:
|
50
|
-
|
53
|
+
if one["max_player"]:
|
54
|
+
out_msg += f"{one['command']} | 服务器{one['active_server']}/{one['max_server']} | 玩家{one['active_player']}/{one['max_player']}\n"
|
55
|
+
else:
|
56
|
+
continue
|
51
57
|
return out_msg
|
52
58
|
|
53
59
|
|
@@ -141,3 +147,67 @@ def reload_ip():
|
|
141
147
|
|
142
148
|
if item.name.endswith("txt"):
|
143
149
|
"""to do"""
|
150
|
+
|
151
|
+
|
152
|
+
async def tj_request(command: str = "云", tj="tj"):
|
153
|
+
server_json = ALLHOST.get(command)
|
154
|
+
logger.info(server_json)
|
155
|
+
if server_json is None:
|
156
|
+
logger.warning("未找到这个组")
|
157
|
+
return None
|
158
|
+
# 返回单个
|
159
|
+
logger.info("正在anne电信服务器信息")
|
160
|
+
player_msg = ""
|
161
|
+
right_ip = []
|
162
|
+
for i in server_json:
|
163
|
+
ser_list = await L4API.a2s_info([(i["host"], i["port"])], is_player=True)
|
164
|
+
one_server = ser_list[0][0]
|
165
|
+
one_player = ser_list[0][1]
|
166
|
+
|
167
|
+
# 判断坐牢条件
|
168
|
+
if tj == "tj" and "普通药役" in one_server.map_name:
|
169
|
+
score: int = 0
|
170
|
+
for index, player in enumerate(one_player, 1):
|
171
|
+
if index > 4:
|
172
|
+
break
|
173
|
+
score += player.score
|
174
|
+
|
175
|
+
t = one_server.map_name.split("[")[-1].split("特")[0]
|
176
|
+
if int(t) * 50 < score:
|
177
|
+
right_ip.append(i)
|
178
|
+
if tj == "zl" and "普通药役" in one_server.map_name and len(one_player) <= 4:
|
179
|
+
right_ip.append(i)
|
180
|
+
|
181
|
+
if not right_ip:
|
182
|
+
return "没有符合条件的服务器"
|
183
|
+
|
184
|
+
s = random.choice(right_ip)
|
185
|
+
ser_list = await L4API.a2s_info([(s["host"], s["port"])], is_player=True)
|
186
|
+
one_server = ser_list[0][0]
|
187
|
+
one_player = ser_list[0][1]
|
188
|
+
if len(one_player):
|
189
|
+
max_duration_len = max(
|
190
|
+
[len(str(await convert_duration(i.duration))) for i in one_player],
|
191
|
+
)
|
192
|
+
max_score_len = max(len(str(i.score)) for i in one_player)
|
193
|
+
|
194
|
+
for player in one_player:
|
195
|
+
soc = "[{:>{}}]".format(player.score, max_score_len)
|
196
|
+
chines_dur = await convert_duration(player.duration)
|
197
|
+
dur = "{:^{}}".format(chines_dur, max_duration_len)
|
198
|
+
name = f"{player.name[0]}***{player.name[-1]}"
|
199
|
+
player_msg += f"{soc} | {dur} | {name} \n"
|
200
|
+
else:
|
201
|
+
player_msg = "服务器感觉很安静啊"
|
202
|
+
msg = f"""*{one_server.server_name}*
|
203
|
+
游戏: {one_server.folder}
|
204
|
+
地图: {one_server.map_name}
|
205
|
+
人数: {one_server.player_count}/{one_server.max_players}"""
|
206
|
+
if one_server.ping is not None:
|
207
|
+
msg += f"""
|
208
|
+
ping: {one_server.ping * 1000:.0f}ms
|
209
|
+
{player_msg}"""
|
210
|
+
if config.l4_show_ip:
|
211
|
+
msg += f"""
|
212
|
+
connect {s["host"]}:{s["port"]}"""
|
213
|
+
return msg
|
@@ -29,8 +29,13 @@ async def draw_one_ip(host: str, port: int):
|
|
29
29
|
soc = "[{:>{}}]".format(player.score, max_score_len)
|
30
30
|
chines_dur = await convert_duration(player.duration)
|
31
31
|
dur = "{:^{}}".format(chines_dur, max_duration_len)
|
32
|
-
|
33
|
-
|
32
|
+
name_leg = len(player.name)
|
33
|
+
if name_leg > 2:
|
34
|
+
# xing = "*" * (name_leg - 2)
|
35
|
+
name = f"{player.name[0]}xing{player.name[-1]}"
|
36
|
+
else:
|
37
|
+
name = player.name
|
38
|
+
player_msg += f"{soc} | {dur} | {name} \n"
|
34
39
|
else:
|
35
40
|
player_msg = "服务器感觉很安静啊"
|
36
41
|
|
@@ -2,13 +2,18 @@ import asyncio
|
|
2
2
|
import contextlib
|
3
3
|
import socket
|
4
4
|
from copy import deepcopy
|
5
|
+
from pathlib import Path
|
5
6
|
from typing import Any, Dict, List, Literal, Optional, Tuple, cast
|
6
7
|
|
7
8
|
import a2s
|
9
|
+
import aiofiles
|
8
10
|
import ujson as js
|
11
|
+
import ujson as json
|
9
12
|
from bs4 import BeautifulSoup
|
10
13
|
from httpx import AsyncClient
|
11
14
|
|
15
|
+
from ...config import config
|
16
|
+
|
12
17
|
# from nonebot.log import logger
|
13
18
|
from ..utils import split_maohao
|
14
19
|
from .api import AnnePlayerApi, AnneSearchApi, anne_ban
|
@@ -24,6 +29,8 @@ from .models import (
|
|
24
29
|
SourceBansInfo,
|
25
30
|
)
|
26
31
|
|
32
|
+
config_path = Path(config.l4_path) / "config.json"
|
33
|
+
|
27
34
|
|
28
35
|
class L4D2Api:
|
29
36
|
ssl_verify = False
|
@@ -72,11 +79,11 @@ class L4D2Api:
|
|
72
79
|
is_server: bool,
|
73
80
|
is_player: bool,
|
74
81
|
):
|
75
|
-
server: a2s.SourceInfo = a2s.SourceInfo()
|
76
82
|
play: List[a2s.Player] = []
|
77
83
|
if is_server:
|
78
84
|
try:
|
79
|
-
server = await a2s.ainfo(ip)
|
85
|
+
server: a2s.SourceInfo = await a2s.ainfo(ip, timeout=3, encoding="utf8")
|
86
|
+
|
80
87
|
if server is not None:
|
81
88
|
server.steam_id = index
|
82
89
|
|
@@ -85,6 +92,25 @@ class L4D2Api:
|
|
85
92
|
ConnectionRefusedError,
|
86
93
|
socket.gaierror,
|
87
94
|
):
|
95
|
+
server: a2s.SourceInfo = a2s.SourceInfo(
|
96
|
+
protocol=0,
|
97
|
+
server_name="服务器无响应",
|
98
|
+
map_name="无",
|
99
|
+
folder="m",
|
100
|
+
game="L4D2",
|
101
|
+
app_id=114514,
|
102
|
+
steam_id=index,
|
103
|
+
player_count=0,
|
104
|
+
max_players=0,
|
105
|
+
bot_count=0,
|
106
|
+
server_type="w",
|
107
|
+
platform="w",
|
108
|
+
password_protected=False,
|
109
|
+
vac_enabled=False,
|
110
|
+
version="1.0",
|
111
|
+
edf=0,
|
112
|
+
ping=0,
|
113
|
+
)
|
88
114
|
server.steam_id = index
|
89
115
|
server.player_count = 0
|
90
116
|
server.max_players = 0
|
@@ -99,7 +125,7 @@ class L4D2Api:
|
|
99
125
|
ConnectionRefusedError,
|
100
126
|
socket.gaierror,
|
101
127
|
):
|
102
|
-
play = await a2s.aplayers(ip)
|
128
|
+
play = await a2s.aplayers(ip, timeout=3, encoding="utf8")
|
103
129
|
return server, play
|
104
130
|
|
105
131
|
async def _server_request(
|
@@ -154,8 +180,10 @@ class L4D2Api:
|
|
154
180
|
html_content = resp.content
|
155
181
|
return BeautifulSoup(html_content, "lxml")
|
156
182
|
|
157
|
-
async def get_sourceban(self, url: str = anne_ban):
|
183
|
+
async def get_sourceban(self, tag: str = "云", url: str = anne_ban):
|
158
184
|
"""从sourceban++获取服务器列表,目前未做名称处理"""
|
185
|
+
if not (url.startswith(("http://", "https://"))):
|
186
|
+
url = "http://" + url # 默认添加 http://
|
159
187
|
soup = await self._server_request(
|
160
188
|
url=url,
|
161
189
|
is_json=False,
|
@@ -177,6 +205,26 @@ class L4D2Api:
|
|
177
205
|
SourceBansInfo(index=index, host=host, port=port),
|
178
206
|
)
|
179
207
|
|
208
|
+
if not Path(Path(config.l4_path) / "config.json").is_file():
|
209
|
+
async with aiofiles.open(config_path, "w", encoding="utf-8") as f:
|
210
|
+
await f.write("{}")
|
211
|
+
with (Path(config.l4_path) / "config.json").open("r", encoding="utf-8") as f:
|
212
|
+
content = f.read().strip()
|
213
|
+
ip_json = json.loads(content)
|
214
|
+
if tag in ip_json:
|
215
|
+
url = ip_json[tag]
|
216
|
+
tag_path = Path(Path(config.l4_path) / f"l4d2/{tag}.json")
|
217
|
+
|
218
|
+
async with aiofiles.open(tag_path, "w", encoding="utf-8") as f:
|
219
|
+
print(Path(Path(config.l4_path) / f"l4d2/{tag}.json"))
|
220
|
+
up_data = {}
|
221
|
+
for server in server_list:
|
222
|
+
new_dict = {}
|
223
|
+
new_dict["id"] = int(server.index) + 1
|
224
|
+
new_dict["ip"] = server.host + ":" + str(server.port)
|
225
|
+
up_data.update(new_dict)
|
226
|
+
print(up_data)
|
227
|
+
json.dump(up_data, f, ensure_ascii=False, indent=4)
|
180
228
|
return server_list
|
181
229
|
|
182
230
|
async def get_anne_steamid(self, name: str):
|
@@ -1,6 +1,6 @@
|
|
1
1
|
[project]
|
2
2
|
name = "nonebot-plugin-l4d2-server"
|
3
|
-
version = "1.0.
|
3
|
+
version = "1.0.2"
|
4
4
|
description = "L4D2 server related operations plugin for NoneBot2"
|
5
5
|
authors = [
|
6
6
|
{ name = "Agnes_Digital", email = "Z735803792@163.com" },
|
@@ -25,12 +25,15 @@ dependencies = [
|
|
25
25
|
"srctools>=2.3.9",
|
26
26
|
"httpx>=0.22.0,<0.24.1",
|
27
27
|
"msgspec>=0.18.0",
|
28
|
-
"python-a2s>=1.
|
28
|
+
"python-a2s>=1.4.1",
|
29
29
|
"ujson>=5.10.0",
|
30
30
|
"lxml>=5.2.2",
|
31
31
|
"rcon>=2.1.0",
|
32
32
|
"pillow>9",
|
33
33
|
"beautifulsoup4>=4.12.3",
|
34
|
+
"rarfile>=4.2",
|
35
|
+
"pyunpack>=0.3",
|
36
|
+
"aiofiles>=24.1.0",
|
34
37
|
]
|
35
38
|
classifiers = [
|
36
39
|
"License :: OSI Approved :: GNU General Public License v3 (GPLv3)",
|
@@ -52,7 +55,7 @@ homepage = "https://github.com/Agnes4m/nonebot_plugin_l4d2_server"
|
|
52
55
|
[tool.pdm.build]
|
53
56
|
includes = []
|
54
57
|
|
55
|
-
[tool.ruff]
|
58
|
+
[tool.ruff.lint]
|
56
59
|
ignore = [
|
57
60
|
"B008",
|
58
61
|
"B905",
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|