I have JSON which is coming by executing a URL. I want to store all the value of id
field in a List<String>
by parsing through GSON. Also, if the next
field is true, then that means there is another URL at the bottom of the JSON which I need to use to get the second page which will also look like this JSON response which will have ids again, so I will add those ids into the same list again.
Here is the flow:
- Execute the URL and get JSON response. After, that check if the
next
field is true or false in that JSON response. - If it is false, then there is only one page so add all those ids into my
List<String>
and return. - If it is true, then there will be another URL at the bottom. Use that URL and add prefix to it and then execute it to get another JSON response and repeat the same thing until
next
is false and keep adding all ids into the same list.
JSON response:
{
"status": {
"number": "100",
"value": "ok"
},
"next": true,
"result": [{
"type": "Process",
"id": "1.2.3.4.5.6",
"device": "hello"
}, {
"type": "Process",
"id": "9.55.1.2.3.2",
"device": "world"
}, {
"type": "Process",
"id": "5.4.3.2.1.2",
"device": "proc"
}, {
"type": "Process",
"id": "99.11.11.2.3.4",
"device": "oreon"
}],
"pagination": {
"cursor": ["", "57d9e9d4e4b073aa2f401542", ""],
"limit": [10000, 1000, 1000],
"hint": 0,
"maxFetch": 0,
"skipEmptyPage": false
},
"next": {
"method": "GET",
"url": "/tries/next_set"
}
}
Working code:
public List<String> getIds() {
List<String> ids = new ArrayList<>();
try {
String url = generateUrl();
boolean hasMore = true;
while (hasMore) {
Optional<String> response = executeUrl(url);
if (!response.isPresent()) {
JsonElement jelement = new JsonParser().parse(response.get());
JsonObject jobject = jelement.getAsJsonObject();
hasMore = jobject.get("next").getAsBoolean();
if (hasMore) {
url = PREFIX + jobject.getAsJsonObject("next").get("url").getAsString();
}
JsonArray jarray = jobject.getAsJsonArray("result");
for (JsonElement type : jarray) {
ids.add(type.getAsJsonObject().get("id").getAsString());
}
} else {
hasMore = false; // to avoid infinite loop if response is not present
}
}
} catch (Exception ex) {
// log error
}
return ids;
}
Below is how my execute
method looks like:
private Optional<String> execute(final String url) {
Optional<String> abcResponse = Optional.absent();
try (AsyncHttpClient asyncHttpClient = new DefaultAsyncHttpClient()) {
Future<Response> future = asyncHttpClient.prepareGet(url).execute();
Response response = future.get();
abcResponse = Optional.of(response.getResponseBody(StandardCharsets.UTF_8.displayName()));
System.out.println(response.getResponseBody());
} catch (IOException | InterruptedException | ExecutionException ex) {
// logging error
}
return abcResponse;
}
The first URL is always generated by calling the generateUrl()
method which is different than the subsequent URL which are there in the bottom of the JSON response. I want to see if there is any better way to do the same thing.