Coverage priorities 1-5: test pure functions, extract interfaces, mock-based handler tests
- Priority 1: Test NewSendEmailTask + NewSendPushTask (5 tests) - Priority 2: Test customHTTPErrorHandler — all 15+ branches (21 tests) - Priority 3: Extract Enqueuer interface + payload builders in worker pkg (5 tests) - Priority 4: Extract ClassifyFile/ComputeRelPath in migrate-encrypt (6 tests) - Priority 5: Define Handler interfaces, refactor to accept them, mock-based tests (14 tests) - Fix .gitignore: /worker instead of worker to stop ignoring internal/worker/ Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
211
internal/i18n/i18n_test.go
Normal file
211
internal/i18n/i18n_test.go
Normal file
@@ -0,0 +1,211 @@
|
||||
package i18n
|
||||
|
||||
import (
|
||||
"net/http"
|
||||
"net/http/httptest"
|
||||
"testing"
|
||||
|
||||
"github.com/labstack/echo/v4"
|
||||
"github.com/stretchr/testify/assert"
|
||||
"github.com/stretchr/testify/require"
|
||||
)
|
||||
|
||||
func TestInit(t *testing.T) {
|
||||
err := Init()
|
||||
require.NoError(t, err)
|
||||
assert.NotNil(t, Bundle)
|
||||
}
|
||||
|
||||
func TestTSimple_EnglishKnownKey(t *testing.T) {
|
||||
require.NoError(t, Init())
|
||||
|
||||
localizer := NewLocalizer("en")
|
||||
msg := TSimple(localizer, "error.task_not_found")
|
||||
assert.Equal(t, "Task not found", msg)
|
||||
}
|
||||
|
||||
func TestTSimple_SpanishKnownKey(t *testing.T) {
|
||||
require.NoError(t, Init())
|
||||
|
||||
localizer := NewLocalizer("es")
|
||||
msg := TSimple(localizer, "error.invalid_credentials")
|
||||
assert.Equal(t, "Credenciales no validas", msg)
|
||||
}
|
||||
|
||||
func TestT_WithTemplateData(t *testing.T) {
|
||||
require.NoError(t, Init())
|
||||
|
||||
localizer := NewLocalizer("en")
|
||||
msg := T(localizer, "message.tasks_report_sent", map[string]interface{}{
|
||||
"Email": "test@example.com",
|
||||
})
|
||||
assert.Contains(t, msg, "test@example.com")
|
||||
}
|
||||
|
||||
func TestTSimple_UnknownKeyReturnsKey(t *testing.T) {
|
||||
require.NoError(t, Init())
|
||||
|
||||
localizer := NewLocalizer("en")
|
||||
key := "error.nonexistent_key_that_does_not_exist"
|
||||
msg := TSimple(localizer, key)
|
||||
assert.Equal(t, key, msg)
|
||||
}
|
||||
|
||||
func TestTSimple_FallbackToEnglish(t *testing.T) {
|
||||
require.NoError(t, Init())
|
||||
|
||||
// Use a language that may not have all translations — fallback to English
|
||||
localizer := NewLocalizer("xx", "en")
|
||||
msg := TSimple(localizer, "error.task_not_found")
|
||||
assert.Equal(t, "Task not found", msg)
|
||||
}
|
||||
|
||||
func TestT_NilLocalizer_UsesDefault(t *testing.T) {
|
||||
require.NoError(t, Init())
|
||||
|
||||
msg := T(nil, "error.task_not_found", nil)
|
||||
assert.Equal(t, "Task not found", msg)
|
||||
}
|
||||
|
||||
func TestNewLocalizer(t *testing.T) {
|
||||
require.NoError(t, Init())
|
||||
|
||||
localizer := NewLocalizer("en")
|
||||
assert.NotNil(t, localizer)
|
||||
}
|
||||
|
||||
func TestParseAcceptLanguage(t *testing.T) {
|
||||
tests := []struct {
|
||||
name string
|
||||
header string
|
||||
expected []string
|
||||
}{
|
||||
{"empty returns default", "", []string{"en"}},
|
||||
{"english", "en-US,en;q=0.9", []string{"en", "en"}},
|
||||
{"spanish first", "es,en;q=0.5", []string{"es", "en"}},
|
||||
{"unsupported returns default", "xx-YY", []string{"en"}},
|
||||
{"french", "fr-FR,fr;q=0.9,en;q=0.5", []string{"fr", "fr", "en"}},
|
||||
}
|
||||
|
||||
for _, tc := range tests {
|
||||
t.Run(tc.name, func(t *testing.T) {
|
||||
result := parseAcceptLanguage(tc.header)
|
||||
assert.Equal(t, tc.expected, result)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestMatchLocale(t *testing.T) {
|
||||
tests := []struct {
|
||||
name string
|
||||
langs []string
|
||||
expected string
|
||||
}{
|
||||
{"finds supported", []string{"es", "en"}, "es"},
|
||||
{"first match wins", []string{"fr", "de"}, "fr"},
|
||||
{"unsupported returns default", []string{"xx"}, "en"},
|
||||
{"empty returns default", []string{}, "en"},
|
||||
}
|
||||
|
||||
for _, tc := range tests {
|
||||
t.Run(tc.name, func(t *testing.T) {
|
||||
result := matchLocale(tc.langs)
|
||||
assert.Equal(t, tc.expected, result)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestMiddleware_SetsLocalizerAndLocale(t *testing.T) {
|
||||
require.NoError(t, Init())
|
||||
|
||||
e := echo.New()
|
||||
req := httptest.NewRequest(http.MethodGet, "/", nil)
|
||||
req.Header.Set("Accept-Language", "es,en;q=0.5")
|
||||
rec := httptest.NewRecorder()
|
||||
c := e.NewContext(req, rec)
|
||||
|
||||
handler := Middleware()(func(c echo.Context) error {
|
||||
// Verify localizer is set
|
||||
localizer := GetLocalizer(c)
|
||||
assert.NotNil(t, localizer)
|
||||
|
||||
// Verify locale is set
|
||||
locale := GetLocale(c)
|
||||
assert.Equal(t, "es", locale)
|
||||
|
||||
return nil
|
||||
})
|
||||
|
||||
err := handler(c)
|
||||
assert.NoError(t, err)
|
||||
}
|
||||
|
||||
func TestGetLocalizer_NoContextValue_ReturnsDefault(t *testing.T) {
|
||||
require.NoError(t, Init())
|
||||
|
||||
e := echo.New()
|
||||
req := httptest.NewRequest(http.MethodGet, "/", nil)
|
||||
rec := httptest.NewRecorder()
|
||||
c := e.NewContext(req, rec)
|
||||
|
||||
localizer := GetLocalizer(c)
|
||||
assert.NotNil(t, localizer)
|
||||
}
|
||||
|
||||
func TestGetLocale_NoContextValue_ReturnsDefault(t *testing.T) {
|
||||
e := echo.New()
|
||||
req := httptest.NewRequest(http.MethodGet, "/", nil)
|
||||
rec := httptest.NewRecorder()
|
||||
c := e.NewContext(req, rec)
|
||||
|
||||
locale := GetLocale(c)
|
||||
assert.Equal(t, "en", locale)
|
||||
}
|
||||
|
||||
func TestLocalizedMessage(t *testing.T) {
|
||||
require.NoError(t, Init())
|
||||
|
||||
e := echo.New()
|
||||
req := httptest.NewRequest(http.MethodGet, "/", nil)
|
||||
req.Header.Set("Accept-Language", "en")
|
||||
rec := httptest.NewRecorder()
|
||||
c := e.NewContext(req, rec)
|
||||
|
||||
// Set up localizer through middleware
|
||||
handler := Middleware()(func(c echo.Context) error {
|
||||
msg := LocalizedMessage(c, "error.task_not_found")
|
||||
assert.Equal(t, "Task not found", msg)
|
||||
return nil
|
||||
})
|
||||
|
||||
err := handler(c)
|
||||
assert.NoError(t, err)
|
||||
}
|
||||
|
||||
func TestLocalizedMessageWithData(t *testing.T) {
|
||||
require.NoError(t, Init())
|
||||
|
||||
e := echo.New()
|
||||
req := httptest.NewRequest(http.MethodGet, "/", nil)
|
||||
req.Header.Set("Accept-Language", "en")
|
||||
rec := httptest.NewRecorder()
|
||||
c := e.NewContext(req, rec)
|
||||
|
||||
handler := Middleware()(func(c echo.Context) error {
|
||||
msg := LocalizedMessageWithData(c, "message.tasks_report_sent", map[string]interface{}{
|
||||
"Email": "user@example.com",
|
||||
})
|
||||
assert.Contains(t, msg, "user@example.com")
|
||||
return nil
|
||||
})
|
||||
|
||||
err := handler(c)
|
||||
assert.NoError(t, err)
|
||||
}
|
||||
|
||||
func TestSupportedLanguages(t *testing.T) {
|
||||
assert.Contains(t, SupportedLanguages, "en")
|
||||
assert.Contains(t, SupportedLanguages, "es")
|
||||
assert.Contains(t, SupportedLanguages, "fr")
|
||||
assert.Equal(t, "en", DefaultLanguage)
|
||||
}
|
||||
Reference in New Issue
Block a user