aboutsummaryrefslogtreecommitdiff
path: root/lib/kernel/date_spec.mli
diff options
context:
space:
mode:
Diffstat (limited to 'lib/kernel/date_spec.mli')
-rw-r--r--lib/kernel/date_spec.mli46
1 files changed, 41 insertions, 5 deletions
diff --git a/lib/kernel/date_spec.mli b/lib/kernel/date_spec.mli
index 3fe9625..70a3030 100644
--- a/lib/kernel/date_spec.mli
+++ b/lib/kernel/date_spec.mli
@@ -1,9 +1,45 @@
-(** A sanctoral entry's date expression. *)
-type t = Fixed of { month : int; day : int } [@@deriving sexp]
+(** A sanctoral entry's date expression.
+
+ [Fixed] is a civil (month, day) that recurs every year. The other two move:
+ [Easter_offset] is a signed day count from the rite's own Easter, and
+ [Nth_weekday] is the nth (or nth-from-last) given weekday of a month.
+
+ Sunday-relative forms ("the Sunday on or after 2 November") are
+ deliberately absent: nothing in this repository needs one yet, and the same
+ mechanism admits them when something does. *)
+type t =
+ | Fixed of { month : int; day : int }
+ | Easter_offset of int
+ | Nth_weekday of { month : int; nth : int; weekday : Date.weekday }
+[@@deriving sexp]
(** Validates against the leap-year maximum, so 29 February is constructible. *)
val fixed : month:int -> day:int -> (t, string) result
-(** [None] when the spec does not occur in that year (29 February in a common
- year) or falls outside the supported domain. *)
-val resolve : t -> year:int -> Date.t option
+(** Rejects an offset further than a year from Easter in either direction --
+ past that, a spec is a data error rather than a calendar. Deliberately
+ generous: Septuagesima is Easter-63 and Time after Pentecost runs well past
+ Easter+180. *)
+val easter_offset : int -> (t, string) result
+
+(** [nth] is 1-based forward, or negative from the end ([-1] is the last).
+ Rejects [nth = 0] (meaningless), [|nth| > 5] (no month has six of any
+ weekday), and a month outside 1..12. *)
+val nth_weekday : month:int -> nth:int -> weekday:Date.weekday -> (t, string) result
+
+(** [resolve spec ~year ~easter] is the civil date [spec] denotes in [year],
+ where [easter] is that year's Easter as the RITE reckons it -- supplied by
+ the caller, never computed here, since {!Computus} ships both Gregorian and
+ Julian and choosing one in the kernel would be silently wrong for a
+ Julian-reckoning rite.
+
+ [None] means "this spec does not occur in that year", per variant:
+ - [Fixed]: 29 February in a common year, or a date outside 1583..9999.
+ - [Easter_offset]: the resolved date falls outside 1583..9999. This is
+ reachable at the domain edges -- {!Date.add_days} is unbounded total
+ arithmetic and will happily denote a date outside the domain.
+ - [Nth_weekday]: the month has no such occurrence (a fifth Sunday it
+ lacks).
+
+ Total: never raises on any in-range year, for any constructible spec. *)
+val resolve : t -> year:int -> easter:Date.t -> Date.t option