@hebcal/core 5.3.3 → 5.3.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.cjs CHANGED
@@ -1,25 +1,39 @@
1
- /*! @hebcal/core v5.3.3 */
1
+ /*! @hebcal/core v5.3.4 */
2
2
  'use strict';
3
3
 
4
+ /* eslint-disable @typescript-eslint/no-namespace, no-inner-declarations */
4
5
  /** @private */
5
6
  const lengths = [0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31];
6
7
  /** @private */
7
- const monthLengths = [
8
- lengths,
9
- lengths.slice(),
10
- ];
8
+ const monthLengths = [lengths, lengths.slice()];
11
9
  monthLengths[1][2] = 29;
12
10
  /**
13
11
  * @private
14
12
  */
15
13
  function mod$1(x, y) {
16
- return x - y * Math.floor(x / y);
14
+ return x - y * Math.floor(x / y);
17
15
  }
18
16
  /**
19
17
  * @private
20
18
  */
21
19
  function quotient(x, y) {
22
- return Math.floor(x / y);
20
+ return Math.floor(x / y);
21
+ }
22
+ /**
23
+ * @private
24
+ * @param abs - R.D. number of days
25
+ */
26
+ function yearFromFixed(abs) {
27
+ const l0 = abs - 1;
28
+ const n400 = quotient(l0, 146097);
29
+ const d1 = mod$1(l0, 146097);
30
+ const n100 = quotient(d1, 36524);
31
+ const d2 = mod$1(d1, 36524);
32
+ const n4 = quotient(d2, 1461);
33
+ const d3 = mod$1(d2, 1461);
34
+ const n1 = quotient(d3, 365);
35
+ const year = 400 * n400 + 100 * n100 + 4 * n4 + n1;
36
+ return n100 !== 4 && n1 !== 4 ? year + 1 : year;
23
37
  }
24
38
  /*
25
39
  const ABS_14SEP1752 = 639797;
@@ -30,116 +44,95 @@ const ABS_2SEP1752 = 639785;
30
44
  */
31
45
  exports.greg = void 0;
32
46
  (function (greg) {
33
- /**
34
- * Returns true if the Gregorian year is a leap year
35
- * @param {number} year Gregorian year
36
- * @return {boolean}
37
- */
38
- function isLeapYear(year) {
39
- return !(year % 4) && (!!(year % 100) || !(year % 400));
40
- }
41
- greg.isLeapYear = isLeapYear;
42
- /**
43
- * Number of days in the Gregorian month for given year
44
- * @param {number} month Gregorian month (1=January, 12=December)
45
- * @param {number} year Gregorian year
46
- * @return {number}
47
- */
48
- function daysInMonth(month, year) {
49
- // 1 based months
50
- return monthLengths[+isLeapYear(year)][month];
51
- }
52
- greg.daysInMonth = daysInMonth;
53
- /**
54
- * Returns true if the object is a Javascript Date
55
- * @param {Object} obj
56
- * @return {boolean}
57
- */
58
- function isDate(obj) {
59
- return typeof obj === 'object' && Date.prototype.isPrototypeOf(obj);
60
- }
61
- greg.isDate = isDate;
62
- /**
63
- * @private
64
- * @param abs - R.D. number of days
65
- */
66
- function yearFromFixed(abs) {
67
- const l0 = abs - 1;
68
- const n400 = quotient(l0, 146097);
69
- const d1 = mod$1(l0, 146097);
70
- const n100 = quotient(d1, 36524);
71
- const d2 = mod$1(d1, 36524);
72
- const n4 = quotient(d2, 1461);
73
- const d3 = mod$1(d2, 1461);
74
- const n1 = quotient(d3, 365);
75
- const year = 400 * n400 + 100 * n100 + 4 * n4 + n1;
76
- return n100 != 4 && n1 != 4 ? year + 1 : year;
47
+ /**
48
+ * Returns true if the Gregorian year is a leap year
49
+ * @param {number} year Gregorian year
50
+ * @return {boolean}
51
+ */
52
+ function isLeapYear(year) {
53
+ return !(year % 4) && (!!(year % 100) || !(year % 400));
54
+ }
55
+ greg.isLeapYear = isLeapYear;
56
+ /**
57
+ * Number of days in the Gregorian month for given year
58
+ * @param {number} month Gregorian month (1=January, 12=December)
59
+ * @param {number} year Gregorian year
60
+ * @return {number}
61
+ */
62
+ function daysInMonth(month, year) {
63
+ // 1 based months
64
+ return monthLengths[+isLeapYear(year)][month];
65
+ }
66
+ greg.daysInMonth = daysInMonth;
67
+ /**
68
+ * Returns true if the object is a Javascript Date
69
+ * @param {Object} obj
70
+ * @return {boolean}
71
+ */
72
+ function isDate(obj) {
73
+ // eslint-disable-next-line no-prototype-builtins
74
+ return typeof obj === 'object' && Date.prototype.isPrototypeOf(obj);
75
+ }
76
+ greg.isDate = isDate;
77
+ /**
78
+ * @private
79
+ * @param year
80
+ * @param month (1-12)
81
+ * @param day (1-31)
82
+ */
83
+ function toFixed(year, month, day) {
84
+ const py = year - 1;
85
+ return 365 * py + quotient(py, 4) - quotient(py, 100) + quotient(py, 400) + quotient(367 * month - 362, 12) + (month <= 2 ? 0 : isLeapYear(year) ? -1 : -2) + day;
86
+ }
87
+ /**
88
+ * Converts Gregorian date to absolute R.D. (Rata Die) days
89
+ * @param {Date} date Gregorian date
90
+ * @return {number}
91
+ */
92
+ function greg2abs(date) {
93
+ if (!isDate(date)) {
94
+ throw new TypeError(`Argument not a Date: ${date}`);
77
95
  }
78
- /**
79
- * @private
80
- * @param year
81
- * @param month (1-12)
82
- * @param day (1-31)
83
- */
84
- function toFixed(year, month, day) {
85
- const py = year - 1;
86
- return 365 * py +
87
- quotient(py, 4) -
88
- quotient(py, 100) +
89
- quotient(py, 400) +
90
- quotient((367 * month - 362), 12) +
91
- (month <= 2 ? 0 : (isLeapYear(year) ? -1 : -2)) +
92
- day;
96
+ const abs = toFixed(date.getFullYear(), date.getMonth() + 1, date.getDate());
97
+ /*
98
+ if (abs < ABS_14SEP1752 && abs > ABS_2SEP1752) {
99
+ throw new RangeError(`Invalid Date: ${date}`);
93
100
  }
94
- /**
95
- * Converts Gregorian date to absolute R.D. (Rata Die) days
96
- * @param {Date} date Gregorian date
97
- * @return {number}
98
- */
99
- function greg2abs(date) {
100
- if (!isDate(date)) {
101
- throw new TypeError(`Argument not a Date: ${date}`);
102
- }
103
- const abs = toFixed(date.getFullYear(), date.getMonth() + 1, date.getDate());
104
- /*
105
- if (abs < ABS_14SEP1752 && abs > ABS_2SEP1752) {
106
- throw new RangeError(`Invalid Date: ${date}`);
107
- }
108
- */
109
- return abs;
101
+ */
102
+ return abs;
103
+ }
104
+ greg.greg2abs = greg2abs;
105
+ /**
106
+ * Converts from Rata Die (R.D. number) to Gregorian date.
107
+ * See the footnote on page 384 of ``Calendrical Calculations, Part II:
108
+ * Three Historical Calendars'' by E. M. Reingold, N. Dershowitz, and S. M.
109
+ * Clamen, Software--Practice and Experience, Volume 23, Number 4
110
+ * (April, 1993), pages 383-404 for an explanation.
111
+ * @param {number} abs - R.D. number of days
112
+ * @return {Date}
113
+ */
114
+ function abs2greg(abs) {
115
+ if (typeof abs !== 'number') {
116
+ throw new TypeError(`Argument not a Number: ${abs}`);
110
117
  }
111
- greg.greg2abs = greg2abs;
112
- /**
113
- * Converts from Rata Die (R.D. number) to Gregorian date.
114
- * See the footnote on page 384 of ``Calendrical Calculations, Part II:
115
- * Three Historical Calendars'' by E. M. Reingold, N. Dershowitz, and S. M.
116
- * Clamen, Software--Practice and Experience, Volume 23, Number 4
117
- * (April, 1993), pages 383-404 for an explanation.
118
- * @param {number} abs - R.D. number of days
119
- * @return {Date}
120
- */
121
- function abs2greg(abs) {
122
- if (typeof abs !== 'number') {
123
- throw new TypeError(`Argument not a Number: ${abs}`);
124
- }
125
- abs = Math.trunc(abs);
126
- /*
127
- if (abs < ABS_14SEP1752 && abs > ABS_2SEP1752) {
128
- throw new RangeError(`Invalid Date: ${abs}`);
129
- }
130
- */
131
- const year = yearFromFixed(abs);
132
- const priorDays = abs - toFixed(year, 1, 1);
133
- const correction = abs < toFixed(year, 3, 1) ? 0 : (isLeapYear(year) ? 1 : 2);
134
- const month = quotient((12 * (priorDays + correction) + 373), 367);
135
- const day = abs - toFixed(year, month, 1) + 1;
136
- const dt = new Date(year, month - 1, day);
137
- if (year < 100 && year >= 0) {
138
- dt.setFullYear(year);
139
- }
140
- return dt;
118
+ abs = Math.trunc(abs);
119
+ /*
120
+ if (abs < ABS_14SEP1752 && abs > ABS_2SEP1752) {
121
+ throw new RangeError(`Invalid Date: ${abs}`);
141
122
  }
142
- greg.abs2greg = abs2greg;
123
+ */
124
+ const year = yearFromFixed(abs);
125
+ const priorDays = abs - toFixed(year, 1, 1);
126
+ const correction = abs < toFixed(year, 3, 1) ? 0 : isLeapYear(year) ? 1 : 2;
127
+ const month = quotient(12 * (priorDays + correction) + 373, 367);
128
+ const day = abs - toFixed(year, month, 1) + 1;
129
+ const dt = new Date(year, month - 1, day);
130
+ if (year < 100 && year >= 0) {
131
+ dt.setFullYear(year);
132
+ }
133
+ return dt;
134
+ }
135
+ greg.abs2greg = abs2greg;
143
136
  })(exports.greg || (exports.greg = {}));
144
137
 
145
138
  /*
@@ -164,63 +157,40 @@ const ADAR_II$2 = 13;
164
157
  * @enum {number}
165
158
  */
166
159
  const months = {
167
- /** Nissan / ניסן */
168
- NISAN: 1,
169
- /** Iyyar / אייר */
170
- IYYAR: 2,
171
- /** Sivan / סיון */
172
- SIVAN: 3,
173
- /** Tamuz (sometimes Tammuz) / תמוז */
174
- TAMUZ: 4,
175
- /** Av / אב */
176
- AV: 5,
177
- /** Elul / אלול */
178
- ELUL: 6,
179
- /** Tishrei / תִּשְׁרֵי */
180
- TISHREI: 7,
181
- /** Cheshvan / חשון */
182
- CHESHVAN: 8,
183
- /** Kislev / כסלו */
184
- KISLEV: 9,
185
- /** Tevet / טבת */
186
- TEVET: 10,
187
- /** Sh'vat / שבט */
188
- SHVAT: 11,
189
- /** Adar or Adar Rishon / אדר */
190
- ADAR_I: 12,
191
- /** Adar Sheini (only on leap years) / אדר ב׳ */
192
- ADAR_II: 13,
160
+ /** Nissan / ניסן */
161
+ NISAN: 1,
162
+ /** Iyyar / אייר */
163
+ IYYAR: 2,
164
+ /** Sivan / סיון */
165
+ SIVAN: 3,
166
+ /** Tamuz (sometimes Tammuz) / תמוז */
167
+ TAMUZ: 4,
168
+ /** Av / אב */
169
+ AV: 5,
170
+ /** Elul / אלול */
171
+ ELUL: 6,
172
+ /** Tishrei / תִּשְׁרֵי */
173
+ TISHREI: 7,
174
+ /** Cheshvan / חשון */
175
+ CHESHVAN: 8,
176
+ /** Kislev / כסלו */
177
+ KISLEV: 9,
178
+ /** Tevet / טבת */
179
+ TEVET: 10,
180
+ /** Sh'vat / שבט */
181
+ SHVAT: 11,
182
+ /** Adar or Adar Rishon / אדר */
183
+ ADAR_I: 12,
184
+ /** Adar Sheini (only on leap years) / אדר ב׳ */
185
+ ADAR_II: 13
193
186
  };
194
- const monthNames0 = [
195
- '',
196
- 'Nisan',
197
- 'Iyyar',
198
- 'Sivan',
199
- 'Tamuz',
200
- 'Av',
201
- 'Elul',
202
- 'Tishrei',
203
- 'Cheshvan',
204
- 'Kislev',
205
- 'Tevet',
206
- 'Sh\'vat',
207
- ];
187
+ const monthNames0 = ['', 'Nisan', 'Iyyar', 'Sivan', 'Tamuz', 'Av', 'Elul', 'Tishrei', 'Cheshvan', 'Kislev', 'Tevet', "Sh'vat"];
208
188
  /**
209
189
  * Transliterations of Hebrew month names.
210
190
  * Regular years are index 0 and leap years are index 1.
211
191
  * @private
212
192
  */
213
- const monthNames = [
214
- monthNames0.concat([
215
- 'Adar',
216
- 'Nisan',
217
- ]),
218
- monthNames0.concat([
219
- 'Adar I',
220
- 'Adar II',
221
- 'Nisan',
222
- ]),
223
- ];
193
+ const monthNames = [monthNames0.concat(['Adar', 'Nisan']), monthNames0.concat(['Adar I', 'Adar II', 'Nisan'])];
224
194
  const edCache = new Map();
225
195
  const EPOCH = -1373428;
226
196
  // Avg year length in the cycle (19 solar years with 235 lunar months)
@@ -229,9 +199,9 @@ const AVG_HEBYEAR_DAYS = 365.24682220597794;
229
199
  * @private
230
200
  */
231
201
  function assertNumber(n, name) {
232
- if (typeof n !== 'number' || isNaN(n)) {
233
- throw new TypeError(`invalid parameter '${name}' not a number: ${n}`);
234
- }
202
+ if (typeof n !== 'number' || isNaN(n)) {
203
+ throw new TypeError(`invalid parameter '${name}' not a number: ${n}`);
204
+ }
235
205
  }
236
206
  /**
237
207
  * Converts Hebrew date to R.D. (Rata Die) fixed days.
@@ -243,33 +213,32 @@ function assertNumber(n, name) {
243
213
  * @return {number}
244
214
  */
245
215
  function hebrew2abs(year, month, day) {
246
- assertNumber(year, 'year');
247
- assertNumber(month, 'month');
248
- assertNumber(day, 'day');
249
- if (year < 1) {
250
- throw new RangeError(`hebrew2abs: invalid year ${year}`);
251
- }
252
- let tempabs = day;
253
- if (month < TISHREI$2) {
254
- for (let m = TISHREI$2; m <= monthsInYear(year); m++) {
255
- tempabs += daysInMonth(m, year);
256
- }
257
- for (let m = NISAN$4; m < month; m++) {
258
- tempabs += daysInMonth(m, year);
259
- }
216
+ assertNumber(year, 'year');
217
+ assertNumber(month, 'month');
218
+ assertNumber(day, 'day');
219
+ if (year < 1) {
220
+ throw new RangeError(`hebrew2abs: invalid year ${year}`);
221
+ }
222
+ let tempabs = day;
223
+ if (month < TISHREI$2) {
224
+ for (let m = TISHREI$2; m <= monthsInYear(year); m++) {
225
+ tempabs += daysInMonth(m, year);
260
226
  }
261
- else {
262
- for (let m = TISHREI$2; m < month; m++) {
263
- tempabs += daysInMonth(m, year);
264
- }
227
+ for (let m = NISAN$4; m < month; m++) {
228
+ tempabs += daysInMonth(m, year);
265
229
  }
266
- return EPOCH + elapsedDays(year) + tempabs - 1;
230
+ } else {
231
+ for (let m = TISHREI$2; m < month; m++) {
232
+ tempabs += daysInMonth(m, year);
233
+ }
234
+ }
235
+ return EPOCH + elapsedDays(year) + tempabs - 1;
267
236
  }
268
237
  /**
269
238
  * @private
270
239
  */
271
240
  function newYear(year) {
272
- return EPOCH + elapsedDays(year);
241
+ return EPOCH + elapsedDays(year);
273
242
  }
274
243
  /**
275
244
  * Converts absolute R.D. days to Hebrew date
@@ -277,23 +246,27 @@ function newYear(year) {
277
246
  * @return {SimpleHebrewDate}
278
247
  */
279
248
  function abs2hebrew(abs) {
280
- assertNumber(abs, 'abs');
281
- abs = Math.trunc(abs);
282
- if (abs <= EPOCH) {
283
- throw new RangeError(`abs2hebrew: ${abs} is before epoch`);
284
- }
285
- // first, quickly approximate year
286
- let year = Math.floor((abs - EPOCH) / AVG_HEBYEAR_DAYS);
287
- while (newYear(year) <= abs) {
288
- ++year;
289
- }
290
- --year;
291
- let month = abs < hebrew2abs(year, 1, 1) ? 7 : 1;
292
- while (abs > hebrew2abs(year, month, daysInMonth(month, year))) {
293
- ++month;
294
- }
295
- const day = 1 + abs - hebrew2abs(year, month, 1);
296
- return { yy: year, mm: month, dd: day };
249
+ assertNumber(abs, 'abs');
250
+ abs = Math.trunc(abs);
251
+ if (abs <= EPOCH) {
252
+ throw new RangeError(`abs2hebrew: ${abs} is before epoch`);
253
+ }
254
+ // first, quickly approximate year
255
+ let year = Math.floor((abs - EPOCH) / AVG_HEBYEAR_DAYS);
256
+ while (newYear(year) <= abs) {
257
+ ++year;
258
+ }
259
+ --year;
260
+ let month = abs < hebrew2abs(year, 1, 1) ? 7 : 1;
261
+ while (abs > hebrew2abs(year, month, daysInMonth(month, year))) {
262
+ ++month;
263
+ }
264
+ const day = 1 + abs - hebrew2abs(year, month, 1);
265
+ return {
266
+ yy: year,
267
+ mm: month,
268
+ dd: day
269
+ };
297
270
  }
298
271
  /**
299
272
  * Returns true if Hebrew year is a leap year
@@ -301,7 +274,7 @@ function abs2hebrew(abs) {
301
274
  * @return {boolean}
302
275
  */
303
276
  function isLeapYear(year) {
304
- return (1 + year * 7) % 19 < 7;
277
+ return (1 + year * 7) % 19 < 7;
305
278
  }
306
279
  /**
307
280
  * Number of months in this Hebrew year (either 12 or 13 depending on leap year)
@@ -309,7 +282,7 @@ function isLeapYear(year) {
309
282
  * @return {number}
310
283
  */
311
284
  function monthsInYear(year) {
312
- return 12 + +(isLeapYear(year)); // boolean is cast to 1 or 0
285
+ return 12 + +isLeapYear(year); // boolean is cast to 1 or 0
313
286
  }
314
287
  /**
315
288
  * Number of days in Hebrew month in a given year (29 or 30)
@@ -318,22 +291,19 @@ function monthsInYear(year) {
318
291
  * @return {number}
319
292
  */
320
293
  function daysInMonth(month, year) {
321
- switch (month) {
322
- case IYYAR$1:
323
- case TAMUZ$1:
324
- case ELUL$1:
325
- case TEVET$2:
326
- case ADAR_II$2:
327
- return 29;
328
- }
329
- if ((month === ADAR_I$2 && !isLeapYear(year)) ||
330
- (month === CHESHVAN$1 && !longCheshvan(year)) ||
331
- (month === KISLEV$2 && shortKislev(year))) {
332
- return 29;
333
- }
334
- else {
335
- return 30;
336
- }
294
+ switch (month) {
295
+ case IYYAR$1:
296
+ case TAMUZ$1:
297
+ case ELUL$1:
298
+ case TEVET$2:
299
+ case ADAR_II$2:
300
+ return 29;
301
+ }
302
+ if (month === ADAR_I$2 && !isLeapYear(year) || month === CHESHVAN$1 && !longCheshvan(year) || month === KISLEV$2 && shortKislev(year)) {
303
+ return 29;
304
+ } else {
305
+ return 30;
306
+ }
337
307
  }
338
308
  /**
339
309
  * Returns a transliterated string name of Hebrew month in year,
@@ -342,12 +312,12 @@ function daysInMonth(month, year) {
342
312
  * @param {number} year Hebrew year
343
313
  */
344
314
  function getMonthName(month, year) {
345
- assertNumber(month, 'month');
346
- assertNumber(year, 'year');
347
- if (month < 1 || month > 14) {
348
- throw new TypeError(`bad month argument ${month}`);
349
- }
350
- return monthNames[+isLeapYear(year)][month];
315
+ assertNumber(month, 'month');
316
+ assertNumber(year, 'year');
317
+ if (month < 1 || month > 14) {
318
+ throw new TypeError(`bad month argument ${month}`);
319
+ }
320
+ return monthNames[+isLeapYear(year)][month];
351
321
  }
352
322
  /**
353
323
  * Days from sunday prior to start of Hebrew calendar to mean
@@ -356,13 +326,13 @@ function getMonthName(month, year) {
356
326
  * @return {number}
357
327
  */
358
328
  function elapsedDays(year) {
359
- const n = edCache.get(year);
360
- if (typeof n === 'number') {
361
- return n;
362
- }
363
- const elapsed = elapsedDays0(year);
364
- edCache.set(year, elapsed);
365
- return elapsed;
329
+ const n = edCache.get(year);
330
+ if (typeof n === 'number') {
331
+ return n;
332
+ }
333
+ const elapsed = elapsedDays0(year);
334
+ edCache.set(year, elapsed);
335
+ return elapsed;
366
336
  }
367
337
  /**
368
338
  * Days from sunday prior to start of Hebrew calendar to mean
@@ -371,29 +341,25 @@ function elapsedDays(year) {
371
341
  * @param year Hebrew year
372
342
  */
373
343
  function elapsedDays0(year) {
374
- const prevYear = year - 1;
375
- const mElapsed = 235 * Math.floor(prevYear / 19) + // Months in complete 19 year lunar (Metonic) cycles so far
376
- 12 * (prevYear % 19) + // Regular months in this cycle
377
- Math.floor(((prevYear % 19) * 7 + 1) / 19); // Leap months this cycle
378
- const pElapsed = 204 + 793 * (mElapsed % 1080);
379
- const hElapsed = 5 +
380
- 12 * mElapsed +
381
- 793 * Math.floor(mElapsed / 1080) +
382
- Math.floor(pElapsed / 1080);
383
- const parts = (pElapsed % 1080) + 1080 * (hElapsed % 24);
384
- const day = 1 + 29 * mElapsed + Math.floor(hElapsed / 24);
385
- let altDay = day;
386
- if (parts >= 19440 ||
387
- (2 === day % 7 && parts >= 9924 && !isLeapYear(year)) ||
388
- (1 === day % 7 && parts >= 16789 && isLeapYear(prevYear))) {
389
- altDay++;
390
- }
391
- if (altDay % 7 === 0 || altDay % 7 === 3 || altDay % 7 === 5) {
392
- return altDay + 1;
393
- }
394
- else {
395
- return altDay;
396
- }
344
+ const prevYear = year - 1;
345
+ const mElapsed = 235 * Math.floor(prevYear / 19) +
346
+ // Months in complete 19 year lunar (Metonic) cycles so far
347
+ 12 * (prevYear % 19) +
348
+ // Regular months in this cycle
349
+ Math.floor((prevYear % 19 * 7 + 1) / 19); // Leap months this cycle
350
+ const pElapsed = 204 + 793 * (mElapsed % 1080);
351
+ const hElapsed = 5 + 12 * mElapsed + 793 * Math.floor(mElapsed / 1080) + Math.floor(pElapsed / 1080);
352
+ const parts = pElapsed % 1080 + 1080 * (hElapsed % 24);
353
+ const day = 1 + 29 * mElapsed + Math.floor(hElapsed / 24);
354
+ let altDay = day;
355
+ if (parts >= 19440 || 2 === day % 7 && parts >= 9924 && !isLeapYear(year) || 1 === day % 7 && parts >= 16789 && isLeapYear(prevYear)) {
356
+ altDay++;
357
+ }
358
+ if (altDay % 7 === 0 || altDay % 7 === 3 || altDay % 7 === 5) {
359
+ return altDay + 1;
360
+ } else {
361
+ return altDay;
362
+ }
397
363
  }
398
364
  /**
399
365
  * Number of days in the hebrew YEAR.
@@ -403,7 +369,7 @@ function elapsedDays0(year) {
403
369
  * @return {number}
404
370
  */
405
371
  function daysInYear(year) {
406
- return elapsedDays(year + 1) - elapsedDays(year);
372
+ return elapsedDays(year + 1) - elapsedDays(year);
407
373
  }
408
374
  /**
409
375
  * true if Cheshvan is long in Hebrew year
@@ -411,7 +377,7 @@ function daysInYear(year) {
411
377
  * @return {boolean}
412
378
  */
413
379
  function longCheshvan(year) {
414
- return daysInYear(year) % 10 === 5;
380
+ return daysInYear(year) % 10 === 5;
415
381
  }
416
382
  /**
417
383
  * true if Kislev is short in Hebrew year
@@ -419,7 +385,7 @@ function longCheshvan(year) {
419
385
  * @return {boolean}
420
386
  */
421
387
  function shortKislev(year) {
422
- return daysInYear(year) % 10 === 3;
388
+ return daysInYear(year) % 10 === 3;
423
389
  }
424
390
  /**
425
391
  * Converts Hebrew month string name to numeric
@@ -427,116 +393,116 @@ function shortKislev(year) {
427
393
  * @return {number}
428
394
  */
429
395
  function monthFromName(monthName) {
430
- if (typeof monthName === 'number') {
431
- if (isNaN(monthName) || monthName < 1 || monthName > 14) {
432
- throw new RangeError(`Invalid month name: ${monthName}`);
433
- }
434
- return monthName;
435
- }
436
- let c = monthName.trim().toLowerCase();
437
- // If Hebrew month starts with a bet (for example `בתמוז`) then ignore it
438
- if (c[0] === 'ב') {
439
- c = c.substring(1);
440
- }
441
- /*
442
- the Hebrew months are unique to their second letter
443
- N Nisan (November?)
444
- I Iyyar
445
- E Elul
446
- C Cheshvan
447
- K Kislev
448
- 1 1Adar
449
- 2 2Adar
450
- Si Sh Sivan, Shvat
451
- Ta Ti Te Tamuz, Tishrei, Tevet
452
- Av Ad Av, Adar
453
-
454
- אב אד אי אל אב אדר אייר אלול
455
- ח חשון
456
- ט טבת
457
- כ כסלו
458
- נ ניסן
459
- ס סיון
460
- ש שבט
461
- תמ תש תמוז תשרי
462
- */
463
- switch (c[0]) {
464
- case 'n':
465
- case 'נ':
466
- if (c[1] == 'o') {
467
- break; /* this catches "november" */
468
- }
469
- return months.NISAN;
396
+ if (typeof monthName === 'number') {
397
+ if (isNaN(monthName) || monthName < 1 || monthName > 14) {
398
+ throw new RangeError(`Invalid month name: ${monthName}`);
399
+ }
400
+ return monthName;
401
+ }
402
+ let c = monthName.trim().toLowerCase();
403
+ // If Hebrew month starts with a bet (for example `בתמוז`) then ignore it
404
+ if (c[0] === 'ב') {
405
+ c = c.substring(1);
406
+ }
407
+ /*
408
+ the Hebrew months are unique to their second letter
409
+ N Nisan (November?)
410
+ I Iyyar
411
+ E Elul
412
+ C Cheshvan
413
+ K Kislev
414
+ 1 1Adar
415
+ 2 2Adar
416
+ Si Sh Sivan, Shvat
417
+ Ta Ti Te Tamuz, Tishrei, Tevet
418
+ Av Ad Av, Adar
419
+ אב אד אי אל אב אדר אייר אלול
420
+ ח חשון
421
+ ט טבת
422
+ כ כסלו
423
+ נ ניסן
424
+ ס סיון
425
+ ש שבט
426
+ תמ תש תמוז תשרי
427
+ */
428
+ switch (c[0]) {
429
+ case 'n':
430
+ case 'נ':
431
+ if (c[1] === 'o') {
432
+ break; /* this catches "november" */
433
+ }
434
+ return months.NISAN;
435
+ case 'i':
436
+ return months.IYYAR;
437
+ case 'e':
438
+ return months.ELUL;
439
+ case 'c':
440
+ case 'ח':
441
+ return months.CHESHVAN;
442
+ case 'k':
443
+ case 'כ':
444
+ return months.KISLEV;
445
+ case 's':
446
+ switch (c[1]) {
470
447
  case 'i':
471
- return months.IYYAR;
472
- case 'e':
473
- return months.ELUL;
474
- case 'c':
475
- case 'ח':
476
- return months.CHESHVAN;
477
- case 'k':
478
- case 'כ':
479
- return months.KISLEV;
480
- case 's':
481
- switch (c[1]) {
482
- case 'i':
483
- return months.SIVAN;
484
- case 'h':
485
- return months.SHVAT;
486
- }
487
- break;
488
- case 't':
489
- switch (c[1]) {
490
- case 'a':
491
- return months.TAMUZ;
492
- case 'i':
493
- return months.TISHREI;
494
- case 'e':
495
- return months.TEVET;
496
- }
497
- break;
448
+ return months.SIVAN;
449
+ case 'h':
450
+ return months.SHVAT;
451
+ }
452
+ break;
453
+ case 't':
454
+ switch (c[1]) {
498
455
  case 'a':
499
- switch (c[1]) {
500
- case 'v':
501
- return months.AV;
502
- case 'd':
503
- if (/(1|[^i]i|a|א)$/i.test(monthName)) {
504
- return months.ADAR_I;
505
- }
506
- return months.ADAR_II; // else assume sheini
507
- }
508
- break;
509
- case 'ס':
510
- return months.SIVAN;
511
- case 'ט':
512
- return months.TEVET;
456
+ return months.TAMUZ;
457
+ case 'i':
458
+ return months.TISHREI;
459
+ case 'e':
460
+ return months.TEVET;
461
+ }
462
+ break;
463
+ case 'a':
464
+ switch (c[1]) {
465
+ case 'v':
466
+ return months.AV;
467
+ case 'd':
468
+ if (/(1|[^i]i|a|א)$/i.test(monthName)) {
469
+ return months.ADAR_I;
470
+ }
471
+ return months.ADAR_II;
472
+ }
473
+ break;
474
+ case 'ס':
475
+ return months.SIVAN;
476
+ case 'ט':
477
+ return months.TEVET;
478
+ case 'ש':
479
+ return months.SHVAT;
480
+ case 'א':
481
+ switch (c[1]) {
482
+ case 'ב':
483
+ return months.AV;
484
+ case 'ד':
485
+ if (/(1|[^i]i|a|א)$/i.test(monthName)) {
486
+ return months.ADAR_I;
487
+ }
488
+ return months.ADAR_II;
489
+ // else assume sheini
490
+ case 'י':
491
+ return months.IYYAR;
492
+ case 'ל':
493
+ return months.ELUL;
494
+ }
495
+ break;
496
+ case 'ת':
497
+ switch (c[1]) {
498
+ case 'מ':
499
+ return months.TAMUZ;
513
500
  case 'ש':
514
- return months.SHVAT;
515
- case 'א':
516
- switch (c[1]) {
517
- case 'ב':
518
- return months.AV;
519
- case 'ד':
520
- if (/(1|[^i]i|a|א)$/i.test(monthName)) {
521
- return months.ADAR_I;
522
- }
523
- return months.ADAR_II; // else assume sheini
524
- case 'י':
525
- return months.IYYAR;
526
- case 'ל':
527
- return months.ELUL;
528
- }
529
- break;
530
- case 'ת':
531
- switch (c[1]) {
532
- case 'מ':
533
- return months.TAMUZ;
534
- case 'ש':
535
- return months.TISHREI;
536
- }
537
- break;
538
- }
539
- throw new RangeError(`Unable to parse month name: ${monthName}`);
501
+ return months.TISHREI;
502
+ }
503
+ break;
504
+ }
505
+ throw new RangeError(`Unable to parse month name: ${monthName}`);
540
506
  }
541
507
 
542
508
  const NISAN$3 = months.NISAN;
@@ -547,155 +513,145 @@ const SHVAT = months.SHVAT;
547
513
  const ADAR_I$1 = months.ADAR_I;
548
514
  const ADAR_II$1 = months.ADAR_II;
549
515
  /**
550
- * Returns true if the object is a Javascript Date
516
+ * Returns true if the object is a SimpleHebrewDate
551
517
  * @private
552
518
  * @param {Object} obj
553
519
  */
554
520
  function isSimpleHebrewDate(obj) {
555
- return typeof obj === 'object' && obj !== null &&
556
- typeof obj.yy === 'number' &&
557
- typeof obj.mm === 'number' &&
558
- typeof obj.dd === 'number';
521
+ return typeof obj === 'object' && obj !== null && typeof obj.yy === 'number' && typeof obj.mm === 'number' && typeof obj.dd === 'number';
559
522
  }
560
523
  /**
561
524
  * @private
562
525
  */
563
526
  function toSimpleHebrewDate(obj) {
564
- if (isSimpleHebrewDate(obj)) {
565
- return obj;
566
- }
567
- else if (typeof obj === 'number') {
568
- return abs2hebrew(obj);
569
- }
570
- else if (exports.greg.isDate(obj)) {
571
- const abs = exports.greg.greg2abs(obj);
572
- return abs2hebrew(abs);
573
- }
574
- else {
575
- throw new TypeError(`Argument not a Date: ${obj}`);
576
- }
527
+ if (isSimpleHebrewDate(obj)) {
528
+ return obj;
529
+ } else if (typeof obj === 'number') {
530
+ return abs2hebrew(obj);
531
+ } else if (exports.greg.isDate(obj)) {
532
+ const abs = exports.greg.greg2abs(obj);
533
+ return abs2hebrew(abs);
534
+ } else {
535
+ throw new TypeError(`Argument not a Date: ${obj}`);
536
+ }
577
537
  }
578
538
  function getYahrzeitHD(hyear, date) {
579
- let hDeath = toSimpleHebrewDate(date);
580
- if (hyear <= hDeath.yy) {
581
- // Hebrew year ${hyear} occurs on or before original date in ${hDeath.yy}
582
- return undefined;
583
- }
584
- if (hDeath.mm == CHESHVAN && hDeath.dd == 30 && !longCheshvan(hDeath.yy + 1)) {
585
- // If it's Heshvan 30 it depends on the first anniversary;
586
- // if that was not Heshvan 30, use the day before Kislev 1.
587
- hDeath = abs2hebrew(hebrew2abs(hyear, KISLEV$1, 1) - 1);
588
- }
589
- else if (hDeath.mm == KISLEV$1 && hDeath.dd == 30 && shortKislev(hDeath.yy + 1)) {
590
- // If it's Kislev 30 it depends on the first anniversary;
591
- // if that was not Kislev 30, use the day before Teveth 1.
592
- hDeath = abs2hebrew(hebrew2abs(hyear, TEVET$1, 1) - 1);
593
- }
594
- else if (hDeath.mm == ADAR_II$1) {
595
- // If it's Adar II, use the same day in last month of year (Adar or Adar II).
596
- hDeath.mm = monthsInYear(hyear);
597
- }
598
- else if (hDeath.mm == ADAR_I$1 && hDeath.dd == 30 && !isLeapYear(hyear)) {
599
- // If it's the 30th in Adar I and year is not a leap year
600
- // (so Adar has only 29 days), use the last day in Shevat.
601
- hDeath.dd = 30;
602
- hDeath.mm = SHVAT;
603
- }
604
- // In all other cases, use the normal anniversary of the date of death.
605
- // advance day to rosh chodesh if needed
606
- if (hDeath.mm == CHESHVAN && hDeath.dd == 30 && !longCheshvan(hyear)) {
607
- hDeath.mm = KISLEV$1;
608
- hDeath.dd = 1;
609
- }
610
- else if (hDeath.mm == KISLEV$1 && hDeath.dd == 30 && shortKislev(hyear)) {
611
- hDeath.mm = TEVET$1;
612
- hDeath.dd = 1;
613
- }
614
- hDeath.yy = hyear;
615
- return hDeath;
539
+ let hDeath = toSimpleHebrewDate(date);
540
+ if (hyear <= hDeath.yy) {
541
+ // Hebrew year ${hyear} occurs on or before original date in ${hDeath.yy}
542
+ return undefined;
543
+ }
544
+ if (hDeath.mm === CHESHVAN && hDeath.dd === 30 && !longCheshvan(hDeath.yy + 1)) {
545
+ // If it's Heshvan 30 it depends on the first anniversary;
546
+ // if that was not Heshvan 30, use the day before Kislev 1.
547
+ hDeath = abs2hebrew(hebrew2abs(hyear, KISLEV$1, 1) - 1);
548
+ } else if (hDeath.mm === KISLEV$1 && hDeath.dd === 30 && shortKislev(hDeath.yy + 1)) {
549
+ // If it's Kislev 30 it depends on the first anniversary;
550
+ // if that was not Kislev 30, use the day before Teveth 1.
551
+ hDeath = abs2hebrew(hebrew2abs(hyear, TEVET$1, 1) - 1);
552
+ } else if (hDeath.mm === ADAR_II$1) {
553
+ // If it's Adar II, use the same day in last month of year (Adar or Adar II).
554
+ hDeath.mm = monthsInYear(hyear);
555
+ } else if (hDeath.mm === ADAR_I$1 && hDeath.dd === 30 && !isLeapYear(hyear)) {
556
+ // If it's the 30th in Adar I and year is not a leap year
557
+ // (so Adar has only 29 days), use the last day in Shevat.
558
+ hDeath.dd = 30;
559
+ hDeath.mm = SHVAT;
560
+ }
561
+ // In all other cases, use the normal anniversary of the date of death.
562
+ // advance day to rosh chodesh if needed
563
+ if (hDeath.mm === CHESHVAN && hDeath.dd === 30 && !longCheshvan(hyear)) {
564
+ hDeath.mm = KISLEV$1;
565
+ hDeath.dd = 1;
566
+ } else if (hDeath.mm === KISLEV$1 && hDeath.dd === 30 && shortKislev(hyear)) {
567
+ hDeath.mm = TEVET$1;
568
+ hDeath.dd = 1;
569
+ }
570
+ hDeath.yy = hyear;
571
+ return hDeath;
616
572
  }
617
573
  function getBirthdayHD(hyear, date) {
618
- const orig = toSimpleHebrewDate(date);
619
- const origYear = orig.yy;
620
- if (hyear === origYear) {
621
- return orig;
622
- }
623
- else if (hyear < origYear) {
624
- // Hebrew year ${hyear} occurs on or before original date in ${origYear}
625
- return undefined;
626
- }
627
- const isOrigLeap = isLeapYear(origYear);
628
- let month = orig.mm;
629
- let day = orig.dd;
630
- if ((month == ADAR_I$1 && !isOrigLeap) || (month == ADAR_II$1 && isOrigLeap)) {
631
- month = monthsInYear(hyear);
632
- }
633
- else if (month == CHESHVAN && day == 30 && !longCheshvan(hyear)) {
634
- month = KISLEV$1;
635
- day = 1;
636
- }
637
- else if (month == KISLEV$1 && day == 30 && shortKislev(hyear)) {
638
- month = TEVET$1;
639
- day = 1;
640
- }
641
- else if (month == ADAR_I$1 && day == 30 && isOrigLeap && !isLeapYear(hyear)) {
642
- month = NISAN$3;
643
- day = 1;
644
- }
645
- return { yy: hyear, mm: month, dd: day };
574
+ const orig = toSimpleHebrewDate(date);
575
+ const origYear = orig.yy;
576
+ if (hyear === origYear) {
577
+ return orig;
578
+ } else if (hyear < origYear) {
579
+ // Hebrew year ${hyear} occurs on or before original date in ${origYear}
580
+ return undefined;
581
+ }
582
+ const isOrigLeap = isLeapYear(origYear);
583
+ let month = orig.mm;
584
+ let day = orig.dd;
585
+ if (month === ADAR_I$1 && !isOrigLeap || month === ADAR_II$1 && isOrigLeap) {
586
+ month = monthsInYear(hyear);
587
+ } else if (month === CHESHVAN && day === 30 && !longCheshvan(hyear)) {
588
+ month = KISLEV$1;
589
+ day = 1;
590
+ } else if (month === KISLEV$1 && day === 30 && shortKislev(hyear)) {
591
+ month = TEVET$1;
592
+ day = 1;
593
+ } else if (month === ADAR_I$1 && day === 30 && isOrigLeap && !isLeapYear(hyear)) {
594
+ month = NISAN$3;
595
+ day = 1;
596
+ }
597
+ return {
598
+ yy: hyear,
599
+ mm: month,
600
+ dd: day
601
+ };
646
602
  }
647
603
 
648
604
  const GERESH = '׳';
649
605
  const GERSHAYIM = '״';
650
606
  const alefbet = {
651
- 'א': 1,
652
- 'ב': 2,
653
- 'ג': 3,
654
- 'ד': 4,
655
- 'ה': 5,
656
- 'ו': 6,
657
- 'ז': 7,
658
- 'ח': 8,
659
- 'ט': 9,
660
- 'י': 10,
661
- 'כ': 20,
662
- 'ל': 30,
663
- 'מ': 40,
664
- 'נ': 50,
665
- 'ס': 60,
666
- 'ע': 70,
667
- 'פ': 80,
668
- 'צ': 90,
669
- 'ק': 100,
670
- 'ר': 200,
671
- 'ש': 300,
672
- 'ת': 400,
607
+ א: 1,
608
+ ב: 2,
609
+ ג: 3,
610
+ ד: 4,
611
+ ה: 5,
612
+ ו: 6,
613
+ ז: 7,
614
+ ח: 8,
615
+ ט: 9,
616
+ י: 10,
617
+ כ: 20,
618
+ ל: 30,
619
+ מ: 40,
620
+ נ: 50,
621
+ ס: 60,
622
+ ע: 70,
623
+ פ: 80,
624
+ צ: 90,
625
+ ק: 100,
626
+ ר: 200,
627
+ ש: 300,
628
+ ת: 400
673
629
  };
674
630
  const heb2num = new Map();
675
631
  const num2heb = new Map();
676
632
  for (const [key, val] of Object.entries(alefbet)) {
677
- heb2num.set(key, val);
678
- num2heb.set(val, key);
633
+ heb2num.set(key, val);
634
+ num2heb.set(val, key);
679
635
  }
680
636
  function num2digits(num) {
681
- const digits = [];
682
- while (num > 0) {
683
- if (num === 15 || num === 16) {
684
- digits.push(9);
685
- digits.push(num - 9);
686
- break;
687
- }
688
- let incr = 100;
689
- let i;
690
- for (i = 400; i > num; i -= incr) {
691
- if (i === incr) {
692
- incr = incr / 10;
693
- }
694
- }
695
- digits.push(i);
696
- num -= i;
637
+ const digits = [];
638
+ while (num > 0) {
639
+ if (num === 15 || num === 16) {
640
+ digits.push(9);
641
+ digits.push(num - 9);
642
+ break;
643
+ }
644
+ let incr = 100;
645
+ let i;
646
+ for (i = 400; i > num; i -= incr) {
647
+ if (i === incr) {
648
+ incr = incr / 10;
649
+ }
697
650
  }
698
- return digits;
651
+ digits.push(i);
652
+ num -= i;
653
+ }
654
+ return digits;
699
655
  }
700
656
  /**
701
657
  * Converts a numerical value to a string of Hebrew letters.
@@ -712,31 +668,31 @@ function num2digits(num) {
712
668
  * @return {string}
713
669
  */
714
670
  function gematriya(num) {
715
- const num0 = num;
716
- const num1 = parseInt(num0, 10);
717
- if (!num1) {
718
- throw new TypeError(`invalid parameter to gematriya ${num}`);
719
- }
720
- let str = '';
721
- const thousands = Math.floor(num1 / 1000);
722
- if (thousands > 0 && thousands !== 5) {
723
- const tdigits = num2digits(thousands);
724
- for (const tdig of tdigits) {
725
- str += num2heb.get(tdig);
726
- }
727
- str += GERESH;
728
- }
729
- const digits = num2digits(num1 % 1000);
730
- if (digits.length == 1) {
731
- return str + num2heb.get(digits[0]) + GERESH;
671
+ const num0 = num;
672
+ const num1 = parseInt(num0, 10);
673
+ if (!num1) {
674
+ throw new TypeError(`invalid parameter to gematriya ${num}`);
675
+ }
676
+ let str = '';
677
+ const thousands = Math.floor(num1 / 1000);
678
+ if (thousands > 0 && thousands !== 5) {
679
+ const tdigits = num2digits(thousands);
680
+ for (const tdig of tdigits) {
681
+ str += num2heb.get(tdig);
732
682
  }
733
- for (let i = 0; i < digits.length; i++) {
734
- if (i + 1 === digits.length) {
735
- str += GERSHAYIM;
736
- }
737
- str += num2heb.get(digits[i]);
683
+ str += GERESH;
684
+ }
685
+ const digits = num2digits(num1 % 1000);
686
+ if (digits.length === 1) {
687
+ return str + num2heb.get(digits[0]) + GERESH;
688
+ }
689
+ for (let i = 0; i < digits.length; i++) {
690
+ if (i + 1 === digits.length) {
691
+ str += GERSHAYIM;
738
692
  }
739
- return str;
693
+ str += num2heb.get(digits[i]);
694
+ }
695
+ return str;
740
696
  }
741
697
  /**
742
698
  * Converts a string of Hebrew letters to a numerical value.
@@ -749,20 +705,189 @@ function gematriya(num) {
749
705
  * @return {number}
750
706
  */
751
707
  function gematriyaStrToNum(str) {
752
- let num = 0;
753
- const gereshIdx = str.indexOf(GERESH);
754
- if (gereshIdx !== -1 && gereshIdx !== str.length - 1) {
755
- const thousands = str.substring(0, gereshIdx);
756
- num += gematriyaStrToNum(thousands) * 1000;
757
- str = str.substring(gereshIdx);
758
- }
759
- for (const ch of str) {
760
- const n = heb2num.get(ch);
761
- if (typeof n === 'number') {
762
- num += n;
763
- }
708
+ let num = 0;
709
+ const gereshIdx = str.indexOf(GERESH);
710
+ if (gereshIdx !== -1 && gereshIdx !== str.length - 1) {
711
+ const thousands = str.substring(0, gereshIdx);
712
+ num += gematriyaStrToNum(thousands) * 1000;
713
+ str = str.substring(gereshIdx);
714
+ }
715
+ for (const ch of str) {
716
+ const n = heb2num.get(ch);
717
+ if (typeof n === 'number') {
718
+ num += n;
719
+ }
720
+ }
721
+ return num;
722
+ }
723
+
724
+ const sefirot = {
725
+ en: {
726
+ infix: 'within ',
727
+ infix26: 'within ',
728
+ words: ['', 'Lovingkindness', 'Might', 'Beauty', 'Eternity', 'Splendor', 'Foundation', 'Majesty']
729
+ },
730
+ he: {
731
+ infix: 'שֶׁבְּ',
732
+ infix26: 'שֶׁבִּ',
733
+ words: ['', 'חֶֽסֶד', 'גְבוּרָה', 'תִּפאֶרֶת', 'נֶּֽצַח', 'הוֹד', 'יְּסוֹד', 'מַּלְכוּת']
734
+ },
735
+ translit: {
736
+ infix: "sheb'",
737
+ infix26: 'shebi',
738
+ words: ['', 'Chesed', 'Gevurah', 'Tiferet', 'Netzach', 'Hod', 'Yesod', 'Malkhut']
739
+ }
740
+ };
741
+ function checkDay(omerDay) {
742
+ if (omerDay < 1 || omerDay > 49) {
743
+ throw new RangeError(`Invalid Omer day ${omerDay}`);
744
+ }
745
+ }
746
+ function getWeeks(omerDay) {
747
+ const weekNum = Math.floor((omerDay - 1) / 7) + 1;
748
+ const daysWithinWeeks = omerDay % 7 || 7;
749
+ return [weekNum, daysWithinWeeks];
750
+ }
751
+ /**
752
+ * Returns the sefira. For example, on day 8
753
+ * חֶֽסֶד שֶׁבִּגְבוּרָה
754
+ * Chesed shebiGevurah
755
+ * Lovingkindness within Might
756
+ * @param omerDay the day of the omer, 1-49 inclusive
757
+ * @param lang `en` (English), `he` (Hebrew with nikud), or `translit` (Hebrew in Sephardic transliteration)
758
+ * @returns a string such as `Lovingkindness within Might` or `חֶֽסֶד שֶׁבִּגְבוּרָה`
759
+ */
760
+ function omerSefira(omerDay, lang) {
761
+ checkDay(omerDay);
762
+ const [weekNum, daysWithinWeeks] = getWeeks(omerDay);
763
+ const config = sefirot[lang];
764
+ const week = config.words[weekNum];
765
+ const dayWithinWeek = config.words[daysWithinWeeks];
766
+ const infix = weekNum === 2 || weekNum === 6 ? config.infix26 : config.infix;
767
+ return (dayWithinWeek + ' ' + infix + week).normalize();
768
+ }
769
+ /**
770
+ * Returns a sentence with that evening's omer count
771
+ * @param omerDay the day of the omer, 1-49 inclusive
772
+ * @param lang `en` (English), `he` (Hebrew with nikud)
773
+ * @returns a string such as `Today is 10 days, which is 1 week and 3 days of the Omer`
774
+ * or `הַיוֹם עֲשָׂרָה יָמִים, שְׁהֵם שָׁבוּעַ אֶחָד וְשְׁלוֹשָׁה יָמִים לָעוֹמֶר`
775
+ */
776
+ function omerTodayIs(omerDay, lang) {
777
+ checkDay(omerDay);
778
+ if (lang === 'en') {
779
+ return omerTodayIsEn(omerDay);
780
+ } else if (lang === 'he') {
781
+ return omerTodayIsHe(omerDay);
782
+ } else {
783
+ return undefined;
784
+ }
785
+ }
786
+ function omerTodayIsEn(omerDay) {
787
+ const [weekNumber, daysWithinWeeks] = getWeeks(omerDay);
788
+ const totalDaysStr = omerDay === 1 ? 'day' : 'days';
789
+ let str = `Today is ${omerDay} ${totalDaysStr}`;
790
+ if (weekNumber > 1 || omerDay === 7) {
791
+ const day7 = daysWithinWeeks === 7;
792
+ const numWeeks = day7 ? weekNumber : weekNumber - 1;
793
+ const weeksStr = numWeeks === 1 ? 'week' : 'weeks';
794
+ str += `, which is ${numWeeks} ${weeksStr}`;
795
+ if (!day7) {
796
+ const daysStr = daysWithinWeeks === 1 ? 'day' : 'days';
797
+ str += ` and ${daysWithinWeeks} ${daysStr}`;
798
+ }
799
+ }
800
+ return str + ' of the Omer';
801
+ }
802
+ // adapted from pip hdate package (GPL)
803
+ // https://github.com/py-libhdate/py-libhdate/blob/master/hdate/date.py
804
+ const tens = ['', 'עֲשָׂרָה', 'עֶשְׂרִים', 'שְׁלוֹשִׁים', 'אַרְבָּעִים'];
805
+ const ones = ['', 'אֶחָד', 'שְׁנַיִם', 'שְׁלוֹשָׁה', 'אַרְבָּעָה', 'חֲמִשָּׁה', 'שִׁשָּׁה', 'שִׁבְעָה', 'שְׁמוֹנָה', 'תִּשְׁעָה'];
806
+ const shnei = 'שְׁנֵי';
807
+ const yamim = 'יָמִים';
808
+ const shneiYamim = shnei + ' ' + yamim;
809
+ const shavuot = 'שָׁבוּעוֹת';
810
+ const yom = 'יוֹם';
811
+ const yomEchad = yom + ' ' + ones[1];
812
+ function omerTodayIsHe(omerDay) {
813
+ const ten = Math.floor(omerDay / 10);
814
+ const one = omerDay % 10;
815
+ let str = 'הַיּוֹם ';
816
+ if (10 < omerDay && omerDay < 20) {
817
+ str += ones[one] + ' עָשָׂר';
818
+ } else if (omerDay > 9) {
819
+ str += ones[one];
820
+ if (one) {
821
+ str += ' ';
822
+ str += ten === 3 ? 'וּ' : 'וְ';
823
+ }
824
+ }
825
+ if (omerDay > 2) {
826
+ if (omerDay > 20 || omerDay === 10 || omerDay === 20) {
827
+ str += tens[ten];
828
+ }
829
+ if (omerDay < 11) {
830
+ str += ones[one] + ' ' + yamim + ' ';
831
+ } else {
832
+ str += ' ' + yom + ' ';
833
+ }
834
+ } else if (omerDay === 1) {
835
+ str += yomEchad + ' ';
836
+ } else {
837
+ // omer == 2
838
+ str += shneiYamim + ' ';
839
+ }
840
+ if (omerDay > 6) {
841
+ str = str.trim(); // remove trailing space before comma
842
+ str += ', שְׁהֵם ';
843
+ const weeks = Math.floor(omerDay / 7);
844
+ const days = omerDay % 7;
845
+ if (weeks > 2) {
846
+ str += ones[weeks] + ' ' + shavuot + ' ';
847
+ } else if (weeks === 1) {
848
+ str += 'שָׁבֽוּעַ' + ' ' + ones[1] + ' ';
849
+ } else {
850
+ // weeks == 2
851
+ str += shnei + ' ' + shavuot + ' ';
852
+ }
853
+ if (days) {
854
+ if (days === 2 || days === 3) {
855
+ str += 'וּ';
856
+ } else if (days === 5) {
857
+ str += 'וַ';
858
+ } else {
859
+ str += 'וְ';
860
+ }
861
+ if (days > 2) {
862
+ str += ones[days] + ' ' + yamim + ' ';
863
+ } else if (days === 1) {
864
+ str += yomEchad + ' ';
865
+ } else {
866
+ // days == 2
867
+ str += shneiYamim + ' ';
868
+ }
764
869
  }
765
- return num;
870
+ }
871
+ str += 'לָעֽוֹמֶר';
872
+ return str.normalize();
873
+ }
874
+ /**
875
+ * Returns an emoji number symbol with a circle, for example `㊲`
876
+ * from the “Enclosed CJK Letters and Months” block of the Unicode standard
877
+ * @param omerDay the day of the omer, 1-49 inclusive
878
+ * @returns a single Unicode character from `①` through `㊾`
879
+ */
880
+ function omerEmoji(omerDay) {
881
+ checkDay(omerDay);
882
+ if (omerDay <= 20) {
883
+ return String.fromCodePoint(9312 + omerDay - 1);
884
+ } else if (omerDay <= 35) {
885
+ // between 21 and 35 inclusive
886
+ return String.fromCodePoint(12881 + omerDay - 21);
887
+ } else {
888
+ // between 36 and 49 inclusive
889
+ return String.fromCodePoint(12977 + omerDay - 36);
890
+ }
766
891
  }
767
892
 
768
893
  const noopLocale = {
@@ -8376,9 +8501,6 @@ class MoladEvent extends Event {
8376
8501
  }
8377
8502
  }
8378
8503
 
8379
- const sefirot = [null, 'Lovingkindness', 'Might', 'Beauty', 'Eternity', 'Splendor', 'Foundation', 'Majesty'];
8380
- const sefirotTranslit = [null, 'Chesed', 'Gevurah', 'Tiferet', 'Netzach', 'Hod', 'Yesod', 'Malkhut'];
8381
-
8382
8504
  /** Represents a day 1-49 of counting the Omer from Pesach to Shavuot */
8383
8505
  class OmerEvent extends Event {
8384
8506
  /**
@@ -8399,39 +8521,10 @@ class OmerEvent extends Event {
8399
8521
  * @return {string}
8400
8522
  */
8401
8523
  sefira(lang = 'en') {
8402
- if (lang === 'he') {
8403
- return this.sefiraHe();
8404
- } else if (lang === 'translit') {
8405
- return this.sefiraTranslit();
8406
- } else {
8407
- const week = sefirot[this.weekNumber];
8408
- const dayWithinWeek = sefirot[this.daysWithinWeeks];
8409
- return `${dayWithinWeek} within ${week}`;
8524
+ if (lang !== 'he' && lang !== 'translit') {
8525
+ lang = 'en';
8410
8526
  }
8411
- }
8412
- /**
8413
- * @private
8414
- * @return {string}
8415
- */
8416
- sefiraTranslit() {
8417
- const weekNum = this.weekNumber;
8418
- const translitWeek = sefirotTranslit[weekNum];
8419
- const translitDayWithinWeek = sefirotTranslit[this.daysWithinWeeks];
8420
- const translitPrefix = weekNum === 2 || weekNum === 6 ? 'shebi' : `sheb'`;
8421
- return `${translitDayWithinWeek} ${translitPrefix}${translitWeek}`;
8422
- }
8423
- /**
8424
- * @private
8425
- * @return {string}
8426
- */
8427
- sefiraHe() {
8428
- const weekNum = this.weekNumber;
8429
- const week = sefirot[weekNum];
8430
- const dayWithinWeek = sefirot[this.daysWithinWeeks];
8431
- const heWeek = Locale.gettext(week, 'he');
8432
- const heDayWithinWeek = Locale.gettext(dayWithinWeek, 'he');
8433
- const hePrefix = weekNum === 2 || weekNum === 6 ? 'שֶׁבִּ' : 'שֶׁבְּ';
8434
- return `${heDayWithinWeek} ${hePrefix}${heWeek}`.normalize();
8527
+ return omerSefira(this.omer, lang);
8435
8528
  }
8436
8529
  /**
8437
8530
  * @todo use gettext()
@@ -8455,16 +8548,7 @@ class OmerEvent extends Event {
8455
8548
  /** @return {string} */
8456
8549
  getEmoji() {
8457
8550
  if (typeof this.emoji === 'string') return this.emoji;
8458
- const number = this.omer;
8459
- if (number <= 20) {
8460
- return String.fromCodePoint(9312 + number - 1);
8461
- } else if (number <= 35) {
8462
- // between 21 and 35 inclusive
8463
- return String.fromCodePoint(12881 + number - 21);
8464
- } else {
8465
- // between 36 and 49 inclusive
8466
- return String.fromCodePoint(12977 + number - 36);
8467
- }
8551
+ return omerEmoji(this.omer);
8468
8552
  }
8469
8553
  /** @return {number} */
8470
8554
  getWeeks() {
@@ -8485,23 +8569,12 @@ class OmerEvent extends Event {
8485
8569
  locale = locale.toLowerCase();
8486
8570
  }
8487
8571
  if (locale === 'he') {
8488
- return getTodayIsHe(this.omer);
8572
+ return omerTodayIs(this.omer, 'he');
8489
8573
  } else if (locale === 'he-x-nonikud') {
8490
- return Locale.hebrewStripNikkud(getTodayIsHe(this.omer));
8491
- }
8492
- const totalDaysStr = this.omer === 1 ? 'day' : 'days';
8493
- let str = `Today is ${this.omer} ${totalDaysStr}`;
8494
- if (this.weekNumber > 1 || this.omer === 7) {
8495
- const day7 = this.daysWithinWeeks === 7;
8496
- const numWeeks = day7 ? this.weekNumber : this.weekNumber - 1;
8497
- const weeksStr = numWeeks === 1 ? 'week' : 'weeks';
8498
- str += `, which is ${numWeeks} ${weeksStr}`;
8499
- if (!day7) {
8500
- const daysStr = this.daysWithinWeeks === 1 ? 'day' : 'days';
8501
- str += ` and ${this.daysWithinWeeks} ${daysStr}`;
8502
- }
8574
+ const str = omerTodayIs(this.omer, 'he');
8575
+ return Locale.hebrewStripNikkud(str);
8503
8576
  }
8504
- return str + ' of the Omer';
8577
+ return omerTodayIs(this.omer, 'en');
8505
8578
  }
8506
8579
  /** @return {string} */
8507
8580
  url() {
@@ -8509,79 +8582,6 @@ class OmerEvent extends Event {
8509
8582
  }
8510
8583
  }
8511
8584
 
8512
- // adapted from pip hdate package (GPL)
8513
- // https://github.com/py-libhdate/py-libhdate/blob/master/hdate/date.py
8514
-
8515
- const tens = ['', 'עֲשָׂרָה', 'עֶשְׂרִים', 'שְׁלוֹשִׁים', 'אַרְבָּעִים'];
8516
- const ones = ['', 'אֶחָד', 'שְׁנַיִם', 'שְׁלוֹשָׁה', 'אַרְבָּעָה', 'חֲמִשָׁה', 'שִׁשָׁה', 'שִׁבְעָה', 'שְׁמוֹנָה', 'תִּשְׁעָה'];
8517
- const shnei = 'שְׁנֵי';
8518
- const yamim = 'יָמִים';
8519
- const shneiYamim = shnei + ' ' + yamim;
8520
- const shavuot = 'שָׁבוּעוֹת';
8521
- const yom = 'יוֹם';
8522
- const yomEchad = yom + ' ' + ones[1];
8523
-
8524
- /**
8525
- * @private
8526
- * @param {number} omer
8527
- * @return {string}
8528
- */
8529
- function getTodayIsHe(omer) {
8530
- const ten = Math.floor(omer / 10);
8531
- const one = omer % 10;
8532
- let str = 'הַיוֹם ';
8533
- if (10 < omer && omer < 20) {
8534
- str += ones[one] + ' עָשָׂר';
8535
- } else if (omer > 9) {
8536
- str += ones[one];
8537
- if (one) {
8538
- str += ' וְ';
8539
- }
8540
- }
8541
- if (omer > 2) {
8542
- if (omer > 20 || omer === 10 || omer === 20) {
8543
- str += tens[ten];
8544
- }
8545
- if (omer < 11) {
8546
- str += ones[one] + ' ' + yamim + ' ';
8547
- } else {
8548
- str += ' ' + yom + ' ';
8549
- }
8550
- } else if (omer === 1) {
8551
- str += yomEchad + ' ';
8552
- } else {
8553
- // omer == 2
8554
- str += shneiYamim + ' ';
8555
- }
8556
- if (omer > 6) {
8557
- str = str.trim(); // remove trailing space before comma
8558
- str += ', שְׁהֵם ';
8559
- const weeks = Math.floor(omer / 7);
8560
- const days = omer % 7;
8561
- if (weeks > 2) {
8562
- str += ones[weeks] + ' ' + shavuot + ' ';
8563
- } else if (weeks == 1) {
8564
- str += 'שָׁבוּעַ' + ' ' + ones[1] + ' ';
8565
- } else {
8566
- // weeks == 2
8567
- str += shnei + ' ' + shavuot + ' ';
8568
- }
8569
- if (days) {
8570
- str += 'וְ';
8571
- if (days > 2) {
8572
- str += ones[days] + ' ' + yamim + ' ';
8573
- } else if (days == 1) {
8574
- str += yomEchad + ' ';
8575
- } else {
8576
- // days == 2
8577
- str += shneiYamim + ' ';
8578
- }
8579
- }
8580
- }
8581
- str += 'לָעוֹמֶר';
8582
- return str.normalize();
8583
- }
8584
-
8585
8585
  class QuickLRU extends Map {
8586
8586
  #size = 0;
8587
8587
  #cache = new Map();
@@ -10355,7 +10355,7 @@ class DailyLearning {
10355
10355
  }
10356
10356
 
10357
10357
  // DO NOT EDIT THIS AUTO-GENERATED FILE!
10358
- const version = '5.3.3';
10358
+ const version = '5.3.4';
10359
10359
 
10360
10360
  const NONE$1 = 0;
10361
10361
  const HALF = 1;