我在我的客户端使用Apache HTTP Client libs和Jackson.当我将
JSON发布到服务器时,我收到错误:
org.codehaus.jackson.JsonParseException: Invalid UTF-8 middle byte 0x65
at [Source: HttpInputOverHTTP@22a4ac95; line: 1, column: 81]
如果我没有设置任何标题而不是我获得无效的媒体类型,这是有道理的.
如果我使用curl和相同的标题,服务器接受它,所以我认为服务器是好的(只是巧合,它也使用杰克逊)
这些是文件;我只使用8位字符将其硬编码为Java文字,以避免任何其他地方发生错位
// "Stra\u00DFe" = "Straße"
static String TINY_UTF8_DOC = "[{ \"id\" : \"2\", \"fields\" : { \"subject\" : [{ \"name\" : \"subject\", \"value\" : \"Stra\u00DFe\" }] } }]";
这是我一直在使用的代码,以及各种尝试的评论:
HttpClient httpClient = new DefaultHttpClient();
HttpPost post = new HttpPost( url );
// Attempt A
// post.setEntity( new StringEntity( content ) );
// Attempt B
// post.setEntity( new StringEntity( content ) );
// post.setHeader("Content-Type", "application/json; charset=utf-8");
// Attempt C
// post.setEntity( new StringEntity( content, ContentType.create("application/json") ) );
// Attempt D
// post.setEntity( new StringEntity( content, ContentType.create("application/json; charset=UTF-8") ) );
// Attempt F
// post.setEntity( new StringEntity( content, ContentType.create("application/json; charset=utf-8") ) );
// Attempt G
// StringEntity params = new StringEntity( content );
// params.setContentType("application/json; charset=UTF-8");
// post.setEntity(params);
// And then send to server
HttpResponse response = httpClient.execute( post );
int code = response.getStatusLine().getStatusCode();
// ...etc...
我注意到的其他奇怪的事情:
>有一段时间,Mac上的Eclipse与在Linux上运行.jar的行为不同;显然这是特定于平台的编码或解码的症状,但我不知道在哪里.具有讽刺意味的是,当我设置Eclipse将代码视为UTF-8(对比ASCII)时,我怀疑这是一个重要的线索,但不确定它适合的位置.
>我已经看过时间而不是2个字节,流中有4个字节,虽然这在编写磁盘时可能是一个不同的编码问题,尽管我在文件IO上专门设置了UTF-8
>当我查看调试器中的字符串实体时,我看到了字节,但是8位字符是负数.当你运行Two’s Compliment数学时,它仍然是正确的Unicode代码点,因此名义上可以,假设httpclient没有错误.
真的没有想法,正如我所说,它适用于curl,所以我认为服务器没问题.
编辑:
curl在发布到服务器时有效,但我无法共享服务器代码.有人指出,由于curl不是用Java编写的,所以可能它的行为方式不同,因此服务器代码仍然可疑.
因此,作为进一步的测试,下面的代码不使用Apache httpclient库,并且在发布到服务器时DOES工作.这证明服务器很好,而且我在客户端使用Apache库的方式仍然有问题(或者它可能是错误的).
非apache-httpclient代码,它可以工作:
import java.io.OutputStream;
import java.io.OutputStreamWriter;
import java.net.HttpURLConnection;
import java.net.URL;
class PostUtf8 {
static String POST_URL = "http://...";
// \u00DF = LATIN SMALL LETTER SHARP S, looks like letter B
static String TINY_UTF8_DOC = "[{ \"id\" : \"2\", \"fields\" : { \"subject\" : [{ \"name\" : \"subject\", \"value\" : \"Stra\u00DFe\" }] } }]";
public static void main( String [] args ) throws Exception {
System.out.println( "Posting to " + POST_URL );
URL url = new URL( POST_URL );
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setRequestProperty( "Content-Type", "application/json; charset=UTF-8" );
conn.setRequestMethod("POST");
conn.setDoOutput(true);
OutputStream sout = conn.getOutputStream();
OutputStreamWriter wout = new OutputStreamWriter(sout, "UTF-8" );
wout.write( TINY_UTF8_DOC );
wout.flush();
int result = conn.getResponseCode();
System.out.println( "Result = " + result );
}
}