fix: 修复腾讯混元API签名算法,使用UTC时区和正确的Content-Type

This commit is contained in:
xuan-bot committed 2026-03-07 08:01:23 +08:00
1 parent 01283f1db7
commit bfc9279b7c
1 file changed
+18 -20
@@ -31,6 +31,9 @@ public class HunYuanAiService {
.build();
public String chat(String systemPrompt, String userMessage) {
if (SECRET_ID == null || SECRET_KEY == null) {
return "AI服务未配置,请设置TENCENT_SECRET_ID和TENCENT_SECRET_KEY环境变量。";
}
try {
String response = sendRequest(systemPrompt, userMessage);
return parseResponse(response);
@@ -41,8 +44,11 @@ public class HunYuanAiService {
}
private String sendRequest(String systemPrompt, String userMessage) throws IOException {
String timestamp = String.valueOf(System.currentTimeMillis() / 1000);
String date = new SimpleDateFormat("yyyy-MM-dd").format(new Date(Long.parseLong(timestamp) * 1000));
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
sdf.setTimeZone(TimeZone.getTimeZone("UTC"));
Date now = new Date();
String date = sdf.format(now);
String timestamp = String.valueOf(now.getTime() / 1000);
JSONObject requestBody = new JSONObject();
requestBody.put("Model", "hunyuan-lite");
@@ -65,22 +71,13 @@ public class HunYuanAiService {
String payload = requestBody.toJSONString();
String credential = generateCredential(timestamp, date, payload);
JSONObject headers = new JSONObject();
headers.put("Authorization", credential);
headers.put("Content-Type", "application/json");
headers.put("Host", HOST);
headers.put("X-TC-Action", ACTION);
headers.put("X-TC-Version", VERSION);
headers.put("X-TC-Timestamp", timestamp);
headers.put("X-TC-Region", REGION);
String authorization = generateAuthorization(timestamp, date, payload);
Request request = new Request.Builder()
.url("https://" + HOST)
.post(RequestBody.create(payload, MediaType.parse("application/json")))
.addHeader("Authorization", credential)
.addHeader("Content-Type", "application/json")
.post(RequestBody.create(payload, MediaType.parse("application/json; charset=utf-8")))
.addHeader("Authorization", authorization)
.addHeader("Content-Type", "application/json; charset=utf-8")
.addHeader("Host", HOST)
.addHeader("X-TC-Action", ACTION)
.addHeader("X-TC-Version", VERSION)
@@ -89,19 +86,20 @@ public class HunYuanAiService {
.build();
try (Response response = client.newCall(request).execute()) {
String responseBody = response.body() != null ? response.body().string() : "";
if (!response.isSuccessful()) {
throw new IOException("Unexpected response code: " + response.code());
return "{\"Response\":{\"Error\":{\"Message\":\"HTTP " + response.code() + ": " + responseBody + "\"}}}";
}
return response.body().string();
return responseBody;
}
}
private String generateCredential(String timestamp, String date, String payload) {
private String generateAuthorization(String timestamp, String date, String payload) {
try {
String httpRequestMethod = "POST";
String canonicalUri = "/";
String canonicalQueryString = "";
String canonicalHeaders = "content-type:application/json\nhost:" + HOST + "\n";
String canonicalHeaders = "content-type:application/json; charset=utf-8\nhost:" + HOST + "\n";
String signedHeaders = "content-type;host";
String hashedRequestPayload = sha256Hex(payload);
@@ -131,7 +129,7 @@ public class HunYuanAiService {
"SignedHeaders=" + signedHeaders + ", " +
"Signature=" + signature;
} catch (Exception e) {
throw new RuntimeException("Failed to generate credential", e);
throw new RuntimeException("Failed to generate authorization", e);
}
}