Correct JSON object can't be read - java

I have an object that I want to parse to a JSON string. When I want to read it out, it says it can't parse it back to an object (i think). This is the error:
As you can see at the top of the console, the JSON object is set properly with the right brackets. What I understand from the JSONSyntaxException is that it doesn't recognize it as a JSON object. I've copied this code from my school and in a different project it does work. I don't know why it doesn't work in my Maven project.
EDIT
This is the code for RESTcontroller.java.
public PlayerDTO addPlayer(String name, String password) {
PlayerDTO playerRequest = new PlayerDTO(NOTDEFINED, name, password);
String queryPost = "/player";
PlayerResponse response = executeQueryPost(playerRequest, queryPost);
return response.getPlayers().get(0);
}
private PlayerResponse executeQueryPost(PlayerDTO playerRequest, String queryPost) {
final String query = url + queryPost;
log.info("[Query POST] : " + query);
HttpPost httpPost = new HttpPost(query);
httpPost.addHeader("content-type", "application/json");
StringEntity params;
try{
params = new StringEntity(gson.toJson(playerRequest));
System.out.println(gson.toJson(playerRequest));
httpPost.setEntity(params);
} catch (UnsupportedEncodingException e) {
Logger.getLogger(SeaBattleGame.class.getName()).log(Level.SEVERE, null, e);
}
return executeHttpUriRequest(httpPost);
}
private PlayerResponse executeHttpUriRequest(HttpUriRequest httpUriRequest) {
// Execute the HttpUriRequest
try (CloseableHttpClient httpClient = HttpClients.createDefault();
CloseableHttpResponse response = httpClient.execute(httpUriRequest)) {
log.info("[Status Line] : " + response.getStatusLine());
HttpEntity entity = response.getEntity();
final String entityString = EntityUtils.toString(entity);
log.info("[Entity] : " + entityString);
return gson.fromJson(entityString, PlayerResponse.class);
} catch (IOException e) {
log.info("IOException : " + e.toString());
PlayerResponse playerResponse = new PlayerResponse();
playerResponse.setSuccess(false);
return playerResponse;
} catch (JsonSyntaxException e) {
log.info("JsonSyntaxException : " + e.toString());
PlayerResponse playerResponse = new PlayerResponse();
playerResponse.setSuccess(false);
return playerResponse;
}
}
Keep in mind that the code gave me this code and it does work in their project!

It would seem to me that your request is failing with this error: Problem accessing /seabattle/player Reason: request failed. It's not very discriptive, but it's something.
Your code is then failing with a NullPointerException, I'm guessing response.getPlayers() is returning a null.
You should really try and send a similar JSON to this endpoint from a curl command or via Postman app and see if it works. Or if you can, see the webserver logs to find out what the actual problem is.
EDIT: You should really also check the response status before trying to parse it. This will get rid of the NullPointerException and will make your code better in general.

A couple of things to fix the issue:
In the method executeQueryPost you have to add the following headers for the request:
httpPost.setHeader("Accept", "application/json");
httpPost.setHeader("Content-type", "application/json");
And the code should look like the following:
private PlayerResponse executeQueryPost(PlayerDTO playerRequest, String queryPost) {
final String query = url + queryPost;
log.info("[Query POST] : " + query);
HttpPost httpPost = new HttpPost(query);
httpPost.addHeader("content-type", "application/json");
StringEntity params;
try{
params = new StringEntity(gson.toJson(playerRequest));
System.out.println(gson.toJson(playerRequest));
httpPost.setEntity(params);
// Need to add the following headers
httpPost.setHeader("Accept", "application/json");
httpPost.setHeader("Content-type", "application/json");
} catch (UnsupportedEncodingException e) {
Logger.getLogger(SeaBattleGame.class.getName()).log(Level.SEVERE, null, e);
}
return executeHttpUriRequest(httpPost);
}
In case the the code continue failing is because it can't create the new player. You must handle the exception in addPlayer() method. Before the return check if the object returned by executeQueryPost is not null.
Update:
The code may be failing just because the service in: http://localhost:8090 isn't running that's why it getting 500 as response.

Related

http post request return 400

I'm using HTTP post method to call Gitlab API which in return it gives me 400 response code.
I have tested the gitlab api with postman with providing propers headers and content body as JSON.
it worked fine and. ( I use gitlab create branch api )
I have debugged the application using eclipse and , there is some specific line which gave me null
I'm using apache http client 4.5.5 to handle http requests.
this is my first method to create a branch
public HttpResponse createBranch(String projectId, String branchName, String ref) {
// url is ok, i debugged it
String url = this.API_BASE_URL + projectId + "/repository/branches";
//branchName = "uifix branch";
//ref = "master";
JSONObject obj = new JSONObject();
try {
obj.put("branch", branchName);
obj.put("ref", ref);
} catch (JSONException e) {
e.printStackTrace();
}
Map<String, String> headerParams = new HashMap<String, String>();
headerParams.put("Private-Token", PAT);
headerParams.put("Content-Type", "application/json; utf-8");
headerParams.put("Accept", "application/json");
return HttpUtility.httpPostForResourceCreation(url, headerParams, obj.toString());
}
then will call the following method which is in httputlity class.
public static HttpResponse httpPostForResourceCreation(String url, Map<String, String> headerParam, String body) {
HttpPost request = new HttpPost(url);
StringEntity params = new StringEntity(body, ContentType.APPLICATION_JSON);
for (Map.Entry<String, String> entry : headerParam.entrySet()) {
request.setHeader(entry.getKey(), entry.getValue());
}
request.setEntity(params); // I think problem is here. when I debugged it , it shows null.
return execute(request);
}
then will call the last method
private static HttpResponse execute(HttpRequestBase request) {
HttpClient httpClient = HttpUtility.buildHttpClient();
HttpResponse response = null;
try {
response = httpClient.execute(request);
} catch (ClientProtocolException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
if(response.getStatusLine().getStatusCode() == 201) {
System.out.println("resource successfully created: " + 201);
} else {
System.out.println("resource creation failed: " + response.getStatusLine().getStatusCode());
}
return response;
}
expected result should be "resource successfully created: + 201"
instead of I'm getting "resource creation failed: 400"
here I attached my request object content
so, what I'm missing here ? Any help would be appreciated.

Javax-RS - how to create a client to push data to a server?

I need to push data from a standalone client back to the server. This client already accesses the server to get information, parses it, executes what it has to do, but now I need it to push back some information.
I have tried doing this:
public class UpdateServer {
public void update(int resultSetRowCount) {
AgentConfiguration config = new AgentConfiguration();
config.init();
String agentId = AgentConfiguration.agent_id;
String serverIp = AgentConfiguration.server_ip;
String serverPort = AgentConfiguration.server_port;
Calendar cal = Calendar.getInstance();
StringBuilder timestamp = new StringBuilder();
timestamp.append(cal.get(Calendar.YEAR));
timestamp.append(String.format("%02d",cal.get(Calendar.MONTH) + 1));
timestamp.append(String.format("%02d",cal.get(Calendar.DAY_OF_MONTH)));
timestamp.append(String.format("%02d",cal.get(Calendar.HOUR_OF_DAY)));
timestamp.append(String.format("%02d",cal.get(Calendar.MINUTE)));
timestamp.append(String.format("%02d",cal.get(Calendar.SECOND)));
String date = timestamp.toString();
String uri = "http://" + serverIp + ":" + serverPort + "/hrm/alerts/" + agentId + "/" + date + "/" + resultSetRowCount;
System.out.println(uri);
try {
// create HTTP Client
HttpClient httpClient = HttpClientBuilder.create().build();
// Create new patchRequest with below mentioned URL
HttpPost postRequest = new HttpPost(uri);
// Add additional header to postRequest which accepts application/xml data
postRequest.addHeader("accept", "application/xml");
// Execute your request and catch response
HttpResponse response = httpClient.execute(postRequest);
// Check for HTTP response code: 200 = success
if (response.getStatusLine().getStatusCode() != 200) {
throw new RuntimeException("Failed : HTTP error code : " + response.getStatusLine().getStatusCode());
}
} catch (ClientProtocolException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
}
I'm trying to access the server with the formatted uri using:
new UpdateServer().update(resultSetRowCount);
But I'm getting the following exception:
Exception in thread "main" java.lang.RuntimeException: Failed : HTTP error code : 405
What am I missing here?
One of the causes of http error code 405 is when a payload is not passed to the POST method. Probably that is the case with your program.
You can use PostMethod instead of HttpPost and set the payload
Your code will look like
...
String uri = "http://" + serverIp + ":" + serverPort + "/hrm/alerts/" + agentId + "/" + date + "/" + resultSetRowCount;
System.out.println(uri);
try
{
// create HTTP Client
HttpClient httpClient = HttpClientBuilder.create().build();
PostMethod post = new PostMethod(uri);
RequestEntity requestEntity = new StringRequestEntity(payload, "application/xml", null/*charset default*/);
post.setRequestEntity(requestEntity);
int iResult = httpclient.executeMethod(post);
// get the status code using post.getStatusCode()
// you can get the response using post.getResponseBodyAsString()
// Check for HTTP response code: 200 = success
if (post.getStatusCode() != 200) {
throw new RuntimeException("Failed : HTTP error code : " + post.getStatusCode());
}
} catch (ClientProtocolException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}

HTTPResponse's string from Play is empty

I am using Play and Faye on my Server. Play is used for API calls, while Faye is used for communication with the clients.
So, I have this method in the server:
public static Result broadcast(String channel, String message)
{
try
{
FayeClient faye = new FayeClient("localhost");
int code = faye.send(channel, message);
// print the code (prints 200).
return ok("Hello"); <------------ This is what we care about.
}
catch(Exception e)
{
return ok("false");
}
}
this is the code on the client, which is an android phone.
(it's the HTTP post method, which sends something to the server and gets a response back
The problem is, I can't print the message of the response.
public static String post(String url, List<BasicNameValuePair> params)
{
HttpClient httpclient = new DefaultHttpClient();
String result = "";
// Prepare a request object
HttpPost httpPost;
httpPost = new HttpPost(url);
httpPost.setHeader("Content-type", "application/json");
httpPost.setHeader("Accept", "application/json");
JSONObject obj = new JSONObject();
try
{
for (NameValuePair pair : params)
obj.put(pair.getName(), pair.getValue());
}
catch (JSONException e)
{
return e.getMessage();
}
// Add your data
try
{
httpPost.setEntity(new StringEntity(obj.toString(), "UTF-8"));
}
catch (UnsupportedEncodingException e)
{
return e.getMessage();
}
HttpResponse httpResponse;
try
{
httpResponse = httpclient.execute(httpPost);
// Get hold of the response entity
HttpEntity entity = httpResponse.getEntity();
String str = EntityUtils.toString(entity);
Log.e("RestClient", "result = \"" + str + "\""); // hello should be printed here??
}
catch(Exception e)
{
// ...
}
The problem is that in logcat, what is printed is [result = ""]. Am I doing something wrong?
Thank you.
Use a tool such as Fiddler and see what the HTTP response contains.

Android Unable to Retrieve JSON response [SC_406]

I have the code which basically retrieving a list of search result based on given keyword from TMDB (API ver.3, new API).
public String getPersonSearchResult(String keywords){
String query = URLEncoder.encode(keywords);
String TMDB_API_URL = "http://api.themoviedb.org/3/search/person?";
String TMDB_LIMIT_LIST = "&page=1";
String TMDB_QUERY = "&query=" + query;
HttpClient httpclient = new DefaultHttpClient();
HttpResponse response;
String responseString = null;
try
{
// ATTEMPT HTTP REQUEST
String fullUrl = TMDB_API_URL + TMDB_API_KEY + TMDB_QUERY + TMDB_LIMIT_LIST;
Log.w(APP_TAG, "TRYING [" + fullUrl + "]");
response = httpclient.execute(new HttpGet(fullUrl));
StatusLine statusLine = response.getStatusLine();
if (statusLine.getStatusCode() == HttpStatus.SC_OK)
{
ByteArrayOutputStream out = new ByteArrayOutputStream();
response.getEntity().writeTo(out);
out.close();
responseString = out.toString();
}else{
// FAILED REQUEST - CLOSE THE CONNECTION
response.getEntity().getContent().close();
throw new IOException(statusLine.getReasonPhrase());
}
}catch(Exception e){
Log.w(APP_TAG, e.getLocalizedMessage());
Log.w(APP_TAG, "FAILED TO RETRIEVE JSON DATA");
}
return responseString;
}
The problem is that i always get 406 Status Code (Not Acceptable). When i tried to run the URL myself
http://api.themoviedb.org/3/search/person?api_key=<MY_API_KEY_HERE>&query=jennifer&page=1
It displays the JSON result correctly.
I am not sure why is this happening. Similar function is used to retrieve JSON value from other source and and it works perfectly.
this is their API docs regarding search: http://docs.themoviedb.apiary.io/#search
Can anyone points me to the right direction? Any help is appreciated.
I figure it out, by adding this:
HttpGet getObj = new HttpGet(fullUrl);
getObj.addHeader("Accept", "application/json");
Perhaps this is API specific requirement. Not sure though...
One way to do it
Try using builder.scheme
URIBuilder builder = new URIBuilder();
builder.setScheme("http").setHost("api.themoviedb.org").setPath("/3/search/person")
.setParameter("api_key", YOURAPIKEY)
.setParameter("page", 1)
.setParameter("query", query)
URI uri = builder.build();
HttpGet httpget = new HttpGet(uri);
.....
response = httpclient.execute(new HttpGet(httpget ));
I think its nothing to do with your code.. your code is perfect. The only problem might be with the API request method. Maybe they require some specific headers to be requested for in the request. Give a try with requesting headers like "("Accept", "application/json")" It might work..
try this
String ret = null; try {
response = httpClient.execute(httpGet);
} catch (Exception e) {
e.printStackTrace();
}
try {
ret = EntityUtils.toString(response.getEntity());
} catch (IOException e) {
Log.e("HttpRequest", "" + e.getMessage());
} catch (Exception e) {
e.printStackTrace();
}
return ret;

Error: Target host must not be null, or set in parameters

I am trying to send a string from one application to another. I would be returning a response which is a string. Here, myhost.com/views is the 2nd application where I need to send the string value and get a response from it. But when I am trying to send it is not executing this code. Can someone please correct me where I am wrong?
Below is the code I have written.
public static void sendData(String strval) throws IOException{
String doSend="https://myhost.com/views?strval="+strval;
HttpClient httpclient = new DefaultHttpClient();
try {
System.out.println("inside try");
URIBuilder builder = new URIBuilder();
System.out.println("builder="+builder);
builder.setHost("myhost.com").setPath("/views");
builder.addParameter("strval", strval);
System.out.println("add param,sethost,setpath complete");
URI uri = builder.build();
System.out.println("uri="+uri);
HttpGet httpget = new HttpGet(uri);
System.out.println("httpGet"+httpget);
HttpResponse response = httpclient.execute(httpget);
System.out.println(response.getStatusLine().toString());
if (response.getStatusLine().getStatusCode() == 200) {
String responseText = EntityUtils.toString(response.getEntity());
System.out.println("responseText="+responseText);
httpclient.getConnectionManager().shutdown();
} else {
System.out.println("Server returned HTTP code "
+ response.getStatusLine().getStatusCode());
}
} catch (java.net.URISyntaxException bad) {
System.out.println("URI construction error: " + bad.toString());
}
catch(Exception e){ System.out.println("e.getMessage=>"+e.getMessage()); }
}
Code runs till and when I print the exceptions I see excep.getMessage() ->
java.lang.IllegalStateException: Target host must not be null, or set in parameters.
at org.apache.http.impl.client.DefaultRequestDirector.determineRoute(DefaultRequestDirector.java:789)
at org.apache.http.impl.client.DefaultRequestDirector.execute(DefaultRequestDirector.java:414)
at org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:906)
at org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:805)
at org.apache.http.impl.client.AbstractHttpClient.execute(AbstractHttpClient.java:784)
This code is not able to recognize it as a valid URI since it was missing http. This is what I added to resolve the code:
builder.setScheme("http");

Categories

Resources