@@ -62,12 +62,10 @@ async def get_status(self, xserverquery: bool = True) -> dict:
62
62
data = xserverquery and self .__Request .STATUS or self .__Request .STATUS .replace (b'xserverquery' , b'' )
63
63
br = await self .__connect_and_send (data )
64
64
65
- info = self .__parse_as_key_values (br , is_status = True )
66
- players = self .__parse_as_object (br )
67
-
68
65
status = {}
69
- status ['info' ] = info
70
- status ['players' ] = players
66
+ status ['info' ] = self .__parse_as_key_values (br , is_status = True )
67
+ status ['players' ] = self .__parse_as_object (br , is_player = True )
68
+ status ['teams' ] = [] if br .is_end () else self .__parse_as_object (br )
71
69
72
70
return status
73
71
@@ -76,33 +74,28 @@ async def get_teams(self) -> list:
76
74
return self .__parse_as_object (await self .__connect_and_send (self .__Request .TEAMS ))
77
75
78
76
# Receive packets and sort it
79
- async def __get_packets_response (self , sock ):
77
+ async def __get_packets_response (self , sock : SocketAsync ):
80
78
payloads = {}
81
79
packet_count = - 1
82
80
83
81
# Loop until received all packets
84
82
while packet_count == - 1 or len (payloads ) < packet_count :
85
83
packet = await sock .recv ()
86
84
87
- # If it is the last packet, it will contain b'\\final\\' at the end of the response
88
- if packet .rsplit (b'\\ ' , 2 )[1 ] == b'final' :
89
- # Split to payload, "queryid", query_id
90
- payload , _ , query_id = packet [:- 7 ].rsplit (b'\\ ' , 2 )
91
-
92
- # Get the packet number from query_id
93
- number = re .search (rb'\d+.(\d+)' , query_id ).group (1 )
85
+ # Get the packet number from query_id
86
+ r = re .compile (rb'\\queryid\\\d+\.(\d+)' )
87
+ number , payload = int (r .search (packet ).group (1 )), r .sub (b'' , packet )
94
88
89
+ # If it is the last packet, it will contain b'\\final\\' at the end of the response
90
+ if payload .endswith (b'\\ final\\ ' ):
95
91
# Save the packet count
96
- packet_count = int (number )
97
- else :
98
- # Split to payload, "queryid", query_id
99
- payload , _ , query_id = packet .rsplit (b'\\ ' , 2 )
92
+ packet_count = number
100
93
101
- # Get the packet number from query_id
102
- number = re . search ( rb'\d+.(\d+)' , query_id ). group ( 1 )
94
+ # Remove the last b'\\final\\'
95
+ payload = payload [: - 7 ]
103
96
104
97
# Save the payload, remove the first byte if it is the first packet
105
- payloads [number ] = int ( number ) == 1 and payload [ 1 :] or payload
98
+ payloads [number ] = payload [ 1 :] if number == 1 else payload
106
99
107
100
# Sort the payload and return as bytes
108
101
response = b'' .join (payloads [number ] for number in sorted (payloads ))
@@ -125,9 +118,9 @@ def __parse_as_key_values(self, br: BinaryReader, is_status=False):
125
118
126
119
# Bind key value
127
120
while br .length () > 0 :
128
- key = br .read_string (b'\\ ' )
121
+ key = br .read_string (b'\\ ' ). lower ()
129
122
130
- if is_status and key .lower () .startswith ('player_' ):
123
+ if is_status and ( key .startswith ( 'player_' ) or key .startswith ('playername_' ) ):
131
124
# Read already, so add it back
132
125
br .prepend_bytes (key .encode () + b'\\ ' )
133
126
break
@@ -137,16 +130,23 @@ def __parse_as_key_values(self, br: BinaryReader, is_status=False):
137
130
138
131
return kv
139
132
140
- def __parse_as_object (self , br : BinaryReader ):
133
+ def __parse_as_object (self , br : BinaryReader , is_player = False ):
141
134
items = []
142
135
143
136
while br .length () > 0 :
144
137
# Get the key, for example player_1, frags_1, ping_1, etc...
145
- key = br .read_string (b'\\ ' )
138
+ key = br .read_string (b'\\ ' ).lower ()
139
+
140
+ if is_player and key .startswith ('teamname_' ):
141
+ # Read already, so add it back
142
+ br .prepend_bytes (key .encode () + b'\\ ' )
143
+ break
146
144
147
145
# Extract to name and index, for example name=player, index=1
148
146
matches = re .search (r'(.+?)_(\d+)' , key )
149
147
name = matches .group (1 )
148
+ name = 'player' if name == 'playername' else name
149
+ name = 'team' if name == 'teamname' else name
150
150
index = int (matches .group (2 ))
151
151
152
152
# Append a dict to items if next index appears
@@ -167,11 +167,9 @@ def __parse_as_object(self, br: BinaryReader):
167
167
import json
168
168
169
169
async def main_async ():
170
- gs1 = GameSpy1 (
171
- address = '139.162.235.20' ,
172
- query_port = 7778 ,
173
- timeout = 5.0
174
- )
170
+ gs1 = GameSpy1 (address = '51.81.48.224' , query_port = 23000 , timeout = 5.0 ) # bfield1942
171
+ #gs1 = GameSpy1(address='139.162.235.20', query_port=7778, timeout=5.0) # ut
172
+ #gs1 = GameSpy1(address='192.223.24.6', query_port=7778, timeout=5.0) # ut
175
173
status = await gs1 .get_status ()
176
174
print (json .dumps (status , indent = None ) + '\n ' )
177
175
0 commit comments