Detect translations in low-level structs

This patch adds .IsTranslated(), .IsTranslatedN() and related functions
to following objects:
- Translation
- Domain

This makes it possible to detect whether a string is translatable or not
during runtime.
This commit is contained in:
Matyas Horky 2023-04-04 18:10:33 +02:00
parent 4ce6b50c65
commit 8941f8bb1c
3 changed files with 110 additions and 1 deletions

View file

@ -402,7 +402,51 @@ func (do *Domain) GetNC(str, plural string, n int, ctx string, vars ...interface
return Printf(plural, vars...)
}
//GetTranslations returns a copy of every translation in the domain. It does not support contexts.
// IsTranslated reports whether a string is translated
func (do *Domain) IsTranslated(str string) bool {
return do.IsTranslatedN(str, 0)
}
// IsTranslatedN reports whether a plural string is translated
func (do *Domain) IsTranslatedN(str string, n int) bool {
do.trMutex.RLock()
defer do.trMutex.RUnlock()
if do.translations == nil {
return false
}
tr, ok := do.translations[str]
if !ok {
return false
}
return tr.IsTranslatedN(n)
}
// IsTranslatedC reports whether a context string is translated
func (do *Domain) IsTranslatedC(str, ctx string) bool {
return do.IsTranslatedNC(str, 0, ctx)
}
// IsTranslatedNC reports whether a plural context string is translated
func (do *Domain) IsTranslatedNC(str string, n int, ctx string) bool {
do.trMutex.RLock()
defer do.trMutex.RUnlock()
if do.contextTranslations == nil {
return false
}
translations, ok := do.contextTranslations[ctx]
if !ok {
return false
}
tr, ok := translations[str]
if !ok {
return false
}
return tr.IsTranslatedN(n)
}
// GetTranslations returns a copy of every translation in the domain. It does not support contexts.
func (do *Domain) GetTranslations() map[string]*Translation {
all := make(map[string]*Translation, len(do.translations))

View file

@ -6,6 +6,7 @@ import (
const (
enUSFixture = "fixtures/en_US/default.po"
arFixture = "fixtures/ar/categories.po"
)
//since both Po and Mo just pass-through to Domain for MarshalBinary and UnmarshalBinary, test it here
@ -72,6 +73,58 @@ func TestDomain_GetTranslations(t *testing.T) {
}
}
func TestDomain_IsTranslated(t *testing.T) {
englishPo := NewPo()
englishPo.ParseFile(enUSFixture)
english := englishPo.GetDomain()
// singular and plural
if english.IsTranslated("My Text") {
t.Error("'My text' should be reported as translated.")
}
if english.IsTranslated("Another string") {
t.Error("'Another string' should be reported as not translated.")
}
if !english.IsTranslatedN("Empty plural form singular", 0) {
t.Error("'Empty plural form singular' should be reported as translated for n=0.")
}
if english.IsTranslatedN("Empty plural form singular", 1) {
t.Error("'Empty plural form singular' should be reported as not translated for n=1.")
}
arabicPo := NewPo()
arabicPo.ParseFile(arFixture)
arabic := arabicPo.GetDomain()
// multiple plurals
if !arabic.IsTranslated("Load %d more document") {
t.Error("Arabic singular should be reported as translated.")
}
if !arabic.IsTranslatedN("Load %d more document", 0) {
t.Error("Arabic plural should be reported as translated for n=0.")
}
if !arabic.IsTranslatedN("Load %d more document", 1) {
t.Error("Arabic plural should be reported as translated for n=1.")
}
if !arabic.IsTranslatedN("Load %d more document", 5) {
t.Error("Arabic plural should be reported as translated for n=5.")
}
if arabic.IsTranslatedN("Load %d more document", 6) {
t.Error("Arabic plural should be reported as not translated for n=6.")
}
// context
if !english.IsTranslatedC("One with var: %s", "Ctx") {
t.Error("Context singular should be reported as translated.")
}
if !english.IsTranslatedNC("One with var: %s", 0, "Ctx") {
t.Error("Context plural should be reported as translated for n=0")
}
if english.IsTranslatedNC("One with var: %s", 2, "Ctx") {
t.Error("Context plural should be reported as translated for n=2")
}
}
func TestDomain_CheckExportFormatting(t *testing.T) {
po := NewPo()
po.Set("myid", "test string\nwith \"newline\"")

View file

@ -78,3 +78,15 @@ func (t *Translation) GetN(n int) string {
// Return untranslated plural by default
return t.PluralID
}
// IsTranslated reports whether a string is translated
func (t *Translation) IsTranslated() bool {
tr, ok := t.Trs[0]
return tr != "" && ok
}
// IsTranslatedN reports whether a plural string is translated
func (t *Translation) IsTranslatedN(n int) bool {
tr, ok := t.Trs[n]
return tr != "" && ok
}