i18n.go 1.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990
  1. package i18n
  2. import (
  3. "context"
  4. _ "embed"
  5. "encoding/json"
  6. "fmt"
  7. "sync"
  8. "git.dmitriygnatenko.ru/dima/go-common/logger"
  9. )
  10. //go:embed ru.json
  11. var ruJsonContent []byte
  12. //go:embed en.json
  13. var enJsonContent []byte
  14. type Language string
  15. const (
  16. Ru Language = "ru"
  17. En Language = "en"
  18. Default Language = Ru
  19. LangParam = "lang"
  20. )
  21. var (
  22. once sync.Once
  23. i18n *I18n
  24. )
  25. type I18n struct {
  26. translations map[Language]map[string]string
  27. }
  28. func Init() error {
  29. var err error
  30. once.Do(func() {
  31. ruTranslations := make(map[string]string)
  32. enTranslations := make(map[string]string)
  33. err = json.Unmarshal(ruJsonContent, &ruTranslations)
  34. if err != nil {
  35. return
  36. }
  37. err = json.Unmarshal(enJsonContent, &enTranslations)
  38. if err != nil {
  39. return
  40. }
  41. i18n = &I18n{translations: map[Language]map[string]string{
  42. Ru: ruTranslations,
  43. En: enTranslations,
  44. }}
  45. })
  46. return err
  47. }
  48. func T(lang Language, key string, args ...any) string {
  49. if i18n == nil {
  50. logger.Error(context.Background(), "i18n not initialized")
  51. return ""
  52. }
  53. if i18n.translations[lang] == nil {
  54. logger.Warnf(context.Background(), "i18n: language %s not initialized", lang)
  55. return ""
  56. }
  57. var translated string
  58. if len(args) == 0 {
  59. translated = i18n.translations[lang][key]
  60. } else {
  61. translated = fmt.Sprintf(i18n.translations[lang][key], args...)
  62. }
  63. if len(translated) == 0 {
  64. logger.Warnf(
  65. context.Background(),
  66. "i18n: language %s translation %s is not found", lang, key,
  67. )
  68. }
  69. return translated
  70. }