diff --git a/polyfill/lib/calendar.mjs b/polyfill/lib/calendar.mjs index b2b68efee2..4ac2f2d8e4 100644 --- a/polyfill/lib/calendar.mjs +++ b/polyfill/lib/calendar.mjs @@ -633,18 +633,20 @@ const nonIsoHelperBase = { adjustCalendarDate(calendarDate, cache, overflow /*, fromLegacyDate = false */) { if (this.calendarType === 'lunisolar') throw new RangeError('Override required for lunisolar calendars'); this.validateCalendarDate(calendarDate); - const largestMonth = this.monthsInYear(calendarDate, cache); - let { month, year, eraYear, monthCode } = calendarDate; - // For calendars that always use the same era, set it here so that derived // calendars won't need to implement this method simply to set the era. if (this.constantEra) { // year and eraYear always match when there's only one possible era - if (year === undefined) year = eraYear; - if (eraYear === undefined) eraYear = year; - calendarDate = { ...calendarDate, era: this.constantEra, year, eraYear }; + const { year, eraYear } = calendarDate; + calendarDate = { + ...calendarDate, + era: this.constantEra, + year: year !== undefined ? year : eraYear, + eraYear: eraYear !== undefined ? eraYear : year + }; } - + const largestMonth = this.monthsInYear(calendarDate, cache); + let { month, monthCode } = calendarDate; ({ month, monthCode } = resolveNonLunisolarMonth(calendarDate, overflow, largestMonth)); return { ...calendarDate, month, monthCode }; }, @@ -1146,10 +1148,10 @@ const helperHebrew = ObjectAssign({}, nonIsoHelperBase, { } else { if (overflow === 'reject') { ES.RejectToRange(month, 1, this.monthsInYear({ year })); - ES.RejectToRange(day, 1, this.maximumMonthLength(calendarDate)); + ES.RejectToRange(day, 1, this.maximumMonthLength({ year, month })); } else { month = ES.ConstrainToRange(month, 1, this.monthsInYear({ year })); - day = ES.ConstrainToRange(day, 1, this.maximumMonthLength({ ...calendarDate, month })); + day = ES.ConstrainToRange(day, 1, this.maximumMonthLength({ year, month })); } if (monthCode === undefined) { monthCode = this.getMonthCode(year, month); @@ -1298,10 +1300,8 @@ const helperIndian = ObjectAssign({}, nonIsoHelperBase, { * eras. Note that it mutates and normalizes the original era objects, which is * OK because this is non-observable, internal-only metadata. * - * The result is an array of eras with this shape: - * ``` - * interface Era { - * // name of the era + * interface Era { + * /** name of the era * name: string; * * // alternate name of the era used in old versions of ICU data @@ -1309,25 +1309,29 @@ const helperIndian = ObjectAssign({}, nonIsoHelperBase, { * // with the oldest era being 0. * genericName: string; * - * // Signed calendar year where this era begins. Will be - * // 1 (or 0 for zero-based eras) for the anchor era assuming that `year` - * // numbering starts at the beginning of the anchor era, which is true - * // for all ICU calendars except Japanese. If an era starts mid-year - * // then a calendar month and day are included. Otherwise - * // `{ month: 1, day: 1 }` is assumed. - * anchorEpoch: { year: number } | { year: number, month: number, day: number } + * // Signed calendar year where this era begins. Will be 1 (or 0 for zero-based + * // eras) for the anchor era assuming that `year` numbering starts at the + * // beginning of the anchor era, which is true for all ICU calendars except + * // Japanese. For input, the month and day are optional. If an era starts + * // mid-year then a calendar month and day are included. + * // Otherwise `{ month: 1, day: 1 }` is assumed. + * anchorEpoch: { year: number; month: number; day: number }; * * // ISO date of the first day of this era - * isoEpoch: { year: number, month: number, day: number} + * isoEpoch: { year: number; month: number; day: number }; * * // If present, then this era counts years backwards like BC * // and this property points to the forward era. This must be * // the last (oldest) era in the array. - * reverseOf: Era; + * reverseOf?: Era; * * // If true, the era's years are 0-based. If omitted or false, * // then the era's years are 1-based. - * hasYearZero: boolean = false; + * hasYearZero?: boolean; + * + * // Override if this era is the anchor. Not normally used because + * // anchor eras are inferred. + * isAnchor?: boolean; * } * ``` * */ @@ -1387,6 +1391,7 @@ function adjustEras(eras) { ArraySort.call(eras, (e1, e2) => { if (e1.reverseOf) return 1; if (e2.reverseOf) return -1; + if (!e1.isoEpoch || !e2.isoEpoch) throw new RangeError('Invalid era data: missing ISO epoch'); return e2.isoEpoch.year - e1.isoEpoch.year; });