在Java中使用JSON进行HTTP POST


187

我想在Java中使用JSON进行简单的HTTP POST。

假设网址是 www.site.com

并采用{"name":"myname","age":"20"}标记'details'为例如的值。

我将如何为POST创建语法?

我似乎也无法在JSON Javadocs中找到POST方法。

Answers:


167

这是您需要做的:

  1. 获取Apache HttpClient,这将使您能够发出所需的请求
  2. 使用它创建一个HttpPost请求,并添加标题“ application / x-www-form-urlencoded”
  3. 创建一个StringEntity,将JSON传递给它
  4. 执行通话

代码大致看起来像(您仍然需要对其进行调试并使之正常工作)

//Deprecated
//HttpClient httpClient = new DefaultHttpClient(); 

HttpClient httpClient = HttpClientBuilder.create().build(); //Use this instead 

try {

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

    //handle response here...

}catch (Exception ex) {

    //handle exception here

} finally {
    //Deprecated
    //httpClient.getConnectionManager().shutdown(); 
}

9
您可以但将其抽象为JSONObject始终是一个好习惯,就像您直接在字符串中执行操作一样,您可能会错误地对字符串进行编程并导致语法错误。通过使用JSONObject,您可以确保序列化始终遵循正确的JSON结构
momo

3
原则上,它们都只是在传输数据。唯一的区别是您在服务器中的处理方式。如果只有几个键/值对,那么普通的POST参数(具有key1 = value1,key2 = value2等)可能就足够了,但是一旦您的数据变得更加复杂,尤其是包含复杂结构(嵌套对象,数组),则需要开始考虑使用JSON。使用键值对发送复杂的结构非常麻烦,并且很难在服务器上进行解析(您可以尝试一下,马上就会看到它)。仍然记得那天我们不得不这样做的日子..那不是很好..
momo

1
乐意效劳!如果这是您想要的,则应接受答案,以便其他有类似问题的人都能很好地引导他们提出问题。您可以在答案上使用复选标记。如果您还有其他问题,请与我们联系
momo

12
内容类型不应为“ application / json”。“ application / x-www-form-urlencoded”表示该字符串的格式将类似于查询字符串。NM我看你做了什么,你把json blob当作一个属性的值。
马修·沃德

1
不推荐使用的部分应该使用CloseableHttpClient替换,它为您提供了.close()-方法。请参阅stackoverflow.com/a/20713689/1484047
Frame91 2013年

91

您可以利用Gson库将Java类转换为JSON对象。

根据上面的示例为要发送的变量创建一个pojo类

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

变成

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

一旦在pojo1类中设置了变量,就可以使用以下代码发送该变量

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);

这些是进口

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;

对于GSON

import com.google.gson.Gson;

1
嗨,您如何创建您的httpClient对象?这是一个界面
user3290180,2016年

1
是的,那是一个接口。您可以使用“ HttpClient httpClient = new DefaultHttpClient();”创建实例。
Prakash

2
现在已弃用,我们必须使用HttpClient httpClient = HttpClientBuilder.create()。build();
user3290180

5
如何导入HttpClientBuilder?
Esterlinkof

3
我发现使用StringUtils构造函数上的ContentType参数并传递ContentType.APPLICATION_JSON稍微好一些,而不是手动设置标头。
TownCube

47

@momo对于Apache HttpClient 4.3.1版或更高版本的答案。我JSON-Java用来构建我的JSON对象:

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();
}

20

使用HttpURLConnection可能是最简单的。

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

您将使用JSONObject或其他方法构造JSON,但不使用网络。您需要对其进行序列化,然后将其传递给HttpURLConnection进行POST。


JSONObject j =新的JSONObject(); j.put(“ name”,“ myname”); j.put(“ age”,“ 20”); 像那样?我如何序列化它?
asdf007 2011年

@ asdf007只需使用j.toString()
亚历克斯·丘吉尔

是的,此连接正在阻塞。如果您要发送POST,这可能没什么大不了的;如果您运行Web服务器,则更为重要。
亚历克斯·丘吉尔

HttpURLConnection链接已死。
Tobias Roland 2015年

你可以发布示例如何将json发布到正文吗?

15
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();
}

7
请考虑编辑您的帖子,以添加更多有关代码功能以及为什么它可以解决问题的解释。通常只包含代码(即使它可以正常工作)的答案通常不会帮助OP理解他们的问题
Reeno 2015年

14

试试这个代码:

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();
}

谢谢!只有您的答案解决了编码问题:)
Shrikant 2015年

@SonuDhakar为什么application/json同时将其作为接受标头和内容类型进行发送
Kasun Siyambalapitiya

似乎DefaultHttpClient已弃用。
sdgfsdh

11

我发现此问题正在寻找有关如何将发帖请求从Java客户端发送到Google端点的解决方案。以上答案很可能是正确的,但对于Google Endpoints而言无效。

Google端点解决方案。

  1. 请求正文必须仅包含JSON字符串,而不能包含name = value对。
  2. 内容类型标头必须设置为“ 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();
    }

    当然也可以使用HttpClient完成。


8

您可以将以下代码用于Apache HTTP:

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

response = client.execute(request);

另外,您可以创建一个json对象,并像这样将字段放入对象

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));

关键是添加ContentType.APPLICATION_JSON否则对我不起作用新的StringEntity(payload,ContentType.APPLICATION_JSON)
Johnny Cage

2

对于Java 11,您可以使用新的HTTP客户端

 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();

您可以通过InputStream,String,File使用发布者。使用Jackson可以将JSON转换为String或IS。


1

带有Apache httpClient 4的Java 8

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();
        }

0

我建议基于apache http api构建的http-request

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. 
}

如果要发送JSON请求正文,您可以:

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

我强烈建议在使用前阅读文档。


您为什么在上述答案中建议最多?
杰里尔·库克

因为使用响应进行操作非常简单。
Beno Arakelyan
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.