aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--internal/calendar/temporal_ef.go21
-rw-r--r--internal/calendar/temporal_ef_test.go23
2 files changed, 38 insertions, 6 deletions
diff --git a/internal/calendar/temporal_ef.go b/internal/calendar/temporal_ef.go
index c649405..3d6c72c 100644
--- a/internal/calendar/temporal_ef.go
+++ b/internal/calendar/temporal_ef.go
@@ -100,12 +100,27 @@ func temporalEF(date time.Time) temporalDay {
// Holy Thursday (the Mass of Chrism and the Mass in Cena Domini) is white,
// a whole-Mass exception to Passiontide's violet -- RG 128(b)'s own named
// exception list, and RG 122 stating the same fact affirmatively in the
- // White section. Good Friday and Holy Saturday, either side, are NOT
- // exceptions here (RG 132's black for Good Friday's liturgical action is a
- // separate, unmodelled gap -- see precedence_ef.go's doc comments).
+ // White section.
if sameDay(date, easter.AddDate(0, 0, -3)) {
col = White
}
+ // Good Friday is BLACK. RG 128(b)'s exception list carries it in the same
+ // sentence as Holy Thursday's -- "...Actione liturgica feria VI in Passione
+ // et Morte Domini usque ad Communionem exclusive..." excepts the day from
+ // Passiontide's violet -- and RG 132 assigns black to it. Adopted
+ // 2026-08-18 from the sibling project colitur, which closed the same gap
+ // against the Missal; this comment previously called it "a separate,
+ // unmodelled gap" and it no longer is.
+ //
+ // The rubric is per-ACTION ("usque ad Communionem exclusive", violet
+ // returns for the Communion rite) and this model carries one colour per
+ // day, so black is the day's principal colour -- the same acknowledged
+ // limit the Palm Sunday blessing already has. missalemeum's own colour set
+ // for the day is "bv", black first, so even the upstream this file is
+ // generated against agrees on the ordering.
+ if sameDay(date, easter.AddDate(0, 0, -2)) {
+ col = Black
+ }
sun := date.Weekday() == time.Sunday
// Major feasts of the Lord (I class): nice titles + colour.
diff --git a/internal/calendar/temporal_ef_test.go b/internal/calendar/temporal_ef_test.go
index 8b1ffa5..db6e6aa 100644
--- a/internal/calendar/temporal_ef_test.go
+++ b/internal/calendar/temporal_ef_test.go
@@ -98,17 +98,34 @@ func TestTemporalEFRoseSundays(t *testing.T) {
// Passiontide's violet. Good Friday and Holy Saturday, either side, stay
// violet (their own black/no-colour exceptions are a separate, unmodelled
// gap -- see RG 132, precedence_ef.go's own doc comments).
-func TestTemporalEFHolyThursdayColour(t *testing.T) {
+// TestTemporalEFTriduumColours pins all three days of the Sacred Triduum,
+// which take three different colours for three different reasons.
+//
+// Renamed from TestTemporalEFHolyThursdayColour, which asserted Good Friday
+// was violet "(unchanged)" -- encoding a gap this file's own comment used to
+// call "separate, unmodelled". It is modelled now, so the test that pinned
+// the gap had to move with it. A test asserting the absence of a feature
+// passes for exactly as long as the feature is absent, which is not the same
+// as being correct.
+func TestTemporalEFTriduumColours(t *testing.T) {
easter := d("2025-04-20")
holyThu := easter.AddDate(0, 0, -3)
goodFri := easter.AddDate(0, 0, -2)
holySat := easter.AddDate(0, 0, -1)
+ // RG 128(b)'s named exception list, and RG 122 affirmatively.
if got := temporalEF(holyThu).Cel.Colour; got != White {
t.Errorf("Holy Thursday colour = %s, want white", got)
}
- if got := temporalEF(goodFri).Cel.Colour; got != Violet {
- t.Errorf("Good Friday colour = %s, want violet (unchanged)", got)
+ // RG 128(b) excepts the day from Passiontide's violet; RG 132 assigns
+ // black. missalemeum's own colour set for the day is "bv", black first.
+ if got := temporalEF(goodFri).Cel.Colour; got != Black {
+ t.Errorf("Good Friday colour = %s, want black (RG 128(b) + RG 132)", got)
}
+ // Holy Saturday IS still violet: RG 128(b)'s exception for it covers only
+ // the deacon at the Easter Preconium and the celebrant at the renewal of
+ // baptismal promises, not the day, and this model carries one colour per
+ // day. Asserted in the other direction on purpose, so a careless "the
+ // whole Triduum is black" change fails here.
if got := temporalEF(holySat).Cel.Colour; got != Violet {
t.Errorf("Holy Saturday colour = %s, want violet (unchanged)", got)
}