Sync telesrv commits 49f9bab and 04d9563 into the public mirror. Exclude private docs and runtime key material per sync rules.
164 lines
5.8 KiB
Go
164 lines
5.8 KiB
Go
package postgres
|
|
|
|
import (
|
|
"context"
|
|
"path/filepath"
|
|
"strings"
|
|
"testing"
|
|
"time"
|
|
|
|
applangpack "telesrv/internal/app/langpack"
|
|
"telesrv/internal/domain"
|
|
)
|
|
|
|
func TestLangPackSeedReconciliationPostgres(t *testing.T) {
|
|
pool := testPool(t)
|
|
ctx := context.Background()
|
|
packName := "seedtest-" + randomSuffix(t)
|
|
store := NewLangPackStore(pool)
|
|
t.Cleanup(func() {
|
|
_, _ = pool.Exec(ctx, "DELETE FROM lang_pack_strings WHERE lang_pack = $1", packName)
|
|
_, _ = pool.Exec(ctx, "DELETE FROM lang_packs WHERE lang_pack = $1", packName)
|
|
_, _ = pool.Exec(ctx, "DELETE FROM seed_states WHERE key LIKE $1 OR key = $2 OR key = $3", "langpack:v1:entry:"+packName+":%", "langpack:v1:catalog:"+packName, "langpack:v2:catalog:"+packName)
|
|
})
|
|
|
|
seedV1 := domain.LangPackSeed{
|
|
Catalog: packName,
|
|
Scopes: []string{packName},
|
|
Packs: []domain.LangPackSeedEntry{{
|
|
SourceHash: "source-v1",
|
|
ContentHash: "hash-v1",
|
|
StringsCount: 2,
|
|
ContentLoaded: true,
|
|
Pack: domain.LangPack{
|
|
LangPack: packName,
|
|
LangCode: "fr",
|
|
Version: 1,
|
|
Strings: []domain.LangPackString{
|
|
{Key: "LanguageName", Value: "Français"},
|
|
{Key: "old", Value: "old"},
|
|
},
|
|
},
|
|
}},
|
|
}
|
|
written, err := store.ReconcileSeed(ctx, seedV1)
|
|
if err != nil || written != 2 {
|
|
t.Fatalf("reconcile v1 = %d, %v", written, err)
|
|
}
|
|
seedV1Unloaded := seedV1
|
|
seedV1Unloaded.Packs = append([]domain.LangPackSeedEntry(nil), seedV1.Packs...)
|
|
seedV1Unloaded.Packs[0].Pack.Strings = nil
|
|
seedV1Unloaded.Packs[0].ContentLoaded = false
|
|
if written, err := store.ReconcileSeed(ctx, seedV1Unloaded); err != nil || written != 0 {
|
|
t.Fatalf("reconcile unchanged v1 = %d, %v", written, err)
|
|
}
|
|
catalog, err := store.GetSeedCatalog(ctx, packName)
|
|
if err != nil || len(catalog.Packs) != 1 || catalog.Packs[0].SourceHash != "source-v1" {
|
|
t.Fatalf("seed catalog = %+v, %v", catalog, err)
|
|
}
|
|
|
|
seedV2 := domain.LangPackSeed{
|
|
Catalog: packName,
|
|
Scopes: []string{packName},
|
|
Packs: []domain.LangPackSeedEntry{{
|
|
SourceHash: "source-v2",
|
|
ContentHash: "hash-v2",
|
|
StringsCount: 2,
|
|
ContentLoaded: true,
|
|
Pack: domain.LangPack{
|
|
LangPack: packName,
|
|
LangCode: "fr",
|
|
Version: 2,
|
|
Strings: []domain.LangPackString{
|
|
{Key: "LanguageName", Value: "Français v2"},
|
|
{Key: "new", Value: "new"},
|
|
},
|
|
},
|
|
}},
|
|
}
|
|
written, err = store.ReconcileSeed(ctx, seedV2)
|
|
if err != nil || written != 2 {
|
|
t.Fatalf("reconcile v2 = %d, %v", written, err)
|
|
}
|
|
pack, err := store.GetPack(ctx, packName, "fr", 0)
|
|
if err != nil || pack.Version != 2 || len(pack.Strings) != 2 || postgresLangPackValue(pack.Strings, "old") != "" || postgresLangPackValue(pack.Strings, "new") != "new" {
|
|
t.Fatalf("replaced postgres pack = %+v, err %v", pack, err)
|
|
}
|
|
|
|
mutated := seedV2
|
|
mutated.Packs = append([]domain.LangPackSeedEntry(nil), seedV2.Packs...)
|
|
mutated.Packs[0].ContentHash = "changed-without-version"
|
|
if _, err := store.ReconcileSeed(ctx, mutated); err == nil || !strings.Contains(err.Error(), "without version bump") {
|
|
t.Fatalf("same-version mutation error = %v", err)
|
|
}
|
|
rollback := seedV2
|
|
rollback.Packs = append([]domain.LangPackSeedEntry(nil), seedV2.Packs...)
|
|
rollback.Packs[0].Pack.Version = 1
|
|
rollback.Packs[0].ContentHash = "rollback"
|
|
if _, err := store.ReconcileSeed(ctx, rollback); err == nil || !strings.Contains(err.Error(), "version rollback") {
|
|
t.Fatalf("rollback error = %v", err)
|
|
}
|
|
|
|
if written, err := store.ReconcileSeed(ctx, domain.LangPackSeed{Catalog: packName}); err != nil || written != 0 {
|
|
t.Fatalf("remove missing language = %d, %v", written, err)
|
|
}
|
|
languages, err := store.ListLanguages(ctx, packName)
|
|
if err != nil || len(languages) != 0 {
|
|
t.Fatalf("languages after manifest removal = %+v, err %v", languages, err)
|
|
}
|
|
}
|
|
|
|
func postgresLangPackValue(items []domain.LangPackString, key string) string {
|
|
for _, item := range items {
|
|
if item.Key == key {
|
|
return item.Value
|
|
}
|
|
}
|
|
return ""
|
|
}
|
|
|
|
func TestBundledLangPackSeedPostgres(t *testing.T) {
|
|
pool := testPool(t)
|
|
ctx := context.Background()
|
|
scopes := []string{"android", "android_x", "ios", "macos", "tdesktop", "weba"}
|
|
t.Cleanup(func() {
|
|
_, _ = pool.Exec(ctx, "DELETE FROM lang_pack_strings WHERE lang_pack = ANY($1::text[])", scopes)
|
|
_, _ = pool.Exec(ctx, "DELETE FROM lang_packs WHERE lang_pack = ANY($1::text[])", scopes)
|
|
for _, scope := range scopes {
|
|
_, _ = pool.Exec(ctx, "DELETE FROM seed_states WHERE key LIKE $1", "langpack:v1:entry:"+scope+":%")
|
|
}
|
|
_, _ = pool.Exec(ctx, "DELETE FROM seed_states WHERE key = 'langpack:v1:catalog:langpack'")
|
|
_, _ = pool.Exec(ctx, "DELETE FROM seed_states WHERE key = 'langpack:v2:catalog:langpack'")
|
|
})
|
|
|
|
service := applangpack.NewService(NewLangPackStore(pool))
|
|
root := filepath.Join("..", "..", "..", "data", "langpack")
|
|
started := time.Now()
|
|
seeded, err := service.SeedDirectory(ctx, root)
|
|
firstDuration := time.Since(started)
|
|
if err != nil {
|
|
t.Fatalf("seed bundled langpacks to postgres: %v", err)
|
|
}
|
|
if seeded < 50000 {
|
|
t.Fatalf("seeded bundled strings = %d, want full catalog", seeded)
|
|
}
|
|
|
|
started = time.Now()
|
|
seededAgain, err := service.SeedDirectory(ctx, root)
|
|
secondDuration := time.Since(started)
|
|
if err != nil || seededAgain != 0 {
|
|
t.Fatalf("reconcile unchanged bundled langpacks = %d, %v", seededAgain, err)
|
|
}
|
|
var metadataCount, activeCount int64
|
|
if err := pool.QueryRow(ctx, `
|
|
SELECT
|
|
(SELECT COALESCE(sum(strings_count), 0) FROM lang_packs WHERE lang_pack = ANY($1::text[])),
|
|
(SELECT count(*) FROM lang_pack_strings WHERE lang_pack = ANY($1::text[]) AND NOT deleted)
|
|
`, scopes).Scan(&metadataCount, &activeCount); err != nil {
|
|
t.Fatalf("count seeded langpack rows: %v", err)
|
|
}
|
|
if metadataCount != activeCount {
|
|
t.Fatalf("seeded strings_count = %d, active rows = %d", metadataCount, activeCount)
|
|
}
|
|
t.Logf("bundled langpack seed: first=%s unchanged=%s strings=%d", firstDuration, secondDuration, metadataCount)
|
|
}
|