| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241 |
- package google
- import (
- "context"
- "fmt"
- "io"
- "net/http"
- "net/url"
- "strconv"
- "strings"
- "bet24.com/servers/adminserver/config"
- "bet24.com/utils"
- "bet24.com/log"
- "cloud.google.com/go/translate"
- "golang.org/x/text/language"
- "google.golang.org/api/option"
- )
- // 是否翻译
- func IsTranslate() (bool, string) {
- googleJson := config.Server.GOOGLE_APPLICATION_CREDENTIALS
- if googleJson == "" {
- // log.Debug("google翻译未配置 json 文件")
- return false, "google翻译未配置 json 文件"
- }
- return true, googleJson
- }
- func Translate(sourceLanguage, targetLanguage, text string) (string, error) {
- utils.SetMinTraceTime(1000)
- defer utils.TimeCost(fmt.Sprintf("google.Translate sourceLanguage=%s targetLanguage=%s text==>%s ",
- sourceLanguage,
- targetLanguage,
- text))()
- ok, googleJson := IsTranslate()
- if !ok {
- return "", fmt.Errorf(googleJson)
- }
- if _, err := strconv.ParseFloat(text, 64); err == nil {
- // log.Debug(fmt.Sprintf("Google Translate 纯数字无需翻译 ==> %s", text))
- return "", err
- }
- ctx := context.Background()
- // sourceLang, err := language.Parse(sourceLanguage)
- // if err != nil {
- // return "", fmt.Errorf("%s source language.Parse: %v", sourceLanguage, err)
- // }
- tarLang, err := language.Parse(targetLanguage)
- if err != nil {
- log.Error("%s target language.Parse: %v", targetLanguage, err)
- return "", fmt.Errorf("%s target language.Parse: %v", targetLanguage, err)
- }
- // log.Debug("google.Translate ==> sourceLanguage=%+v targetLanguage=%+v text==>%s ",
- // sourceLang,
- // tarLang,
- // text)
- client, err := translate.NewClient(ctx, option.WithCredentialsFile(googleJson))
- if err != nil {
- log.Error("google.Translate NewClient err = %+v", err)
- return "", err
- }
- defer client.Close()
- // resp, err := client.Translate(ctx, []string{text}, tarLang, &translate.Options{
- // Source: sourceLang,
- // Format: translate.Text,
- // })
- resp, err := client.Translate(ctx, []string{text}, tarLang, nil)
- if err != nil {
- log.Error("google.Translate Translate resp=%+v err=%+v", resp, err)
- return "", fmt.Errorf("Translate: %v", err)
- }
- if len(resp) == 0 {
- log.Error("google.Translate Translate resp=%+v", resp)
- return "", fmt.Errorf("Translate returned empty response to text: %s", text)
- }
- // log.Debug("google.Translate ==> Translate sourceLanguage=%s targetLanguage=%s resp=%+v err=%+v",
- // sourceLanguage, targetLanguage, resp, err)
- return resp[0].Text, nil
- }
- func TranslateTextWithModel(targetLanguage, text, model string) (string, error) {
- // targetLanguage := "ja"
- // text := "The Go Gopher is cute"
- // model := "nmt"
- utils.SetMinTraceTime(1000)
- defer utils.TimeCost(fmt.Sprintf("google.Translate targetLanguage=%s model=%s text==>%s ",
- targetLanguage,
- model,
- text))()
- ok, googleJson := IsTranslate()
- if !ok {
- return "", fmt.Errorf(googleJson)
- }
- if _, err := strconv.ParseFloat(text, 64); err == nil {
- // log.Debug(fmt.Sprintf("Google Translate 纯数字无需翻译 ==> %s", text))
- return "", err
- }
- ctx := context.Background()
- lang, err := language.Parse(targetLanguage)
- if err != nil {
- return "", fmt.Errorf("language.Parse: %v", err)
- }
- log.Debug("google.TranslateTextWithModel ==> targetLanguage=%+v model=%s text==>%s ",
- targetLanguage,
- model,
- text)
- client, err := translate.NewClient(ctx, option.WithCredentialsFile(googleJson))
- if err != nil {
- return "", fmt.Errorf("translate.NewClient: %v", err)
- }
- defer client.Close()
- resp, err := client.Translate(ctx, []string{text}, lang, &translate.Options{
- Model: "base", // Either "nmt" or "base".
- })
- if err != nil {
- return "", fmt.Errorf("Translate: %v", err)
- }
- if len(resp) == 0 {
- return "", nil
- }
- log.Debug("google.TranslateTextWithModel ==> Translate targetLanguage=%s model=%s resp=%+v err=%+v",
- targetLanguage, model, resp, err)
- return resp[0].Text, nil
- }
- func DetectLanguage(text string) (*translate.Detection, error) {
- // text := "こんにちは世界"
- ok, googleJson := IsTranslate()
- if !ok {
- return nil, fmt.Errorf(googleJson)
- }
- ctx := context.Background()
- client, err := translate.NewClient(ctx, option.WithCredentialsFile(googleJson))
- if err != nil {
- return nil, fmt.Errorf("translate.NewClient: %v", err)
- }
- defer client.Close()
- lang, err := client.DetectLanguage(ctx, []string{text})
- if err != nil {
- return nil, fmt.Errorf("DetectLanguage: %v", err)
- }
- if len(lang) == 0 || len(lang[0]) == 0 {
- return nil, fmt.Errorf("DetectLanguage return value empty")
- }
- log.Debug("google.DetectLanguage ==> lang = %+v", lang)
- return &lang[0][0], nil
- }
- // Google 翻译API
- // url GET https://translate.googleapis.com/translate_a/single
- // client url-query 默认值(不要修改) gtx
- // sl url-query 来源语言 en zh-cn 语言代码如下
- // tl url-query 目标语言 en zh-cn 语言代码如下
- // dt url-query 默认值(不要修改) t
- // q u rl-query 翻译的文本 建议先url-encode
- func TranslateFree(sl, tl, text string) (string, error) {
- if _, err := strconv.ParseFloat(text, 64); err == nil {
- // log.Debug(fmt.Sprintf("Google Translate 纯数字无需翻译 ==> %s", text))
- return "", err
- }
- // log.Debug("全角:%s", text)
- text = DBC2SBC(text)
- // log.Debug("半角:%s", text)
- url := fmt.Sprintf("https://translate.googleapis.com/translate_a/single?client=gtx&sl=%s&tl=%s&dt=t&q=%s",
- sl, tl, url.QueryEscape(text))
- resp, err := http.Get(url)
- if err != nil {
- return "", err
- }
- defer resp.Body.Close()
- if err != nil {
- return "", err
- }
- bs, err := io.ReadAll(resp.Body)
- if err != nil {
- return "", err
- }
- // 返回的json反序列化比较麻烦, 直接字符串拆解
- ss := string(bs)
- if strings.HasPrefix(ss, "<!DOCTYPE") {
- return "", err
- }
- ss = strings.ReplaceAll(ss, "[", "")
- ss = strings.ReplaceAll(ss, "]", "")
- ss = strings.ReplaceAll(ss, "null,", "")
- ss = strings.Trim(ss, `"`)
- ps := strings.Split(ss, `","`)
- log.Debug("google.Translate 原文:%s 译文:%s", text, ps[0])
- return ps[0], nil
- }
- // 全角转半角
- func DBC2SBC(s string) string {
- var strLst []string
- for _, i := range s {
- insideCode := i
- if insideCode == 12288 {
- insideCode = 32
- } else {
- insideCode -= 65248
- }
- if insideCode < 32 || insideCode > 126 {
- strLst = append(strLst, string(i))
- } else {
- strLst = append(strLst, string(insideCode))
- }
- }
- return strings.Join(strLst, "")
- }
|