5 changed files with 260 additions and 11 deletions
@ -0,0 +1,211 @@ |
|||||
|
package com.bx.implatform.util; |
||||
|
|
||||
|
import cn.hutool.crypto.digest.DigestUtil; |
||||
|
import cn.hutool.http.HttpRequest; |
||||
|
import cn.hutool.http.HttpResponse; |
||||
|
import cn.hutool.json.JSONArray; |
||||
|
import cn.hutool.json.JSONObject; |
||||
|
import cn.hutool.json.JSONUtil; |
||||
|
import com.bx.implatform.entity.ImSetting; |
||||
|
import com.bx.implatform.entity.setting.domain.TranslationSetting; |
||||
|
import com.bx.implatform.enums.SettingEnum; |
||||
|
import com.bx.implatform.service.IImSettingService; |
||||
|
import lombok.RequiredArgsConstructor; |
||||
|
import lombok.extern.slf4j.Slf4j; |
||||
|
import org.springframework.stereotype.Component; |
||||
|
|
||||
|
/** |
||||
|
* 有道翻译工具类 |
||||
|
*/ |
||||
|
@Slf4j |
||||
|
@Component |
||||
|
@RequiredArgsConstructor |
||||
|
public class YouDaoTranslationUtils { |
||||
|
|
||||
|
/** |
||||
|
* 有道翻译API地址 |
||||
|
*/ |
||||
|
private static final String YouDao_URL = "https://openapi.youdao.com/api"; |
||||
|
|
||||
|
/** |
||||
|
* 有道翻译APPID |
||||
|
*/ |
||||
|
private static final String APP_KEY = "20311d34bea5d593"; |
||||
|
|
||||
|
/** |
||||
|
* 有道翻译密钥 |
||||
|
*/ |
||||
|
private static final String APP_SECRET = "n1XjfaBApp9xed8YnmVNLaOlBqhEB6Wq"; |
||||
|
|
||||
|
private final IImSettingService settingService; |
||||
|
|
||||
|
/** |
||||
|
* 翻译文本 |
||||
|
* |
||||
|
* @param query 待翻译文本 |
||||
|
* @param from 源语言 |
||||
|
* @param to 目标语言 |
||||
|
* @return 翻译结果 |
||||
|
*/ |
||||
|
public String translate(String query, String from, String to) { |
||||
|
try { |
||||
|
// 生成随机数
|
||||
|
String salt = String.valueOf(System.currentTimeMillis()); |
||||
|
|
||||
|
// 生成当前时间戳
|
||||
|
String curtime = String.valueOf(System.currentTimeMillis() / 1000); |
||||
|
|
||||
|
// 生成签名:appKey + truncate(q) + salt + curtime + appSecret的SHA256值
|
||||
|
String signStr = APP_KEY + truncate(query) + salt + curtime + APP_SECRET; |
||||
|
String sign = DigestUtil.sha256Hex(signStr); |
||||
|
|
||||
|
// 发送请求
|
||||
|
HttpResponse response = HttpRequest.post(YouDao_URL) |
||||
|
.form("q", query) |
||||
|
.form("from", from) |
||||
|
.form("to", to) |
||||
|
.form("appKey", APP_KEY) |
||||
|
.form("salt", salt) |
||||
|
.form("sign", sign) |
||||
|
.form("signType", "v3") |
||||
|
.form("curtime", curtime) |
||||
|
.execute(); |
||||
|
|
||||
|
// 解析响应
|
||||
|
String body = response.body(); |
||||
|
JSONObject result = JSONUtil.parseObj(body); |
||||
|
|
||||
|
// 检查是否有错误
|
||||
|
if (result.containsKey("errorCode") && result.getStr("errorCode").equals("0")) { |
||||
|
log.error("有道翻译失败,错误码:{},错误信息:{}", result.getStr("errorCode"), result.getStr("errorMsg")); |
||||
|
return result.getStr("errorMsg") == null ? "system error" : "system error:" + result.getStr("errorMsg"); |
||||
|
} |
||||
|
|
||||
|
// 获取翻译结果
|
||||
|
JSONArray translationArray = result.getJSONArray("translation"); |
||||
|
if (translationArray == null || translationArray.isEmpty()) { |
||||
|
log.error("有道翻译结果为空"); |
||||
|
return "result empty"; |
||||
|
} |
||||
|
|
||||
|
// 返回第一条翻译结果
|
||||
|
return translationArray.getStr(0); |
||||
|
} catch (Exception e) { |
||||
|
log.error("有道翻译异常", e); |
||||
|
return "translation unknown error"; |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* 翻译文本(自动检测源语言) |
||||
|
* |
||||
|
* @param query 待翻译文本 |
||||
|
* @param to 目标语言 |
||||
|
* @return 翻译结果 |
||||
|
*/ |
||||
|
public String translate(String query, String to) { |
||||
|
return translate(query, "auto", to); |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* 翻译文本 |
||||
|
* |
||||
|
* @param query 待翻译文本 |
||||
|
* @param from 源语言 |
||||
|
* @param to 目标语言 |
||||
|
* @return 翻译结果 |
||||
|
*/ |
||||
|
public String translateByAgentConfiguration(String query, String from, String to) { |
||||
|
try { |
||||
|
|
||||
|
ImSetting setting = settingService.getByTokenAndSettingName(SettingEnum.TRANSLATION_SETTING.name()); |
||||
|
TranslationSetting configuration = JSONUtil.toBean(setting.getSettingValue(), TranslationSetting.class); |
||||
|
|
||||
|
//转化语言标识
|
||||
|
to = convertTo(to); |
||||
|
|
||||
|
// 生成随机数
|
||||
|
String salt = String.valueOf(System.currentTimeMillis()); |
||||
|
|
||||
|
// 生成当前时间戳
|
||||
|
String curtime = String.valueOf(System.currentTimeMillis() / 1000); |
||||
|
|
||||
|
// 生成签名:appKey + truncate(q) + salt + curtime + appSecret的SHA256值
|
||||
|
String signStr = configuration.getAppKey() + truncate(query) + salt + curtime + configuration.getAppSecret(); |
||||
|
String sign = DigestUtil.sha256Hex(signStr); |
||||
|
|
||||
|
// 发送请求
|
||||
|
HttpResponse response = HttpRequest.post(YouDao_URL) |
||||
|
.form("q", query) |
||||
|
.form("from", from) |
||||
|
.form("to", to) |
||||
|
.form("appKey", configuration.getAppKey()) |
||||
|
.form("salt", salt) |
||||
|
.form("sign", sign) |
||||
|
.form("signType", "v3") |
||||
|
.form("curtime", curtime) |
||||
|
.execute(); |
||||
|
|
||||
|
// 解析响应
|
||||
|
String body = response.body(); |
||||
|
JSONObject result = JSONUtil.parseObj(body); |
||||
|
|
||||
|
// 检查是否有错误
|
||||
|
if (result.containsKey("errorCode") &&!result.getStr("errorCode").equals("0")) { |
||||
|
System.out.println(result); |
||||
|
log.error("有道翻译失败,错误码:{},错误信息:{}", result.getStr("errorCode"), result.getStr("errorMsg")); |
||||
|
return result.getStr("errorMsg") == null ? "system error" : "system error:" + result.getStr("errorMsg"); |
||||
|
} |
||||
|
System.out.println(result); |
||||
|
// 获取翻译结果
|
||||
|
JSONArray translationArray = result.getJSONArray("translation"); |
||||
|
if (translationArray == null || translationArray.isEmpty()) { |
||||
|
log.error("有道翻译结果为空"); |
||||
|
return "result empty"; |
||||
|
} |
||||
|
|
||||
|
// 返回第一条翻译结果
|
||||
|
return translationArray.getStr(0); |
||||
|
} catch (Exception e) { |
||||
|
log.error("有道翻译异常", e); |
||||
|
return "translation unknown error"; |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* 翻译文本(自动检测源语言) |
||||
|
* |
||||
|
* @param query 待翻译文本 |
||||
|
* @param to 目标语言 |
||||
|
* @return 翻译结果 |
||||
|
*/ |
||||
|
public String translateByAgentConfiguration(String query, String to) { |
||||
|
return translateByAgentConfiguration(query, "auto", to); |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* 截断字符串用于生成签名 |
||||
|
* |
||||
|
* @param q 待截断的字符串 |
||||
|
* @return 截断后的字符串 |
||||
|
*/ |
||||
|
private String truncate(String q) { |
||||
|
if (q == null) { |
||||
|
return null; |
||||
|
} |
||||
|
int len = q.length(); |
||||
|
return len <= 20 ? q : (q.substring(0, 10) + len + q.substring(len - 10, len)); |
||||
|
} |
||||
|
|
||||
|
//转化to
|
||||
|
private String convertTo(String to) { |
||||
|
return switch (to) { |
||||
|
case "jp" -> "ja"; |
||||
|
case "kor" -> "ko"; |
||||
|
case "vie" -> "vi"; |
||||
|
case "fra" -> "fr"; |
||||
|
case "ara" -> "ar"; |
||||
|
default -> to; |
||||
|
}; |
||||
|
} |
||||
|
} |
||||
Loading…
Reference in new issue