Spring集成Zoho Invoice创建联系人API返回400错误求助
解决Zoho Invoice创建联系人API返回400错误的问题
从你的代码和请求信息来看,问题主要出在请求头的Content-Type设置和请求体的格式处理上,下面是具体的分析和修复方案:
核心问题分析
- Content-Type不匹配:你设置了
multipart/form-data,但Zoho Invoice的Create Contact API要求请求体是JSON格式,对应的Content-Type应该是application/json。 - 请求体格式错误:你当前用
ParameterStringBuilder.getParamsString(params)把Map转成了表单编码的字符串(比如key1=value1&key2=value2),但API需要的是完整的JSON结构体,嵌套的billing_address和shipping_address没法通过普通的键值对Map正确传递。
修复步骤及代码修改
1. 调整请求头的Content-Type
把con.setRequestProperty("Content-Type", "multipart/form-data");改成con.setRequestProperty("Content-Type", "application/json");。
2. 直接发送JSON字符串作为请求体
不需要再用Map来传递参数,直接把你准备好的JSON字符串写入输出流,而不是转成表单格式。
修改后的完整代码示例
import java.io.*; import java.net.HttpURLConnection; import java.net.URL; import java.nio.charset.StandardCharsets; public String processZohoRequest(String apiUrl, String jsonBody, String method, String auth) throws UnsupportedEncodingException, IOException { URL url = new URL(apiUrl); HttpURLConnection con = (HttpURLConnection) url.openConnection(); con.setRequestMethod(method); if (!AppUtility.isEmpty(auth)) { con.setRequestProperty("Authorization", auth); con.setRequestProperty("Content-Type", "application/json"); // 修正Content-Type con.setRequestProperty("X-com-zoho-invoice-organizationid", testZohoOrgId); } if (!AppUtility.isEmpty(jsonBody)) { con.setDoOutput(true); // 直接写入JSON字符串,用UTF-8编码保证兼容性 try (OutputStream os = con.getOutputStream()) { byte[] input = jsonBody.getBytes(StandardCharsets.UTF_8); os.write(input, 0, input.length); } } // 新增错误流处理:400等错误码时,读取错误流获取具体报错信息 int responseCode = con.getResponseCode(); BufferedReader in; if (responseCode >= 200 && responseCode < 300) { in = new BufferedReader(new InputStreamReader(con.getInputStream())); } else { in = new BufferedReader(new InputStreamReader(con.getErrorStream())); } String inputLine; StringBuffer content = new StringBuffer(); while ((inputLine = in.readLine()) != null) { content.append(inputLine); } in.close(); con.disconnect(); return content.toString(); }
3. 调用方式调整
调用这个方法时,直接传入你准备好的JSON字符串(注意替换${address}为实际地址值),而不是Map:
String apiUrl = "https://invoice.zoho.com/api/v3/contacts"; String jsonBody = "{\"contact_name\":\"Jay Panjwanai\",\"company_name\":\"Ozone\",\"billing_address\":{\"attention\":\"Jay \",\"address\":\"实际地址内容\",\"city\":\"INDORE\",\"country\":\"India\",\"phone\":9xxxxxxxxx},\"shipping_address\":{\"attention\":\"Jay\",\"address\":\"实际地址内容\",\"city\":\"INDORE\",\"country\":\"India\",\"phone\":9xxxxxxxxx}}"; String auth = "Bearer 你的AuthToken"; // 注意格式是「Bearer + 空格 + Token」 String result = processZohoRequest(apiUrl, jsonBody, "POST", auth);
额外验证要点
- 确认
X-com-zoho-invoice-organizationid的值是正确的组织ID,这个ID可以在Zoho Invoice的后台设置中找到。 - 确认AuthToken的格式正确,必须包含
Bearer前缀和后续的空格,不要直接传入纯Token字符串。 - 检查JSON字符串是否有语法错误,比如引号是否配对、嵌套结构是否正确,可以用在线JSON校验工具提前验证。
内容的提问来源于stack exchange,提问作者Jayesh Choudhary
相关产品推荐
相关产品推荐

