200

I would like to make a simple HTTP POST using JSON in Java.

Let's say the URL is www.site.com

and it takes in the value {"name":"myname","age":"20"} labeled as 'details' for example.

How would I go about creating the syntax for the POST?

I also can't seem to find a POST method in the JSON Javadocs.

OneCricketeer
  • 126,858
  • 14
  • 92
  • 185
asdf007
  • 2,009
  • 2
  • 12
  • 3

11 Answers11

177

Here is what you need to do:

  1. Get the Apache HttpClient, this would enable you to make the required request
  2. Create an HttpPost request with it and add the header application/x-www-form-urlencoded
  3. Create a StringEntity that you will pass JSON to it
  4. Execute the call

The code roughly looks like (you will still need to debug it and make it work):

// @Deprecated HttpClient httpClient = new DefaultHttpClient();
HttpClient httpClient = HttpClientBuilder.create().build();
try {
    HttpPost request = new HttpPost("http://yoururl");
    StringEntity params = new StringEntity("details={\"name\":\"xyz\",\"age\":\"20\"} ");
    request.addHeader("content-type", "application/x-www-form-urlencoded");
    request.setEntity(params);
    HttpResponse response = httpClient.execute(request);
} catch (Exception ex) {
} finally {
    // @Deprecated httpClient.getConnectionManager().shutdown(); 
}
ℛɑƒæĿᴿᴹᴿ
  • 2,182
  • 2
  • 26
  • 44
momo
  • 20,477
  • 8
  • 36
  • 38
  • Super. This looks quite like what I would need to write. Im trying to take a look at Apache HttpClient at hc.apache.org/httpclient-3.x/ but it seems to be down? Hmph. – asdf007 Aug 24 '11 at 20:34
  • So do I not actually need a JSONObject? I can just input the String directly into the StringEntity as shown above and use that? – asdf007 Aug 24 '11 at 20:45
  • 10
    You could but it always good practice to abstract it out as JSONObject as if you are doing directly in the string, you might program the string wrongly and causing syntax error. By using JSONObject you make sure that your serialization is always follow the right JSON structure – momo Aug 24 '11 at 20:47
  • That's very true, thank you for pointing that out! :) I am having another look back at this, and I'm just curious, this looks almost the same as a normal POST request, what is the difference between a normal POST request and one that is implemented for JSON? – asdf007 Aug 24 '11 at 21:47
  • 3
    In principal, they are both just transmitting data. The only difference is how you process it in the server. If you have only few key-value pair then a normal POST parameter with key1=value1, key2=value2, etc is probably enough, but once your data is more complex and especially containing complex structure (nested object, arrays) you would want to start consider using JSON. Sending complex structure using a key-value pair would be very nasty and difficult to parse on the server (you could try and you'll see it right away). Still remember the day when we had to do that urgh.. it wasn't pretty.. – momo Aug 24 '11 at 21:53
  • Awesome. Thanks a ton momo! Really appreciate all the experienced information. – asdf007 Aug 24 '11 at 22:23
  • 1
    Glad to help! If this is what you are looking for, you should accept the answer so other people with similar questions have good lead to their questions. You can use the check mark on the answer. Let me know if you have further questions – momo Aug 25 '11 at 01:56
  • 13
    Shouldn't the content-type be 'application/json'. 'application/x-www-form-urlencoded' implies the string will be formatted similar to a query string. NM I see what you did, you put the json blob as a value of a property. – Matthew Ward May 02 '13 at 20:31
  • 1
    The deprecated part should be replaced by using CloseableHttpClient which gives you a .close() - method. See http://stackoverflow.com/a/20713689/1484047 – Frame91 Jun 28 '16 at 19:18
  • @mom can you please have a look on the this question [http://stackoverflow.com/questions/42024158/how-to-access-github-graphql-api-using-java?noredirect=1#comment71225261_42024158] I wrote code by looking at this answer, but I could get it working. Thanks in advance – Kasun Siyambalapitiya Feb 06 '17 at 04:04
  • @momo thank you very much. Really helped me out of a jam. – Ayusman Mar 24 '17 at 17:07
  • For an updated version of this code: https://hc.apache.org/httpcomponents-client-ga/quickstart.html – NoName Jun 12 '17 at 06:53
  • Android 6.0 release removes support for the Apache HTTP client. If your app is using this client and targets Android 2.3 (API level 9) or higher, use the `HttpURLConnection` class instead. – amirz98 Aug 07 '18 at 03:57
96

You can make use of Gson library to convert your java classes to JSON objects.

Create a pojo class for variables you want to send as per above Example

{"name":"myname","age":"20"}

becomes

class pojo1
{
   String name;
   String age;
   //generate setter and getters
}

once you set the variables in pojo1 class you can send that using the following code

String       postUrl       = "www.site.com";// put in your url
Gson         gson          = new Gson();
HttpClient   httpClient    = HttpClientBuilder.create().build();
HttpPost     post          = new HttpPost(postUrl);
StringEntity postingString = new StringEntity(gson.toJson(pojo1));//gson.tojson() converts your pojo to json
post.setEntity(postingString);
post.setHeader("Content-type", "application/json");
HttpResponse  response = httpClient.execute(post);

and these are the imports

import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.HttpClientBuilder;

and for GSON

import com.google.gson.Gson;
Buddhika Alwis
  • 353
  • 14
  • 21
Prakash
  • 6,772
  • 3
  • 43
  • 40
  • 1
    hi, how do you create your httpClient object? It's an interface – user3290180 Jan 26 '16 at 11:19
  • 1
    Yes that is an Interface. You can create an instance using 'HttpClient httpClient = new DefaultHttpClient();' – Prakash Jan 26 '16 at 15:03
  • 2
    now that is deprecated, we must use HttpClient httpClient = HttpClientBuilder.create().build(); – user3290180 Jan 28 '16 at 09:03
  • 5
    How importing HttpClientBuilder ? – Esterlinkof Apr 07 '16 at 14:11
  • are you missed new in line 5th of the second code example? `StringEntity postingString = new StringEntity(gson.toJson( new pojo1()));` I have a error when I removing new. – Esterlinkof Apr 07 '16 at 14:21
  • @Prakash can you please look on this question [http://stackoverflow.com/questions/42024158/how-to-access-github-graphql-api-using-java?noredirect=1#comment71225261_42024158] – Kasun Siyambalapitiya Feb 06 '17 at 04:41
  • HttpClientBuilder is in the Maven repository: org.apache.directory.studio:org.apache.httpcomponents:4.0 – Joel Stevick Aug 15 '17 at 18:19
  • 3
    I find it slightly cleaner to use the ContentType parameter on StringUtils constructor and pass in ContentType.APPLICATION_JSON instead of manually setting the header. – TownCube Feb 10 '18 at 12:30
57

@momo's answer for Apache HttpClient, version 4.3.1 or later. I'm using JSON-Java to build my JSON object:

JSONObject json = new JSONObject();
json.put("someKey", "someValue");    

CloseableHttpClient httpClient = HttpClientBuilder.create().build();

try {
    HttpPost request = new HttpPost("http://yoururl");
    StringEntity params = new StringEntity(json.toString());
    request.addHeader("content-type", "application/json");
    request.setEntity(params);
    httpClient.execute(request);
// handle response here...
} catch (Exception ex) {
    // handle exception here
} finally {
    httpClient.close();
}
Leonel Sanches da Silva
  • 5,441
  • 9
  • 42
  • 57
20

It's probably easiest to use HttpURLConnection.

http://www.xyzws.com/Javafaq/how-to-use-httpurlconnection-post-data-to-web-server/139

You'll use JSONObject or whatever to construct your JSON, but not to handle the network; you need to serialize it and then pass it to an HttpURLConnection to POST.

Alex Churchill
  • 4,719
  • 4
  • 27
  • 41
18
protected void sendJson(final String play, final String prop) {
     Thread t = new Thread() {
     public void run() {
        Looper.prepare(); //For Preparing Message Pool for the childThread
        HttpClient client = new DefaultHttpClient();
        HttpConnectionParams.setConnectionTimeout(client.getParams(), 1000); //Timeout Limit
        HttpResponse response;
        JSONObject json = new JSONObject();

            try {
                HttpPost post = new HttpPost("http://192.168.0.44:80");
                json.put("play", play);
                json.put("Properties", prop);
                StringEntity se = new StringEntity(json.toString());
                se.setContentType(new BasicHeader(HTTP.CONTENT_TYPE, "application/json"));
                post.setEntity(se);
                response = client.execute(post);

                /*Checking response */
                if (response != null) {
                    InputStream in = response.getEntity().getContent(); //Get the data in the entity
                }

            } catch (Exception e) {
                e.printStackTrace();
                showMessage("Error", "Cannot Estabilish Connection");
            }

            Looper.loop(); //Loop in the message queue
        }
    };
    t.start();
}
Derlin
  • 8,518
  • 2
  • 22
  • 42
Med Elgarnaoui
  • 1,395
  • 13
  • 29
  • 7
    Please consider editing your post to add more explanation about what your code does and why it will solve the problem. An answer that mostly just contains code (even if it's working) usually won't help the OP to understand their problem – Reeno Sep 08 '15 at 14:14
15

Try this code:

HttpClient httpClient = new DefaultHttpClient();

try {
    HttpPost request = new HttpPost("http://yoururl");
    StringEntity params =new StringEntity("details={\"name\":\"myname\",\"age\":\"20\"} ");
    request.addHeader("content-type", "application/json");
    request.addHeader("Accept","application/json");
    request.setEntity(params);
    HttpResponse response = httpClient.execute(request);

    // handle response here...
}catch (Exception ex) {
    // handle exception here
} finally {
    httpClient.getConnectionManager().shutdown();
}
vdenotaris
  • 11,848
  • 23
  • 69
  • 121
Sonu Dhakar
  • 151
  • 1
  • 2
11

I found this question looking for solution about how to send post request from java client to Google Endpoints. Above answers, very likely correct, but not work in case of Google Endpoints.

Solution for Google Endpoints.

  1. Request body must contains only JSON string, not name=value pair.
  2. Content type header must be set to "application/json".

    post("http://localhost:8888/_ah/api/langapi/v1/createLanguage",
                       "{\"language\":\"russian\", \"description\":\"dsfsdfsdfsdfsd\"}");
    
    
    
    public static void post(String url, String json ) throws Exception{
      String charset = "UTF-8"; 
      URLConnection connection = new URL(url).openConnection();
      connection.setDoOutput(true); // Triggers POST.
      connection.setRequestProperty("Accept-Charset", charset);
      connection.setRequestProperty("Content-Type", "application/json;charset=" + charset);
    
      try (OutputStream output = connection.getOutputStream()) {
        output.write(json.getBytes(charset));
      }
    
      InputStream response = connection.getInputStream();
    }
    

    It sure can be done using HttpClient as well.

Enginer
  • 2,399
  • 21
  • 21
yurin
  • 3,512
  • 1
  • 29
  • 29
9

You can use the following code with Apache HTTP:

String payload = "{\"name\": \"myname\", \"age\": \"20\"}";
post.setEntity(new StringEntity(payload, ContentType.APPLICATION_JSON));

response = client.execute(request);

Additionally you can create a json object and put in fields into the object like this

HttpPost post = new HttpPost(URL);
JSONObject payload = new JSONObject();
payload.put("name", "myName");
payload.put("age", "20");
post.setEntity(new StringEntity(payload.toString(), ContentType.APPLICATION_JSON));
TMO
  • 131
  • 3
  • 8
  • key thing is to add ContentType.APPLICATION_JSON otherwise it was not working for me new StringEntity(payload, ContentType.APPLICATION_JSON) – Johnny Cage Feb 19 '20 at 10:34
5

For Java 11 you can use new HTTP client:

 HttpClient client = HttpClient.newHttpClient();
    HttpRequest request = HttpRequest.newBuilder()
        .uri(URI.create("http://localhost/api"))
        .header("Content-Type", "application/json")
        .POST(ofInputStream(() -> getClass().getResourceAsStream(
            "/some-data.json")))
        .build();

    client.sendAsync(request, BodyHandlers.ofString())
        .thenApply(HttpResponse::body)
        .thenAccept(System.out::println)
        .join();

You can use publisher from InputStream, String, File. Converting JSON to the String or IS you can with Jackson.

user3359592
  • 51
  • 1
  • 2
1

Java 8 with apache httpClient 4

CloseableHttpClient client = HttpClientBuilder.create().build();
HttpPost httpPost = new HttpPost("www.site.com");


String json = "details={\"name\":\"myname\",\"age\":\"20\"} ";

        try {
            StringEntity entity = new StringEntity(json);
            httpPost.setEntity(entity);

            // set your POST request headers to accept json contents
            httpPost.setHeader("Accept", "application/json");
            httpPost.setHeader("Content-type", "application/json");

            try {
                // your closeablehttp response
                CloseableHttpResponse response = client.execute(httpPost);

                // print your status code from the response
                System.out.println(response.getStatusLine().getStatusCode());

                // take the response body as a json formatted string 
                String responseJSON = EntityUtils.toString(response.getEntity());

                // convert/parse the json formatted string to a json object
                JSONObject jobj = new JSONObject(responseJSON);

                //print your response body that formatted into json
                System.out.println(jobj);

            } catch (IOException e) {
                e.printStackTrace();
            } catch (JSONException e) {

                e.printStackTrace();
            }

        } catch (UnsupportedEncodingException e) {
            e.printStackTrace();
        }
Dushan
  • 833
  • 9
  • 18
0

I recomend http-request built on apache http api.

HttpRequest<String> httpRequest = HttpRequestBuilder.createPost(yourUri, String.class)
    .responseDeserializer(ResponseDeserializer.ignorableDeserializer()).build();

public void send(){
   ResponseHandler<String> responseHandler = httpRequest.execute("details", yourJsonData);

   int statusCode = responseHandler.getStatusCode();
   String responseContent = responseHandler.orElse(null); // returns Content from response. If content isn't present returns null. 
}

If you want send JSON as request body you can:

  ResponseHandler<String> responseHandler = httpRequest.executeWithBody(yourJsonData);

I higly recomend read documentation before use.

Beno Arakelyan
  • 833
  • 10
  • 20