package render import ( "strings" "testing" "github.com/lukaszkasprzak/lectio/internal/liturgy" ) func TestGatherBible(t *testing.T) { // Offline sections carry the English-canonical lookup reference in Ref; the // display citation stays in the reader's sigla dialect. sec := liturgy.Section{Heading: "Ewangelia", Citation: "J 20, 1. 11-18", Ref: "John 20:1,11-18"} label, blocks := GatherVersion("wuj", sec, "new", "pl") if !strings.Contains(label, "Wujek") { t.Errorf("label = %q", label) } if len(blocks) == 0 || !strings.HasPrefix(blocks[0], "20:1") { t.Errorf("first block = %q", blocks) } } func TestGatherTraditional(t *testing.T) { sec := liturgy.Section{Citation: "Luke 7:36-50"} _, blocks := GatherVersion("vul", sec, "traditional", "pl") if len(blocks) == 0 || !strings.HasPrefix(blocks[0], "7:36") { t.Errorf("first block = %q", blocks) } } // TestGatherVersionLabelLang checks that the label's language follows the // lang parameter -- pl reproduces today's Polish labels exactly, en gives // the English set from internal/i18n. func TestGatherVersionLabelLang(t *testing.T) { sec := liturgy.Section{Heading: "Ewangelia (J 20, 1. 11-18)"} label, _ := GatherVersion("vul", sec, "new", "pl") if label != "Wulgata (lac.)" { t.Errorf(`GatherVersion(..., "pl") label = %q, want "Wulgata (lac.)"`, label) } label, _ = GatherVersion("vul", sec, "new", "en") if label != "Vulgate (Latin)" { t.Errorf(`GatherVersion(..., "en") label = %q, want "Vulgate (Latin)"`, label) } } // TestCompareLabelLang checks Compare's column-header row follows lang, // same as GatherVersion (which it wraps via compareSection). func TestCompareLabelLang(t *testing.T) { sec := liturgy.Section{Heading: "Ewangelia (J 20, 1. 11-18)"} out := Compare([]liturgy.Section{sec}, []string{"vul"}, 80, "new", "pl") if !strings.Contains(out, "Wulgata (lac.)") { t.Errorf(`Compare(..., "pl") = %q, want it to contain "Wulgata (lac.)"`, out) } out = Compare([]liturgy.Section{sec}, []string{"vul"}, 80, "new", "en") if !strings.Contains(out, "Vulgate (Latin)") { t.Errorf(`Compare(..., "en") = %q, want it to contain "Vulgate (Latin)"`, out) } } // TestGatherVersionNoVersionLang checks that the "(not in %s)" block // (bible.Lookup finding nothing at all) follows lang -- pl reproduces the // original Polish wording exactly, en uses internal/i18n's English wording. func TestGatherVersionNoVersionLang(t *testing.T) { sec := liturgy.Section{Heading: "Ewangelia (J 20, 1. 11-18)"} _, blocks := GatherVersion("zzz", sec, "new", "pl") if len(blocks) == 0 || blocks[0] != `(brak w „zzz”)` { t.Errorf(`GatherVersion(..., "pl") blocks = %v, want [(brak w „zzz”)]`, blocks) } _, blocks = GatherVersion("zzz", sec, "new", "en") if len(blocks) == 0 || blocks[0] != "(not in zzz)" { t.Errorf(`GatherVersion(..., "en") blocks = %v, want [(not in zzz)]`, blocks) } } // TestGatherVersionNoReferenceLang checks the "(no reference)" block (no // citation resolvable at all) follows lang. func TestGatherVersionNoReferenceLang(t *testing.T) { sec := liturgy.Section{Heading: "Bez odwołania"} _, blocks := GatherVersion("wuj", sec, "new", "pl") if len(blocks) == 0 || blocks[0] != "(brak odwołania)" { t.Errorf(`GatherVersion(..., "pl") blocks = %v, want [(brak odwołania)]`, blocks) } _, blocks = GatherVersion("wuj", sec, "new", "en") if len(blocks) == 0 || blocks[0] != "(no reference)" { t.Errorf(`GatherVersion(..., "en") blocks = %v, want [(no reference)]`, blocks) } } func TestOfflineVersions(t *testing.T) { got := OfflineVersions([]string{"bt", "wuj", "vul"}) for _, v := range got { if v == "bt" { t.Error("bt not dropped offline") } } } func TestGatherVersesBible(t *testing.T) { sec := liturgy.Section{Heading: "Ewangelia", Citation: "J 20, 1. 11-18", Ref: "John 20:1,11-18"} label, verses, versified := GatherVerses("wuj", sec, "new", "pl") if !strings.Contains(label, "Wujek") { t.Errorf("label = %q", label) } if !versified { t.Error("versified = false, want true for wuj with a resolvable citation") } if len(verses) == 0 { t.Fatal("verses empty") } if verses[0].Chapter != 20 || verses[0].Verse != 1 || verses[0].Text == "" { t.Errorf("verses[0] = %+v", verses[0]) } } func TestGatherVersesBT(t *testing.T) { sec := liturgy.Section{ Heading: "Psalm (Ps 1)", Paragraphs: [][]string{{"stanza one"}}, } _, verses, versified := GatherVerses("bt", sec, "new", "pl") if versified { t.Error("versified = true, want false for bt (paragraph text, no verse numbers)") } if verses != nil { t.Errorf("verses = %+v, want nil for bt", verses) } } // TestGatherVersesLabelLang checks GatherVerses' label also follows lang, // same as GatherVersion. func TestGatherVersesLabelLang(t *testing.T) { sec := liturgy.Section{Heading: "Ewangelia (J 20, 1. 11-18)"} label, _, _ := GatherVerses("vul", sec, "new", "en") if label != "Vulgate (Latin)" { t.Errorf(`GatherVerses(..., "en") label = %q, want "Vulgate (Latin)"`, label) } } // TestLocalizeHeading covers render.LocalizeHeading's part-label swap // (brief §3b): the pl label prefix of a modern (niedziela.pl) heading is // replaced by its en label, the citation kept exactly as scraped, and every // other case (pl, unknown/traditional partID, prefix mismatch) is a safe // no-op that returns heading unchanged. func TestHeadingWithRef(t *testing.T) { // Traditional-style: a bare label plus Citation -> reference appended. trad := liturgy.Section{Heading: "Gospel", Citation: "Luke 16:1-9", PartID: "evangelium"} if got := HeadingWithRef(trad, "en"); got != "Gospel (Luke 16:1-9)" { t.Errorf("traditional heading = %q, want %q", got, "Gospel (Luke 16:1-9)") } // Modern-style: heading already carries "(...)" -> not doubled; the pl label // is still localised to en. modern := liturgy.Section{Heading: "Ewangelia (J 20, 1. 11-18)", Citation: "J 20, 1. 11-18", PartID: "ewangelia"} if got := HeadingWithRef(modern, "en"); got != "Gospel (J 20, 1. 11-18)" { t.Errorf("modern heading = %q", got) } // No citation -> unchanged. if got := HeadingWithRef(liturgy.Section{Heading: "Gospel", PartID: "evangelium"}, "en"); got != "Gospel" { t.Errorf("no-citation heading = %q", got) } } func TestLocalizeHeading(t *testing.T) { cases := []struct { name, heading, partID, lang, want string }{ {"gospel en", "Ewangelia (J 20, 1. 11-18)", "ewangelia", "en", "Gospel (J 20, 1. 11-18)"}, {"first reading en", "1. czytanie (Dz 2, 14. 22-33)", "pierwsze_czytanie", "en", "1st reading (Dz 2, 14. 22-33)"}, {"psalm en", "Psalm (Ps 15)", "psalm", "en", "Psalm (Ps 15)"}, {"acclamation en", "Aklamacja (Alleluja)", "aklamacja", "en", "Acclamation (Alleluja)"}, {"pl unchanged", "Ewangelia (J 20, 1. 11-18)", "ewangelia", "pl", "Ewangelia (J 20, 1. 11-18)"}, {"unknown partID unchanged", "Coś innego (X 1)", "", "en", "Coś innego (X 1)"}, {"already-English heading unchanged (traditional lectionary, no pl prefix to match)", "Gospel (Luke 7:36-50)", "ewangelia", "en", "Gospel (Luke 7:36-50)"}, {"prefix mismatch unchanged", "Nieoczekiwany tytuł (J 1)", "ewangelia", "en", "Nieoczekiwany tytuł (J 1)"}, // Split (two-reading) feast day: niedziela.pl scrapes // PartID="drugie_czytanie" onto a heading that still literally // starts with "1. czytanie" (its own numbering quirk). Matching // must follow the heading's actual text, not partID's label, so // this localises to "1st reading", not staying Polish. {"drugie_czytanie partID with a 1. czytanie heading (split feast day)", "1. czytanie (Dz 2, 14. 22-33)", "drugie_czytanie", "en", "1st reading (Dz 2, 14. 22-33)"}, } for _, c := range cases { t.Run(c.name, func(t *testing.T) { got := LocalizeHeading(c.heading, c.partID, c.lang) if got != c.want { t.Errorf("LocalizeHeading(%q, %q, %q) = %q, want %q", c.heading, c.partID, c.lang, got, c.want) } }) } }