2012-04-21 40 views
3

我正在为我的Android手机构建一个小应用程序,使用非常基本的REST界面将文本消息转发到网络服务器。Java HttpClient更改内容类型?

我正在使用android 4.0.3 SDK。我使用Django和Django restframework软件包在python中开发了web服务。该设置完全开箱即用。基本上有一个端点接收持有消息信息(sender,body,date)的JSON对象的POST。我已经测试使用cURL使用以下命令的服务:

curl -X POST -H 'Content-Type: application/json' --data '{"sender":"+xxxxxxxx", "body": "test", "send_date":"2011-03-20 16:32:02"}' http://[...]/messages.json

这一切工作正常,我也得到了预期的响应:

{"body": "test", "send_date": "2011-03-20T16:32:02", "id": 25, "sender": "+xxxxxxxxxx"}

现在我成立了Android应用。这是一个简单的BroadcastReceiver子类,包括一个私人的AsyncTask类:

private class httpPost extends AsyncTask<String, Void, JSONObject> { 
    protected JSONObject doInBackground(String... args) { 
     // Create a new HttpClient and Post Header 
     HttpClient httpclient = new DefaultHttpClient(); 
     HttpParams myParams = new BasicHttpParams(); 
     HttpConnectionParams.setConnectionTimeout(myParams, 10000); 
     HttpConnectionParams.setSoTimeout(myParams, 10000); 

     String url = args[0]; 
     String json=args[1];    
     JSONObject JSONResponse = null; 
     InputStream contentStream = null; 
     String resultString = ""; 

     try { 
      HttpPost httppost = new HttpPost(url); 
      httppost.setHeader("Content-Type", "application/json"); 
      httppost.setHeader("Accept", "application/json"); 

      StringEntity se = new StringEntity(json); 
      se.setContentEncoding(new BasicHeader(HTTP.CONTENT_TYPE, "application/json")); 
      httppost.setEntity(se); 

      for (int i=0;i<httppost.getAllHeaders().length;i++) { 
       Log.v("set header", httppost.getAllHeaders()[i].getValue()); 
      } 

      HttpResponse response = httpclient.execute(httppost); 

      // Do some checks to make sure that the request was processed properly 
      Header[] headers = response.getAllHeaders(); 
      HttpEntity entity = response.getEntity(); 
      contentStream = entity.getContent(); 

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

     //convert response to string 
     try{ 
      BufferedReader reader = new BufferedReader(new InputStreamReader(contentStream,"iso-8859-1"),8); 
      StringBuilder sb = new StringBuilder(); 
      String line; 
      while ((line = reader.readLine()) != null) { 
       sb.append(line + "\n"); 
      } 
      contentStream.close(); 
      resultString = sb.toString(); 
     }catch(Exception e){ 
      e.printStackTrace(); 
     } 

     Log.v("log", resultString); 
     return new JSONObject(); 
    } 


} 

正如你看到的,我刚开始熟悉Java和Android的SDK,所以请大家多多包涵。这个设置在我构建的另一个应用程序中实际运行良好,可以将JSON字符串发送到Neo4J Web服务。

问题是,当我通过Android发布消息到我的web服务时,某些时候内容类型从'application/json'变为'application/json,application/json'。在头部循环日志条目仍输出正确的价值观对每个头,然而,Web服务将返回此错误消息:

{"error": "Unsupported media type in request 'application/json, application/json'."}

我百思不得其解,任何帮助是值得欢迎的。

+0

为什么你写两个 “内容类型” 头?一旦与http.setHeader和其他通过实体。也许这是错误的原因。 – SJuan76 2012-04-21 23:12:59

+0

据我了解,第二个(在StringEntity)只是设置实体的解码,并不影响后标题。我已经通过不添加帖子标题来测试。在这种情况下,结束于请求中的标题是标准文本/普通标题。 – Bart 2012-04-21 23:18:03

+1

不是说我确信这一点,但我会尝试没有实体。除此之外,HTTP嗅探器(如wireshark)可以帮助您诊断故障是在客户端还是在服务器中。 – SJuan76 2012-04-21 23:20:27

回答

6

更改此:

StringEntity se = new StringEntity(json); 
se.setContentEncoding(new BasicHeader(HTTP.CONTENT_TYPE, "application/json")); 
httppost.setEntity(se); 

对此只:

httppost.setEntity(new StringEntity(json.toString(), HTTP.UTF_8)); 
+0

感谢队友!这就是我所需要的。 @ SJuan76你是对的,欢呼家伙,非常有帮助! – Bart 2012-04-22 01:14:40

+3

应该是'se.setContentType(new BasicHeader(HTTP.CONTENT_TYPE,“application/json”));' – Danpe 2014-10-12 19:54:20