Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

does Gin has Internationalization support(i18n)? #1382

Closed
zcmiao190 opened this issue Jun 6, 2018 · 10 comments
Closed

does Gin has Internationalization support(i18n)? #1382

zcmiao190 opened this issue Jun 6, 2018 · 10 comments

Comments

@zcmiao190
Copy link

does Gin has Internationalization support(i18n)?

where's the Document or Example.

@syssam
Copy link
Contributor

syssam commented Jun 6, 2018

Gin does not provide i18n, you could find some pacakge here.
https://github.com/avelino/awesome-go

@aceyin
Copy link

aceyin commented Sep 7, 2018

@syssam is there any plan for support i18n in gin framework?

@syssam
Copy link
Contributor

syssam commented Sep 7, 2018

@aceyin you should ask GIN team any plan support i18n.
or you can find i18n package on here.
https://github.com/avelino/awesome-go

I have a validator package support multiple language.
https://github.com/syssam/go-validator
However, it does not fully test.

@thinkerou thinkerou reopened this Sep 7, 2018
@nanom1t
Copy link

nanom1t commented Jan 4, 2019

Hi. Is it possible to use go-i18n(https://github.com/nicksnyder/go-i18n) with Gin? How to use it in templates?

@kataras
Copy link

kataras commented Nov 15, 2019

Hi. Is it possible to use go-i18n(https://github.com/nicksnyder/go-i18n) with Gin? How to use it in templates?

Hello @nanom1t, No, Gin does not support it, however other frameworks like Iris and Beego does support it for a long time now (iris does support it for 2 years+). I will copy-paste some content here so gin contributors can see its usage and hopefully manage to do something like this for gin users as well, all gophers deserves the Iris features:

./locales/en-US.all.yaml

- id: hi
  translation: "hi {{.}}"

a .go file

import "github.com/kataras/iris/v12"
import "github.com/iris-contrib/middleware/go-i18n"
// ...

app := iris.New()
locale := i18n.New(
	"./locales/en-US.all.yaml",
	"./locales/en-US.errors.yaml",
	"./locales/zh-CN.all.yaml",
)

app.Use(locale.Serve)

// Route, use of i18n in a line of `.Translate("key", optionalArguments)`.
app.Get("/", func(ctx iris.Context){
    message := ctx.Translate("hi", "iris")
    ctx.Writef("translated: %s", message )
})

Inside templates you can bind the ctx.Translate method itself.

app.Get("/", func(ctx iris.Context) {
	ctx.View("index.html", iris.Map{
		"tr": ctx.Translate,
	})
	// it will return "hello, iris"
	// when {{call .tr "hi" "iris"}}
})
{{call .tr "hi" "iris"}}

The full source code is located at: iris-contrib/middleare/go-i18n.

@appleboy
Copy link
Member

maybe we can create new middleware in https://github.com/gin-contrib

@cayter
Copy link

cayter commented Nov 24, 2019

I'm currently using gin to build a web framework for my own use case which comes with i18n middleware that uses https://github.com/nicksnyder/go-i18n/v2/i18n underneath. Hope that helps to give some reference on how to port it into https://github.com/gin-contrib.

@thinkerou
Copy link
Member

please commit pr to https://github.com/gin-contrib/i18n thanks!

@suisrc
Copy link

suisrc commented Aug 8, 2020

middleware

package middleware

import (
	"github.com/gin-gonic/gin"
	"github.com/nicksnyder/go-i18n/v2/i18n"
	"github.com/suisrc/zgo/modules/helper"
)

// I18nMiddleware 国际化
func I18nMiddleware() gin.HandlerFunc {
	bundle := i18n.NewBundle(language.Chinese)
	bundle.RegisterUnmarshalFunc("toml", toml.Unmarshal)
	bundle.LoadMessageFile("locales/active.zh-CN.toml")
	bundle.LoadMessageFile("locales/active.en-US.toml")

	return func(c *gin.Context) {
		lang := c.Request.FormValue("lang")
		accept := c.Request.Header.Get("Accept-Language")
		localizer := i18n.NewLocalizer(bundle, lang, accept)
		helper.SetI18n(c, localizer)

		c.Next()
	}
}

helper

package helper

import (
	"errors"
	"strconv"
	"strings"

	"github.com/gin-gonic/gin"
	"github.com/nicksnyder/go-i18n/v2/i18n"
)

// 定义上下文中的键
const (
	ResI18nKey = Prefix + "/res-i18n"
)

// FormatMessage fm
func FormatMessage(c *gin.Context, lc *i18n.LocalizeConfig) string {
	return MustI18n(c).MustLocalize(lc)
}

// FormatText ft
func FormatText(c *gin.Context, message *i18n.Message) string {
	return FormatCode(c, message, nil)
}

// FormatCode fc
func FormatCode(c *gin.Context, message *i18n.Message, args map[string]interface{}) string {
	if localizer, ok := GetI18n(c); ok {
		return localizer.MustLocalize(&i18n.LocalizeConfig{
			DefaultMessage: message,
			TemplateData:   args,
		})
	}
	// 加载i18n中间件后,不会进入该分支,简单处理未加载i18n中间件时候的处理内容
	if args == nil {
		return message.Other
	}
	text := message.Other
	for key, val := range args {
		text = strings.ReplaceAll(text, "{{."+key+"}}", toString(val))
	}
	return text
}

// MustI18n i18n
func MustI18n(c *gin.Context) *i18n.Localizer {
	localizer, ok := GetI18n(c)
	if !ok {
		panic(errors.New("context no has i18n localizer"))
	}
	return localizer
}

// GetI18n i18n
func GetI18n(c *gin.Context) (*i18n.Localizer, bool) {
	if v, ok := c.Get(ResI18nKey); ok {
		if l, b := v.(*i18n.Localizer); b {
			return l, true
		}
	}
	return nil, false
}

// SetI18n i18n
func SetI18n(c *gin.Context, l *i18n.Localizer) {
	c.Set(ResI18nKey, l)
}

// ToString to string
func toString(a interface{}) string {
	switch a.(type) {
	case int:
		return strconv.Itoa(a.(int))
	case bool:
		return strconv.FormatBool(a.(bool))
	case string:
		return a.(string)
	default:
		return "conver error"
	}
}

使用

message := helper.FormatText(c, &i18n.Message{ID: "service.signin.select-role-text", Other: "请选择角色"}

@suisrc
Copy link

suisrc commented Aug 13, 2020

我将项目中的中间件抽出, 希望可以帮助到大家, suisrc/gin-i18n

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

9 participants