Skip to content

Commit 8617042

Browse files
committed
Make server requests work over multiple threads at once
1 parent 3c295dd commit 8617042

7 files changed

Lines changed: 99 additions & 33 deletions

File tree

src/main/java/com/pokegoapi/api/PokemonGo.java

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -75,15 +75,13 @@ private PlayerDataOuterClass.PlayerData getPlayerAndUpdateInventory(PlayerProfil
7575

7676
GetPlayerMessage getPlayerReqMsg = GetPlayerMessage.newBuilder().build();
7777
ServerRequest getPlayerServerRequest = new ServerRequest(RequestType.GET_PLAYER, getPlayerReqMsg);
78-
getRequestHandler().request(getPlayerServerRequest);
7978

8079
GetInventoryMessage invReqMsg = GetInventoryMessage.newBuilder()
8180
.setLastTimestampMs(this.lastInventoryUpdate)
8281
.build();
8382
ServerRequest getInventoryServerRequest = new ServerRequest(RequestType.GET_INVENTORY, invReqMsg);
84-
getRequestHandler().request(getInventoryServerRequest);
8583

86-
getRequestHandler().sendServerRequests();
84+
getRequestHandler().sendServerRequests(getPlayerServerRequest, getInventoryServerRequest);
8785

8886
GetPlayerResponse getPlayerResponse;
8987
GetInventoryResponse getInventoryResponse;

src/main/java/com/pokegoapi/api/inventory/Bag.java

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -38,8 +38,7 @@ public Result removeItem(ItemId id, int quantity) throws RemoteServerException,
3838
.setItemId(id).setCount(quantity).build();
3939

4040
ServerRequest serverRequest = new ServerRequest(RequestTypeOuterClass.RequestType.RECYCLE_INVENTORY_ITEM, msg);
41-
pgo.getRequestHandler().request(serverRequest);
42-
pgo.getRequestHandler().sendServerRequests();
41+
pgo.getRequestHandler().sendServerRequests(serverRequest);
4342

4443
RecycleInventoryItemResponseOuterClass.RecycleInventoryItemResponse response = null;
4544
try {

src/main/java/com/pokegoapi/api/map/Map.java

Lines changed: 5 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -166,8 +166,7 @@ public MapObjects getMapObjects(List<Long> cellIds) throws LoginFailedException,
166166
}
167167

168168
ServerRequest serverRequest = new ServerRequest(RequestTypeOuterClass.RequestType.GET_MAP_OBJECTS, builder.build());
169-
api.getRequestHandler().request(serverRequest);
170-
api.getRequestHandler().sendServerRequests();
169+
api.getRequestHandler().sendServerRequests(serverRequest);
171170
GetMapObjectsResponseOuterClass.GetMapObjectsResponse response = null;
172171
try {
173172
response = GetMapObjectsResponseOuterClass.GetMapObjectsResponse.parseFrom(serverRequest.getData());
@@ -237,8 +236,7 @@ public FortDetails getFortDetails(String id, long lon, long lat) throws LoginFai
237236
.build();
238237

239238
ServerRequest serverRequest = new ServerRequest(RequestTypeOuterClass.RequestType.FORT_DETAILS, reqMsg);
240-
api.getRequestHandler().request(serverRequest);
241-
api.getRequestHandler().sendServerRequests();
239+
api.getRequestHandler().sendServerRequests(serverRequest);
242240
FortDetailsResponseOuterClass.FortDetailsResponse response = null;
243241
try {
244242
response = FortDetailsResponseOuterClass.FortDetailsResponse.parseFrom(serverRequest.getData());
@@ -258,8 +256,7 @@ public FortSearchResponseOuterClass.FortSearchResponse searchFort(FortDataOuterC
258256
.setPlayerLongitude(api.getLongitude())
259257
.build();
260258
ServerRequest serverRequest = new ServerRequest(RequestTypeOuterClass.RequestType.FORT_SEARCH, reqMsg);
261-
api.getRequestHandler().request(serverRequest);
262-
api.getRequestHandler().sendServerRequests();
259+
api.getRequestHandler().sendServerRequests(serverRequest);
263260
FortSearchResponseOuterClass.FortSearchResponse response = null;
264261
try {
265262
response = FortSearchResponseOuterClass.FortSearchResponse.parseFrom(serverRequest.getData());
@@ -278,8 +275,7 @@ public EncounterResponseOuterClass.EncounterResponse encounterPokemon(MapPokemon
278275
.setSpawnpointId(catchablePokemon.getSpawnpointId())
279276
.build();
280277
ServerRequest serverRequest = new ServerRequest(RequestTypeOuterClass.RequestType.ENCOUNTER, reqMsg);
281-
api.getRequestHandler().request(serverRequest);
282-
api.getRequestHandler().sendServerRequests();
278+
api.getRequestHandler().sendServerRequests(serverRequest);
283279
EncounterResponseOuterClass.EncounterResponse response = null;
284280
try {
285281
response = EncounterResponseOuterClass.EncounterResponse.parseFrom(serverRequest.getData());
@@ -301,8 +297,7 @@ public CatchPokemonResponseOuterClass.CatchPokemonResponse catchPokemon(MapPokem
301297
.setPokeball(pokeball)
302298
.build();
303299
ServerRequest serverRequest = new ServerRequest(RequestTypeOuterClass.RequestType.CATCH_POKEMON, reqMsg);
304-
api.getRequestHandler().request(serverRequest);
305-
api.getRequestHandler().sendServerRequests();
300+
api.getRequestHandler().sendServerRequests(serverRequest);
306301
CatchPokemonResponseOuterClass.CatchPokemonResponse response = null;
307302
try {
308303
response = CatchPokemonResponseOuterClass.CatchPokemonResponse.parseFrom(serverRequest.getData());

src/main/java/com/pokegoapi/api/map/Pokemon/CatchablePokemon.java

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -71,8 +71,7 @@ public EncounterResult encounterPokemon() throws LoginFailedException, RemoteSer
7171
.setSpawnpointId(getSpawnpointId())
7272
.build();
7373
ServerRequest serverRequest = new ServerRequest(RequestTypeOuterClass.RequestType.ENCOUNTER, reqMsg);
74-
api.getRequestHandler().request(serverRequest);
75-
api.getRequestHandler().sendServerRequests();
74+
api.getRequestHandler().sendServerRequests(serverRequest);
7675
EncounterResponseOuterClass.EncounterResponse response = null;
7776
try {
7877
response = EncounterResponseOuterClass.EncounterResponse.parseFrom(serverRequest.getData());
@@ -149,8 +148,7 @@ public CatchResult catchPokemon(double normalizedHitPosition, double normalizedR
149148
.setPokeball(type.getBalltype())
150149
.build();
151150
ServerRequest serverRequest = new ServerRequest(RequestTypeOuterClass.RequestType.CATCH_POKEMON, reqMsg);
152-
api.getRequestHandler().request(serverRequest);
153-
api.getRequestHandler().sendServerRequests();
151+
api.getRequestHandler().sendServerRequests(serverRequest);
154152

155153
try {
156154
response = CatchPokemonResponseOuterClass.CatchPokemonResponse.parseFrom(serverRequest.getData());

src/main/java/com/pokegoapi/api/map/fort/Pokestop.java

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -71,8 +71,7 @@ public PokestopLootResult loot() throws LoginFailedException, RemoteServerExcept
7171
.build();
7272

7373
ServerRequest serverRequest = new ServerRequest(RequestTypeOuterClass.RequestType.FORT_SEARCH, searchMessage);
74-
api.getRequestHandler().request(serverRequest);
75-
api.getRequestHandler().sendServerRequests();
74+
api.getRequestHandler().sendServerRequests(serverRequest);
7675
FortSearchResponseOuterClass.FortSearchResponse response;
7776
try {
7877
response = FortSearchResponseOuterClass.FortSearchResponse.parseFrom(serverRequest.getData());
@@ -98,8 +97,7 @@ public FortDetails getDetails() throws LoginFailedException, RemoteServerExcepti
9897
.build();
9998

10099
ServerRequest serverRequest = new ServerRequest(RequestTypeOuterClass.RequestType.FORT_DETAILS, reqMsg);
101-
api.getRequestHandler().request(serverRequest);
102-
api.getRequestHandler().sendServerRequests();
100+
api.getRequestHandler().sendServerRequests(serverRequest);
103101
FortDetailsResponseOuterClass.FortDetailsResponse response = null;
104102
try {
105103
response = FortDetailsResponseOuterClass.FortDetailsResponse.parseFrom(serverRequest.getData());

src/main/java/com/pokegoapi/api/pokemon/Pokemon.java

Lines changed: 3 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -39,8 +39,7 @@ public Result transferPokemon() throws LoginFailedException, RemoteServerExcepti
3939
ReleasePokemonMessage reqMsg = ReleasePokemonMessage.newBuilder().setPokemonId(getId()).build();
4040

4141
ServerRequest serverRequest = new ServerRequest(RequestType.RELEASE_POKEMON, reqMsg);
42-
pgo.getRequestHandler().request(serverRequest);
43-
pgo.getRequestHandler().sendServerRequests();
42+
pgo.getRequestHandler().sendServerRequests(serverRequest);
4443

4544
ReleasePokemonResponse response;
4645
try {
@@ -61,8 +60,7 @@ public NicknamePokemonResponse.Result renamePokemon(String nickname) throws Logi
6160
NicknamePokemonMessage reqMsg = NicknamePokemonMessage.newBuilder().setPokemonId(getId()).setNickname(nickname).build();
6261

6362
ServerRequest serverRequest = new ServerRequest(RequestType.NICKNAME_POKEMON, reqMsg);
64-
pgo.getRequestHandler().request(serverRequest);
65-
pgo.getRequestHandler().sendServerRequests();
63+
pgo.getRequestHandler().sendServerRequests(serverRequest);
6664

6765
NicknamePokemonResponse response;
6866
try {
@@ -78,8 +76,7 @@ public EvolutionResult evolve() throws LoginFailedException, RemoteServerExcepti
7876
EvolvePokemonMessage reqMsg = EvolvePokemonMessage.newBuilder().setPokemonId(getId()).build();
7977

8078
ServerRequest serverRequest = new ServerRequest(RequestType.EVOLVE_POKEMON, reqMsg);
81-
pgo.getRequestHandler().request(serverRequest);
82-
pgo.getRequestHandler().sendServerRequests();
79+
pgo.getRequestHandler().sendServerRequests(serverRequest);
8380

8481
EvolvePokemonResponse response;
8582
try {

src/main/java/com/pokegoapi/main/RequestHandler.java

Lines changed: 85 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -36,16 +36,89 @@ public RequestHandler(PokemonGo api, RequestEnvelopeOuterClass.RequestEnvelope.A
3636
this.client = client;
3737
api_endpoint = APISettings.API_ENDPOINT;
3838
this.auth = auth;
39-
serverRequests = new ArrayList<ServerRequest>();
39+
serverRequests = new ArrayList<>();
40+
// TODO: somehow fix it so people using the deprecated functions will still work, while not calling this deprecated stuff ourselves
4041
resetBuilder();
4142
}
4243

44+
@Deprecated
4345
public void request(ServerRequest requestIn) {
4446
hasRequests = true;
4547
serverRequests.add(requestIn);
4648
builder.addRequests(requestIn.getRequest());
4749
}
4850

51+
public void sendServerRequests(ServerRequest... serverRequests) throws RemoteServerException, LoginFailedException {
52+
if (serverRequests.length == 0) {
53+
return;
54+
}
55+
RequestEnvelopeOuterClass.RequestEnvelope.Builder builder = RequestEnvelopeOuterClass.RequestEnvelope.newBuilder();
56+
resetBuilder(builder);
57+
58+
for (ServerRequest serverRequest : serverRequests) {
59+
builder.addRequests(serverRequest.getRequest());
60+
}
61+
62+
ByteArrayOutputStream stream = new ByteArrayOutputStream();
63+
RequestEnvelopeOuterClass.RequestEnvelope request = builder.build();
64+
try {
65+
request.writeTo(stream);
66+
} catch (IOException e) {
67+
Log.wtf(TAG, "Failed to write request to bytearray ouput stream. This should never happen", e);
68+
}
69+
70+
RequestBody body = RequestBody.create(null, stream.toByteArray());
71+
okhttp3.Request httpRequest = new okhttp3.Request.Builder()
72+
.url(api_endpoint)
73+
.post(body)
74+
.build();
75+
Response response;
76+
try {
77+
response = client.newCall(httpRequest).execute();
78+
} catch (IOException e) {
79+
throw new RemoteServerException(e);
80+
}
81+
82+
if (response.code() != 200)
83+
throw new RemoteServerException("Got a unexcepted http code : " + response.code());
84+
85+
ResponseEnvelopeOuterClass.ResponseEnvelope responseEnvelop;
86+
try (InputStream content = response.body().byteStream()) {
87+
responseEnvelop = ResponseEnvelopeOuterClass.ResponseEnvelope.parseFrom(content);
88+
} catch (IOException e) {
89+
// retrieved garbage from the server
90+
throw new RemoteServerException("Received malformed response : " + e);
91+
}
92+
93+
if (responseEnvelop.getApiUrl() != null && responseEnvelop.getApiUrl().length() > 0) {
94+
api_endpoint = "https://" + responseEnvelop.getApiUrl() + "/rpc";
95+
}
96+
97+
if (responseEnvelop.hasAuthTicket()) {
98+
lastAuth = responseEnvelop.getAuthTicket();
99+
}
100+
101+
if (responseEnvelop.getStatusCode() == 102) {
102+
throw new LoginFailedException();
103+
} else if (responseEnvelop.getStatusCode() == 53) {
104+
// 53 means that the api_endpoint was not correctly set, should be at this point, though, so redo the request
105+
sendServerRequests(serverRequests);
106+
return;
107+
}
108+
109+
// map each reply to the numeric response, ie first response = first request and send back to the requests to handle.
110+
int count = 0;
111+
for (ByteString payload : responseEnvelop.getReturnsList()) {
112+
ServerRequest serverReq = serverRequests[count];
113+
// TODO: Probably all other payloads are garbage as well in this case, so might as well throw an exception and leave this loop
114+
if (payload != null) {
115+
serverReq.handleData(payload);
116+
}
117+
count++;
118+
}
119+
}
120+
121+
@Deprecated
49122
public void sendServerRequests() throws RemoteServerException, LoginFailedException {
50123
setLatitude(api.getLatitude());
51124
setLongitude(api.getLongitude());
@@ -64,7 +137,7 @@ public void sendServerRequests() throws RemoteServerException, LoginFailedExcept
64137
.url(api_endpoint)
65138
.post(body)
66139
.build();
67-
Response response = null;
140+
Response response;
68141
try {
69142
response = client.newCall(httpRequest).execute();
70143
} catch (IOException e) {
@@ -112,17 +185,25 @@ public void sendServerRequests() throws RemoteServerException, LoginFailedExcept
112185
resetBuilder();
113186
}
114187

188+
@Deprecated
115189
private void resetBuilder() {
116190
builder = RequestEnvelopeOuterClass.RequestEnvelope.newBuilder();
191+
resetBuilder(builder);
192+
hasRequests = false;
193+
serverRequests.clear();
194+
}
195+
196+
private void resetBuilder(RequestEnvelopeOuterClass.RequestEnvelope.Builder builder) {
117197
builder.setStatusCode(2);
118198
builder.setRequestId(8145806132888207460l);
119199
if (lastAuth != null && lastAuth.getExpireTimestampMs() > 0)
120200
builder.setAuthTicket(lastAuth);
121201
else
122202
builder.setAuthInfo(auth);
123203
builder.setUnknown12(989);
124-
hasRequests = false;
125-
serverRequests.clear();
204+
builder.setLatitude(api.getLatitude());
205+
builder.setLongitude(api.getLongitude());
206+
builder.setAltitude(api.getAltitude());
126207
}
127208

128209

0 commit comments

Comments
 (0)