@hebcal/core 5.3.2 → 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.mjs CHANGED
@@ -1,23 +1,37 @@
1
- /*! @hebcal/core v5.3.2 */
1
+ /*! @hebcal/core v5.3.4 */
2
+ /* eslint-disable @typescript-eslint/no-namespace, no-inner-declarations */
2
3
  /** @private */
3
4
  const lengths = [0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31];
4
5
  /** @private */
5
- const monthLengths = [
6
- lengths,
7
- lengths.slice(),
8
- ];
6
+ const monthLengths = [lengths, lengths.slice()];
9
7
  monthLengths[1][2] = 29;
10
8
  /**
11
9
  * @private
12
10
  */
13
11
  function mod$1(x, y) {
14
- return x - y * Math.floor(x / y);
12
+ return x - y * Math.floor(x / y);
15
13
  }
16
14
  /**
17
15
  * @private
18
16
  */
19
17
  function quotient(x, y) {
20
- return Math.floor(x / y);
18
+ return Math.floor(x / y);
19
+ }
20
+ /**
21
+ * @private
22
+ * @param abs - R.D. number of days
23
+ */
24
+ function yearFromFixed(abs) {
25
+ const l0 = abs - 1;
26
+ const n400 = quotient(l0, 146097);
27
+ const d1 = mod$1(l0, 146097);
28
+ const n100 = quotient(d1, 36524);
29
+ const d2 = mod$1(d1, 36524);
30
+ const n4 = quotient(d2, 1461);
31
+ const d3 = mod$1(d2, 1461);
32
+ const n1 = quotient(d3, 365);
33
+ const year = 400 * n400 + 100 * n100 + 4 * n4 + n1;
34
+ return n100 !== 4 && n1 !== 4 ? year + 1 : year;
21
35
  }
22
36
  /*
23
37
  const ABS_14SEP1752 = 639797;
@@ -28,116 +42,95 @@ const ABS_2SEP1752 = 639785;
28
42
  */
29
43
  var greg;
30
44
  (function (greg) {
31
- /**
32
- * Returns true if the Gregorian year is a leap year
33
- * @param {number} year Gregorian year
34
- * @return {boolean}
35
- */
36
- function isLeapYear(year) {
37
- return !(year % 4) && (!!(year % 100) || !(year % 400));
38
- }
39
- greg.isLeapYear = isLeapYear;
40
- /**
41
- * Number of days in the Gregorian month for given year
42
- * @param {number} month Gregorian month (1=January, 12=December)
43
- * @param {number} year Gregorian year
44
- * @return {number}
45
- */
46
- function daysInMonth(month, year) {
47
- // 1 based months
48
- return monthLengths[+isLeapYear(year)][month];
49
- }
50
- greg.daysInMonth = daysInMonth;
51
- /**
52
- * Returns true if the object is a Javascript Date
53
- * @param {Object} obj
54
- * @return {boolean}
55
- */
56
- function isDate(obj) {
57
- return typeof obj === 'object' && Date.prototype.isPrototypeOf(obj);
58
- }
59
- greg.isDate = isDate;
60
- /**
61
- * @private
62
- * @param abs - R.D. number of days
63
- */
64
- function yearFromFixed(abs) {
65
- const l0 = abs - 1;
66
- const n400 = quotient(l0, 146097);
67
- const d1 = mod$1(l0, 146097);
68
- const n100 = quotient(d1, 36524);
69
- const d2 = mod$1(d1, 36524);
70
- const n4 = quotient(d2, 1461);
71
- const d3 = mod$1(d2, 1461);
72
- const n1 = quotient(d3, 365);
73
- const year = 400 * n400 + 100 * n100 + 4 * n4 + n1;
74
- return n100 != 4 && n1 != 4 ? year + 1 : year;
45
+ /**
46
+ * Returns true if the Gregorian year is a leap year
47
+ * @param {number} year Gregorian year
48
+ * @return {boolean}
49
+ */
50
+ function isLeapYear(year) {
51
+ return !(year % 4) && (!!(year % 100) || !(year % 400));
52
+ }
53
+ greg.isLeapYear = isLeapYear;
54
+ /**
55
+ * Number of days in the Gregorian month for given year
56
+ * @param {number} month Gregorian month (1=January, 12=December)
57
+ * @param {number} year Gregorian year
58
+ * @return {number}
59
+ */
60
+ function daysInMonth(month, year) {
61
+ // 1 based months
62
+ return monthLengths[+isLeapYear(year)][month];
63
+ }
64
+ greg.daysInMonth = daysInMonth;
65
+ /**
66
+ * Returns true if the object is a Javascript Date
67
+ * @param {Object} obj
68
+ * @return {boolean}
69
+ */
70
+ function isDate(obj) {
71
+ // eslint-disable-next-line no-prototype-builtins
72
+ return typeof obj === 'object' && Date.prototype.isPrototypeOf(obj);
73
+ }
74
+ greg.isDate = isDate;
75
+ /**
76
+ * @private
77
+ * @param year
78
+ * @param month (1-12)
79
+ * @param day (1-31)
80
+ */
81
+ function toFixed(year, month, day) {
82
+ const py = year - 1;
83
+ 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;
84
+ }
85
+ /**
86
+ * Converts Gregorian date to absolute R.D. (Rata Die) days
87
+ * @param {Date} date Gregorian date
88
+ * @return {number}
89
+ */
90
+ function greg2abs(date) {
91
+ if (!isDate(date)) {
92
+ throw new TypeError(`Argument not a Date: ${date}`);
75
93
  }
76
- /**
77
- * @private
78
- * @param year
79
- * @param month (1-12)
80
- * @param day (1-31)
81
- */
82
- function toFixed(year, month, day) {
83
- const py = year - 1;
84
- return 365 * py +
85
- quotient(py, 4) -
86
- quotient(py, 100) +
87
- quotient(py, 400) +
88
- quotient((367 * month - 362), 12) +
89
- (month <= 2 ? 0 : (isLeapYear(year) ? -1 : -2)) +
90
- day;
94
+ const abs = toFixed(date.getFullYear(), date.getMonth() + 1, date.getDate());
95
+ /*
96
+ if (abs < ABS_14SEP1752 && abs > ABS_2SEP1752) {
97
+ throw new RangeError(`Invalid Date: ${date}`);
91
98
  }
92
- /**
93
- * Converts Gregorian date to absolute R.D. (Rata Die) days
94
- * @param {Date} date Gregorian date
95
- * @return {number}
96
- */
97
- function greg2abs(date) {
98
- if (!isDate(date)) {
99
- throw new TypeError(`Argument not a Date: ${date}`);
100
- }
101
- const abs = toFixed(date.getFullYear(), date.getMonth() + 1, date.getDate());
102
- /*
103
- if (abs < ABS_14SEP1752 && abs > ABS_2SEP1752) {
104
- throw new RangeError(`Invalid Date: ${date}`);
105
- }
106
- */
107
- return abs;
99
+ */
100
+ return abs;
101
+ }
102
+ greg.greg2abs = greg2abs;
103
+ /**
104
+ * Converts from Rata Die (R.D. number) to Gregorian date.
105
+ * See the footnote on page 384 of ``Calendrical Calculations, Part II:
106
+ * Three Historical Calendars'' by E. M. Reingold, N. Dershowitz, and S. M.
107
+ * Clamen, Software--Practice and Experience, Volume 23, Number 4
108
+ * (April, 1993), pages 383-404 for an explanation.
109
+ * @param {number} abs - R.D. number of days
110
+ * @return {Date}
111
+ */
112
+ function abs2greg(abs) {
113
+ if (typeof abs !== 'number') {
114
+ throw new TypeError(`Argument not a Number: ${abs}`);
108
115
  }
109
- greg.greg2abs = greg2abs;
110
- /**
111
- * Converts from Rata Die (R.D. number) to Gregorian date.
112
- * See the footnote on page 384 of ``Calendrical Calculations, Part II:
113
- * Three Historical Calendars'' by E. M. Reingold, N. Dershowitz, and S. M.
114
- * Clamen, Software--Practice and Experience, Volume 23, Number 4
115
- * (April, 1993), pages 383-404 for an explanation.
116
- * @param {number} abs - R.D. number of days
117
- * @return {Date}
118
- */
119
- function abs2greg(abs) {
120
- if (typeof abs !== 'number') {
121
- throw new TypeError(`Argument not a Number: ${abs}`);
122
- }
123
- abs = Math.trunc(abs);
124
- /*
125
- if (abs < ABS_14SEP1752 && abs > ABS_2SEP1752) {
126
- throw new RangeError(`Invalid Date: ${abs}`);
127
- }
128
- */
129
- const year = yearFromFixed(abs);
130
- const priorDays = abs - toFixed(year, 1, 1);
131
- const correction = abs < toFixed(year, 3, 1) ? 0 : (isLeapYear(year) ? 1 : 2);
132
- const month = quotient((12 * (priorDays + correction) + 373), 367);
133
- const day = abs - toFixed(year, month, 1) + 1;
134
- const dt = new Date(year, month - 1, day);
135
- if (year < 100 && year >= 0) {
136
- dt.setFullYear(year);
137
- }
138
- return dt;
116
+ abs = Math.trunc(abs);
117
+ /*
118
+ if (abs < ABS_14SEP1752 && abs > ABS_2SEP1752) {
119
+ throw new RangeError(`Invalid Date: ${abs}`);
139
120
  }
140
- greg.abs2greg = abs2greg;
121
+ */
122
+ const year = yearFromFixed(abs);
123
+ const priorDays = abs - toFixed(year, 1, 1);
124
+ const correction = abs < toFixed(year, 3, 1) ? 0 : isLeapYear(year) ? 1 : 2;
125
+ const month = quotient(12 * (priorDays + correction) + 373, 367);
126
+ const day = abs - toFixed(year, month, 1) + 1;
127
+ const dt = new Date(year, month - 1, day);
128
+ if (year < 100 && year >= 0) {
129
+ dt.setFullYear(year);
130
+ }
131
+ return dt;
132
+ }
133
+ greg.abs2greg = abs2greg;
141
134
  })(greg || (greg = {}));
142
135
 
143
136
  /*
@@ -162,63 +155,40 @@ const ADAR_II$2 = 13;
162
155
  * @enum {number}
163
156
  */
164
157
  const months = {
165
- /** Nissan / ניסן */
166
- NISAN: 1,
167
- /** Iyyar / אייר */
168
- IYYAR: 2,
169
- /** Sivan / סיון */
170
- SIVAN: 3,
171
- /** Tamuz (sometimes Tammuz) / תמוז */
172
- TAMUZ: 4,
173
- /** Av / אב */
174
- AV: 5,
175
- /** Elul / אלול */
176
- ELUL: 6,
177
- /** Tishrei / תִּשְׁרֵי */
178
- TISHREI: 7,
179
- /** Cheshvan / חשון */
180
- CHESHVAN: 8,
181
- /** Kislev / כסלו */
182
- KISLEV: 9,
183
- /** Tevet / טבת */
184
- TEVET: 10,
185
- /** Sh'vat / שבט */
186
- SHVAT: 11,
187
- /** Adar or Adar Rishon / אדר */
188
- ADAR_I: 12,
189
- /** Adar Sheini (only on leap years) / אדר ב׳ */
190
- ADAR_II: 13,
158
+ /** Nissan / ניסן */
159
+ NISAN: 1,
160
+ /** Iyyar / אייר */
161
+ IYYAR: 2,
162
+ /** Sivan / סיון */
163
+ SIVAN: 3,
164
+ /** Tamuz (sometimes Tammuz) / תמוז */
165
+ TAMUZ: 4,
166
+ /** Av / אב */
167
+ AV: 5,
168
+ /** Elul / אלול */
169
+ ELUL: 6,
170
+ /** Tishrei / תִּשְׁרֵי */
171
+ TISHREI: 7,
172
+ /** Cheshvan / חשון */
173
+ CHESHVAN: 8,
174
+ /** Kislev / כסלו */
175
+ KISLEV: 9,
176
+ /** Tevet / טבת */
177
+ TEVET: 10,
178
+ /** Sh'vat / שבט */
179
+ SHVAT: 11,
180
+ /** Adar or Adar Rishon / אדר */
181
+ ADAR_I: 12,
182
+ /** Adar Sheini (only on leap years) / אדר ב׳ */
183
+ ADAR_II: 13
191
184
  };
192
- const monthNames0 = [
193
- '',
194
- 'Nisan',
195
- 'Iyyar',
196
- 'Sivan',
197
- 'Tamuz',
198
- 'Av',
199
- 'Elul',
200
- 'Tishrei',
201
- 'Cheshvan',
202
- 'Kislev',
203
- 'Tevet',
204
- 'Sh\'vat',
205
- ];
185
+ const monthNames0 = ['', 'Nisan', 'Iyyar', 'Sivan', 'Tamuz', 'Av', 'Elul', 'Tishrei', 'Cheshvan', 'Kislev', 'Tevet', "Sh'vat"];
206
186
  /**
207
187
  * Transliterations of Hebrew month names.
208
188
  * Regular years are index 0 and leap years are index 1.
209
189
  * @private
210
190
  */
211
- const monthNames = [
212
- monthNames0.concat([
213
- 'Adar',
214
- 'Nisan',
215
- ]),
216
- monthNames0.concat([
217
- 'Adar I',
218
- 'Adar II',
219
- 'Nisan',
220
- ]),
221
- ];
191
+ const monthNames = [monthNames0.concat(['Adar', 'Nisan']), monthNames0.concat(['Adar I', 'Adar II', 'Nisan'])];
222
192
  const edCache = new Map();
223
193
  const EPOCH = -1373428;
224
194
  // Avg year length in the cycle (19 solar years with 235 lunar months)
@@ -227,9 +197,9 @@ const AVG_HEBYEAR_DAYS = 365.24682220597794;
227
197
  * @private
228
198
  */
229
199
  function assertNumber(n, name) {
230
- if (typeof n !== 'number' || isNaN(n)) {
231
- throw new TypeError(`invalid parameter '${name}' not a number: ${n}`);
232
- }
200
+ if (typeof n !== 'number' || isNaN(n)) {
201
+ throw new TypeError(`invalid parameter '${name}' not a number: ${n}`);
202
+ }
233
203
  }
234
204
  /**
235
205
  * Converts Hebrew date to R.D. (Rata Die) fixed days.
@@ -241,33 +211,32 @@ function assertNumber(n, name) {
241
211
  * @return {number}
242
212
  */
243
213
  function hebrew2abs(year, month, day) {
244
- assertNumber(year, 'year');
245
- assertNumber(month, 'month');
246
- assertNumber(day, 'day');
247
- if (year < 1) {
248
- throw new RangeError(`hebrew2abs: invalid year ${year}`);
249
- }
250
- let tempabs = day;
251
- if (month < TISHREI$2) {
252
- for (let m = TISHREI$2; m <= monthsInYear(year); m++) {
253
- tempabs += daysInMonth(m, year);
254
- }
255
- for (let m = NISAN$4; m < month; m++) {
256
- tempabs += daysInMonth(m, year);
257
- }
214
+ assertNumber(year, 'year');
215
+ assertNumber(month, 'month');
216
+ assertNumber(day, 'day');
217
+ if (year < 1) {
218
+ throw new RangeError(`hebrew2abs: invalid year ${year}`);
219
+ }
220
+ let tempabs = day;
221
+ if (month < TISHREI$2) {
222
+ for (let m = TISHREI$2; m <= monthsInYear(year); m++) {
223
+ tempabs += daysInMonth(m, year);
258
224
  }
259
- else {
260
- for (let m = TISHREI$2; m < month; m++) {
261
- tempabs += daysInMonth(m, year);
262
- }
225
+ for (let m = NISAN$4; m < month; m++) {
226
+ tempabs += daysInMonth(m, year);
227
+ }
228
+ } else {
229
+ for (let m = TISHREI$2; m < month; m++) {
230
+ tempabs += daysInMonth(m, year);
263
231
  }
264
- return EPOCH + elapsedDays(year) + tempabs - 1;
232
+ }
233
+ return EPOCH + elapsedDays(year) + tempabs - 1;
265
234
  }
266
235
  /**
267
236
  * @private
268
237
  */
269
238
  function newYear(year) {
270
- return EPOCH + elapsedDays(year);
239
+ return EPOCH + elapsedDays(year);
271
240
  }
272
241
  /**
273
242
  * Converts absolute R.D. days to Hebrew date
@@ -275,23 +244,27 @@ function newYear(year) {
275
244
  * @return {SimpleHebrewDate}
276
245
  */
277
246
  function abs2hebrew(abs) {
278
- assertNumber(abs, 'abs');
279
- abs = Math.trunc(abs);
280
- if (abs <= EPOCH) {
281
- throw new RangeError(`abs2hebrew: ${abs} is before epoch`);
282
- }
283
- // first, quickly approximate year
284
- let year = Math.floor((abs - EPOCH) / AVG_HEBYEAR_DAYS);
285
- while (newYear(year) <= abs) {
286
- ++year;
287
- }
288
- --year;
289
- let month = abs < hebrew2abs(year, 1, 1) ? 7 : 1;
290
- while (abs > hebrew2abs(year, month, daysInMonth(month, year))) {
291
- ++month;
292
- }
293
- const day = 1 + abs - hebrew2abs(year, month, 1);
294
- return { yy: year, mm: month, dd: day };
247
+ assertNumber(abs, 'abs');
248
+ abs = Math.trunc(abs);
249
+ if (abs <= EPOCH) {
250
+ throw new RangeError(`abs2hebrew: ${abs} is before epoch`);
251
+ }
252
+ // first, quickly approximate year
253
+ let year = Math.floor((abs - EPOCH) / AVG_HEBYEAR_DAYS);
254
+ while (newYear(year) <= abs) {
255
+ ++year;
256
+ }
257
+ --year;
258
+ let month = abs < hebrew2abs(year, 1, 1) ? 7 : 1;
259
+ while (abs > hebrew2abs(year, month, daysInMonth(month, year))) {
260
+ ++month;
261
+ }
262
+ const day = 1 + abs - hebrew2abs(year, month, 1);
263
+ return {
264
+ yy: year,
265
+ mm: month,
266
+ dd: day
267
+ };
295
268
  }
296
269
  /**
297
270
  * Returns true if Hebrew year is a leap year
@@ -299,7 +272,7 @@ function abs2hebrew(abs) {
299
272
  * @return {boolean}
300
273
  */
301
274
  function isLeapYear(year) {
302
- return (1 + year * 7) % 19 < 7;
275
+ return (1 + year * 7) % 19 < 7;
303
276
  }
304
277
  /**
305
278
  * Number of months in this Hebrew year (either 12 or 13 depending on leap year)
@@ -307,7 +280,7 @@ function isLeapYear(year) {
307
280
  * @return {number}
308
281
  */
309
282
  function monthsInYear(year) {
310
- return 12 + +(isLeapYear(year)); // boolean is cast to 1 or 0
283
+ return 12 + +isLeapYear(year); // boolean is cast to 1 or 0
311
284
  }
312
285
  /**
313
286
  * Number of days in Hebrew month in a given year (29 or 30)
@@ -316,22 +289,19 @@ function monthsInYear(year) {
316
289
  * @return {number}
317
290
  */
318
291
  function daysInMonth(month, year) {
319
- switch (month) {
320
- case IYYAR$1:
321
- case TAMUZ$1:
322
- case ELUL$1:
323
- case TEVET$2:
324
- case ADAR_II$2:
325
- return 29;
326
- }
327
- if ((month === ADAR_I$2 && !isLeapYear(year)) ||
328
- (month === CHESHVAN$1 && !longCheshvan(year)) ||
329
- (month === KISLEV$2 && shortKislev(year))) {
330
- return 29;
331
- }
332
- else {
333
- return 30;
334
- }
292
+ switch (month) {
293
+ case IYYAR$1:
294
+ case TAMUZ$1:
295
+ case ELUL$1:
296
+ case TEVET$2:
297
+ case ADAR_II$2:
298
+ return 29;
299
+ }
300
+ if (month === ADAR_I$2 && !isLeapYear(year) || month === CHESHVAN$1 && !longCheshvan(year) || month === KISLEV$2 && shortKislev(year)) {
301
+ return 29;
302
+ } else {
303
+ return 30;
304
+ }
335
305
  }
336
306
  /**
337
307
  * Returns a transliterated string name of Hebrew month in year,
@@ -340,12 +310,12 @@ function daysInMonth(month, year) {
340
310
  * @param {number} year Hebrew year
341
311
  */
342
312
  function getMonthName(month, year) {
343
- assertNumber(month, 'month');
344
- assertNumber(year, 'year');
345
- if (month < 1 || month > 14) {
346
- throw new TypeError(`bad month argument ${month}`);
347
- }
348
- return monthNames[+isLeapYear(year)][month];
313
+ assertNumber(month, 'month');
314
+ assertNumber(year, 'year');
315
+ if (month < 1 || month > 14) {
316
+ throw new TypeError(`bad month argument ${month}`);
317
+ }
318
+ return monthNames[+isLeapYear(year)][month];
349
319
  }
350
320
  /**
351
321
  * Days from sunday prior to start of Hebrew calendar to mean
@@ -354,13 +324,13 @@ function getMonthName(month, year) {
354
324
  * @return {number}
355
325
  */
356
326
  function elapsedDays(year) {
357
- const n = edCache.get(year);
358
- if (typeof n === 'number') {
359
- return n;
360
- }
361
- const elapsed = elapsedDays0(year);
362
- edCache.set(year, elapsed);
363
- return elapsed;
327
+ const n = edCache.get(year);
328
+ if (typeof n === 'number') {
329
+ return n;
330
+ }
331
+ const elapsed = elapsedDays0(year);
332
+ edCache.set(year, elapsed);
333
+ return elapsed;
364
334
  }
365
335
  /**
366
336
  * Days from sunday prior to start of Hebrew calendar to mean
@@ -369,29 +339,25 @@ function elapsedDays(year) {
369
339
  * @param year Hebrew year
370
340
  */
371
341
  function elapsedDays0(year) {
372
- const prevYear = year - 1;
373
- const mElapsed = 235 * Math.floor(prevYear / 19) + // Months in complete 19 year lunar (Metonic) cycles so far
374
- 12 * (prevYear % 19) + // Regular months in this cycle
375
- Math.floor(((prevYear % 19) * 7 + 1) / 19); // Leap months this cycle
376
- const pElapsed = 204 + 793 * (mElapsed % 1080);
377
- const hElapsed = 5 +
378
- 12 * mElapsed +
379
- 793 * Math.floor(mElapsed / 1080) +
380
- Math.floor(pElapsed / 1080);
381
- const parts = (pElapsed % 1080) + 1080 * (hElapsed % 24);
382
- const day = 1 + 29 * mElapsed + Math.floor(hElapsed / 24);
383
- let altDay = day;
384
- if (parts >= 19440 ||
385
- (2 === day % 7 && parts >= 9924 && !isLeapYear(year)) ||
386
- (1 === day % 7 && parts >= 16789 && isLeapYear(prevYear))) {
387
- altDay++;
388
- }
389
- if (altDay % 7 === 0 || altDay % 7 === 3 || altDay % 7 === 5) {
390
- return altDay + 1;
391
- }
392
- else {
393
- return altDay;
394
- }
342
+ const prevYear = year - 1;
343
+ const mElapsed = 235 * Math.floor(prevYear / 19) +
344
+ // Months in complete 19 year lunar (Metonic) cycles so far
345
+ 12 * (prevYear % 19) +
346
+ // Regular months in this cycle
347
+ Math.floor((prevYear % 19 * 7 + 1) / 19); // Leap months this cycle
348
+ const pElapsed = 204 + 793 * (mElapsed % 1080);
349
+ const hElapsed = 5 + 12 * mElapsed + 793 * Math.floor(mElapsed / 1080) + Math.floor(pElapsed / 1080);
350
+ const parts = pElapsed % 1080 + 1080 * (hElapsed % 24);
351
+ const day = 1 + 29 * mElapsed + Math.floor(hElapsed / 24);
352
+ let altDay = day;
353
+ if (parts >= 19440 || 2 === day % 7 && parts >= 9924 && !isLeapYear(year) || 1 === day % 7 && parts >= 16789 && isLeapYear(prevYear)) {
354
+ altDay++;
355
+ }
356
+ if (altDay % 7 === 0 || altDay % 7 === 3 || altDay % 7 === 5) {
357
+ return altDay + 1;
358
+ } else {
359
+ return altDay;
360
+ }
395
361
  }
396
362
  /**
397
363
  * Number of days in the hebrew YEAR.
@@ -401,7 +367,7 @@ function elapsedDays0(year) {
401
367
  * @return {number}
402
368
  */
403
369
  function daysInYear(year) {
404
- return elapsedDays(year + 1) - elapsedDays(year);
370
+ return elapsedDays(year + 1) - elapsedDays(year);
405
371
  }
406
372
  /**
407
373
  * true if Cheshvan is long in Hebrew year
@@ -409,7 +375,7 @@ function daysInYear(year) {
409
375
  * @return {boolean}
410
376
  */
411
377
  function longCheshvan(year) {
412
- return daysInYear(year) % 10 === 5;
378
+ return daysInYear(year) % 10 === 5;
413
379
  }
414
380
  /**
415
381
  * true if Kislev is short in Hebrew year
@@ -417,7 +383,7 @@ function longCheshvan(year) {
417
383
  * @return {boolean}
418
384
  */
419
385
  function shortKislev(year) {
420
- return daysInYear(year) % 10 === 3;
386
+ return daysInYear(year) % 10 === 3;
421
387
  }
422
388
  /**
423
389
  * Converts Hebrew month string name to numeric
@@ -425,116 +391,116 @@ function shortKislev(year) {
425
391
  * @return {number}
426
392
  */
427
393
  function monthFromName(monthName) {
428
- if (typeof monthName === 'number') {
429
- if (isNaN(monthName) || monthName < 1 || monthName > 14) {
430
- throw new RangeError(`Invalid month name: ${monthName}`);
431
- }
432
- return monthName;
433
- }
434
- let c = monthName.trim().toLowerCase();
435
- // If Hebrew month starts with a bet (for example `בתמוז`) then ignore it
436
- if (c[0] === 'ב') {
437
- c = c.substring(1);
438
- }
439
- /*
440
- the Hebrew months are unique to their second letter
441
- N Nisan (November?)
442
- I Iyyar
443
- E Elul
444
- C Cheshvan
445
- K Kislev
446
- 1 1Adar
447
- 2 2Adar
448
- Si Sh Sivan, Shvat
449
- Ta Ti Te Tamuz, Tishrei, Tevet
450
- Av Ad Av, Adar
451
-
452
- אב אד אי אל אב אדר אייר אלול
453
- ח חשון
454
- ט טבת
455
- כ כסלו
456
- נ ניסן
457
- ס סיון
458
- ש שבט
459
- תמ תש תמוז תשרי
460
- */
461
- switch (c[0]) {
462
- case 'n':
463
- case 'נ':
464
- if (c[1] == 'o') {
465
- break; /* this catches "november" */
466
- }
467
- return months.NISAN;
394
+ if (typeof monthName === 'number') {
395
+ if (isNaN(monthName) || monthName < 1 || monthName > 14) {
396
+ throw new RangeError(`Invalid month name: ${monthName}`);
397
+ }
398
+ return monthName;
399
+ }
400
+ let c = monthName.trim().toLowerCase();
401
+ // If Hebrew month starts with a bet (for example `בתמוז`) then ignore it
402
+ if (c[0] === 'ב') {
403
+ c = c.substring(1);
404
+ }
405
+ /*
406
+ the Hebrew months are unique to their second letter
407
+ N Nisan (November?)
408
+ I Iyyar
409
+ E Elul
410
+ C Cheshvan
411
+ K Kislev
412
+ 1 1Adar
413
+ 2 2Adar
414
+ Si Sh Sivan, Shvat
415
+ Ta Ti Te Tamuz, Tishrei, Tevet
416
+ Av Ad Av, Adar
417
+ אב אד אי אל אב אדר אייר אלול
418
+ ח חשון
419
+ ט טבת
420
+ כ כסלו
421
+ נ ניסן
422
+ ס סיון
423
+ ש שבט
424
+ תמ תש תמוז תשרי
425
+ */
426
+ switch (c[0]) {
427
+ case 'n':
428
+ case 'נ':
429
+ if (c[1] === 'o') {
430
+ break; /* this catches "november" */
431
+ }
432
+ return months.NISAN;
433
+ case 'i':
434
+ return months.IYYAR;
435
+ case 'e':
436
+ return months.ELUL;
437
+ case 'c':
438
+ case 'ח':
439
+ return months.CHESHVAN;
440
+ case 'k':
441
+ case 'כ':
442
+ return months.KISLEV;
443
+ case 's':
444
+ switch (c[1]) {
468
445
  case 'i':
469
- return months.IYYAR;
470
- case 'e':
471
- return months.ELUL;
472
- case 'c':
473
- case 'ח':
474
- return months.CHESHVAN;
475
- case 'k':
476
- case 'כ':
477
- return months.KISLEV;
478
- case 's':
479
- switch (c[1]) {
480
- case 'i':
481
- return months.SIVAN;
482
- case 'h':
483
- return months.SHVAT;
484
- }
485
- break;
486
- case 't':
487
- switch (c[1]) {
488
- case 'a':
489
- return months.TAMUZ;
490
- case 'i':
491
- return months.TISHREI;
492
- case 'e':
493
- return months.TEVET;
494
- }
495
- break;
446
+ return months.SIVAN;
447
+ case 'h':
448
+ return months.SHVAT;
449
+ }
450
+ break;
451
+ case 't':
452
+ switch (c[1]) {
496
453
  case 'a':
497
- switch (c[1]) {
498
- case 'v':
499
- return months.AV;
500
- case 'd':
501
- if (/(1|[^i]i|a|א)$/i.test(monthName)) {
502
- return months.ADAR_I;
503
- }
504
- return months.ADAR_II; // else assume sheini
505
- }
506
- break;
507
- case 'ס':
508
- return months.SIVAN;
509
- case 'ט':
510
- return months.TEVET;
454
+ return months.TAMUZ;
455
+ case 'i':
456
+ return months.TISHREI;
457
+ case 'e':
458
+ return months.TEVET;
459
+ }
460
+ break;
461
+ case 'a':
462
+ switch (c[1]) {
463
+ case 'v':
464
+ return months.AV;
465
+ case 'd':
466
+ if (/(1|[^i]i|a|א)$/i.test(monthName)) {
467
+ return months.ADAR_I;
468
+ }
469
+ return months.ADAR_II;
470
+ }
471
+ break;
472
+ case 'ס':
473
+ return months.SIVAN;
474
+ case 'ט':
475
+ return months.TEVET;
476
+ case 'ש':
477
+ return months.SHVAT;
478
+ case 'א':
479
+ switch (c[1]) {
480
+ case 'ב':
481
+ return months.AV;
482
+ case 'ד':
483
+ if (/(1|[^i]i|a|א)$/i.test(monthName)) {
484
+ return months.ADAR_I;
485
+ }
486
+ return months.ADAR_II;
487
+ // else assume sheini
488
+ case 'י':
489
+ return months.IYYAR;
490
+ case 'ל':
491
+ return months.ELUL;
492
+ }
493
+ break;
494
+ case 'ת':
495
+ switch (c[1]) {
496
+ case 'מ':
497
+ return months.TAMUZ;
511
498
  case 'ש':
512
- return months.SHVAT;
513
- case 'א':
514
- switch (c[1]) {
515
- case 'ב':
516
- return months.AV;
517
- case 'ד':
518
- if (/(1|[^i]i|a|א)$/i.test(monthName)) {
519
- return months.ADAR_I;
520
- }
521
- return months.ADAR_II; // else assume sheini
522
- case 'י':
523
- return months.IYYAR;
524
- case 'ל':
525
- return months.ELUL;
526
- }
527
- break;
528
- case 'ת':
529
- switch (c[1]) {
530
- case 'מ':
531
- return months.TAMUZ;
532
- case 'ש':
533
- return months.TISHREI;
534
- }
535
- break;
536
- }
537
- throw new RangeError(`Unable to parse month name: ${monthName}`);
499
+ return months.TISHREI;
500
+ }
501
+ break;
502
+ }
503
+ throw new RangeError(`Unable to parse month name: ${monthName}`);
538
504
  }
539
505
 
540
506
  const NISAN$3 = months.NISAN;
@@ -545,155 +511,145 @@ const SHVAT = months.SHVAT;
545
511
  const ADAR_I$1 = months.ADAR_I;
546
512
  const ADAR_II$1 = months.ADAR_II;
547
513
  /**
548
- * Returns true if the object is a Javascript Date
514
+ * Returns true if the object is a SimpleHebrewDate
549
515
  * @private
550
516
  * @param {Object} obj
551
517
  */
552
518
  function isSimpleHebrewDate(obj) {
553
- return typeof obj === 'object' && obj !== null &&
554
- typeof obj.yy === 'number' &&
555
- typeof obj.mm === 'number' &&
556
- typeof obj.dd === 'number';
519
+ return typeof obj === 'object' && obj !== null && typeof obj.yy === 'number' && typeof obj.mm === 'number' && typeof obj.dd === 'number';
557
520
  }
558
521
  /**
559
522
  * @private
560
523
  */
561
524
  function toSimpleHebrewDate(obj) {
562
- if (isSimpleHebrewDate(obj)) {
563
- return obj;
564
- }
565
- else if (typeof obj === 'number') {
566
- return abs2hebrew(obj);
567
- }
568
- else if (greg.isDate(obj)) {
569
- const abs = greg.greg2abs(obj);
570
- return abs2hebrew(abs);
571
- }
572
- else {
573
- throw new TypeError(`Argument not a Date: ${obj}`);
574
- }
525
+ if (isSimpleHebrewDate(obj)) {
526
+ return obj;
527
+ } else if (typeof obj === 'number') {
528
+ return abs2hebrew(obj);
529
+ } else if (greg.isDate(obj)) {
530
+ const abs = greg.greg2abs(obj);
531
+ return abs2hebrew(abs);
532
+ } else {
533
+ throw new TypeError(`Argument not a Date: ${obj}`);
534
+ }
575
535
  }
576
536
  function getYahrzeitHD(hyear, date) {
577
- let hDeath = toSimpleHebrewDate(date);
578
- if (hyear <= hDeath.yy) {
579
- // Hebrew year ${hyear} occurs on or before original date in ${hDeath.yy}
580
- return undefined;
581
- }
582
- if (hDeath.mm == CHESHVAN && hDeath.dd == 30 && !longCheshvan(hDeath.yy + 1)) {
583
- // If it's Heshvan 30 it depends on the first anniversary;
584
- // if that was not Heshvan 30, use the day before Kislev 1.
585
- hDeath = abs2hebrew(hebrew2abs(hyear, KISLEV$1, 1) - 1);
586
- }
587
- else if (hDeath.mm == KISLEV$1 && hDeath.dd == 30 && shortKislev(hDeath.yy + 1)) {
588
- // If it's Kislev 30 it depends on the first anniversary;
589
- // if that was not Kislev 30, use the day before Teveth 1.
590
- hDeath = abs2hebrew(hebrew2abs(hyear, TEVET$1, 1) - 1);
591
- }
592
- else if (hDeath.mm == ADAR_II$1) {
593
- // If it's Adar II, use the same day in last month of year (Adar or Adar II).
594
- hDeath.mm = monthsInYear(hyear);
595
- }
596
- else if (hDeath.mm == ADAR_I$1 && hDeath.dd == 30 && !isLeapYear(hyear)) {
597
- // If it's the 30th in Adar I and year is not a leap year
598
- // (so Adar has only 29 days), use the last day in Shevat.
599
- hDeath.dd = 30;
600
- hDeath.mm = SHVAT;
601
- }
602
- // In all other cases, use the normal anniversary of the date of death.
603
- // advance day to rosh chodesh if needed
604
- if (hDeath.mm == CHESHVAN && hDeath.dd == 30 && !longCheshvan(hyear)) {
605
- hDeath.mm = KISLEV$1;
606
- hDeath.dd = 1;
607
- }
608
- else if (hDeath.mm == KISLEV$1 && hDeath.dd == 30 && shortKislev(hyear)) {
609
- hDeath.mm = TEVET$1;
610
- hDeath.dd = 1;
611
- }
612
- hDeath.yy = hyear;
613
- return hDeath;
537
+ let hDeath = toSimpleHebrewDate(date);
538
+ if (hyear <= hDeath.yy) {
539
+ // Hebrew year ${hyear} occurs on or before original date in ${hDeath.yy}
540
+ return undefined;
541
+ }
542
+ if (hDeath.mm === CHESHVAN && hDeath.dd === 30 && !longCheshvan(hDeath.yy + 1)) {
543
+ // If it's Heshvan 30 it depends on the first anniversary;
544
+ // if that was not Heshvan 30, use the day before Kislev 1.
545
+ hDeath = abs2hebrew(hebrew2abs(hyear, KISLEV$1, 1) - 1);
546
+ } else if (hDeath.mm === KISLEV$1 && hDeath.dd === 30 && shortKislev(hDeath.yy + 1)) {
547
+ // If it's Kislev 30 it depends on the first anniversary;
548
+ // if that was not Kislev 30, use the day before Teveth 1.
549
+ hDeath = abs2hebrew(hebrew2abs(hyear, TEVET$1, 1) - 1);
550
+ } else if (hDeath.mm === ADAR_II$1) {
551
+ // If it's Adar II, use the same day in last month of year (Adar or Adar II).
552
+ hDeath.mm = monthsInYear(hyear);
553
+ } else if (hDeath.mm === ADAR_I$1 && hDeath.dd === 30 && !isLeapYear(hyear)) {
554
+ // If it's the 30th in Adar I and year is not a leap year
555
+ // (so Adar has only 29 days), use the last day in Shevat.
556
+ hDeath.dd = 30;
557
+ hDeath.mm = SHVAT;
558
+ }
559
+ // In all other cases, use the normal anniversary of the date of death.
560
+ // advance day to rosh chodesh if needed
561
+ if (hDeath.mm === CHESHVAN && hDeath.dd === 30 && !longCheshvan(hyear)) {
562
+ hDeath.mm = KISLEV$1;
563
+ hDeath.dd = 1;
564
+ } else if (hDeath.mm === KISLEV$1 && hDeath.dd === 30 && shortKislev(hyear)) {
565
+ hDeath.mm = TEVET$1;
566
+ hDeath.dd = 1;
567
+ }
568
+ hDeath.yy = hyear;
569
+ return hDeath;
614
570
  }
615
571
  function getBirthdayHD(hyear, date) {
616
- const orig = toSimpleHebrewDate(date);
617
- const origYear = orig.yy;
618
- if (hyear === origYear) {
619
- return orig;
620
- }
621
- else if (hyear < origYear) {
622
- // Hebrew year ${hyear} occurs on or before original date in ${origYear}
623
- return undefined;
624
- }
625
- const isOrigLeap = isLeapYear(origYear);
626
- let month = orig.mm;
627
- let day = orig.dd;
628
- if ((month == ADAR_I$1 && !isOrigLeap) || (month == ADAR_II$1 && isOrigLeap)) {
629
- month = monthsInYear(hyear);
630
- }
631
- else if (month == CHESHVAN && day == 30 && !longCheshvan(hyear)) {
632
- month = KISLEV$1;
633
- day = 1;
634
- }
635
- else if (month == KISLEV$1 && day == 30 && shortKislev(hyear)) {
636
- month = TEVET$1;
637
- day = 1;
638
- }
639
- else if (month == ADAR_I$1 && day == 30 && isOrigLeap && !isLeapYear(hyear)) {
640
- month = NISAN$3;
641
- day = 1;
642
- }
643
- return { yy: hyear, mm: month, dd: day };
572
+ const orig = toSimpleHebrewDate(date);
573
+ const origYear = orig.yy;
574
+ if (hyear === origYear) {
575
+ return orig;
576
+ } else if (hyear < origYear) {
577
+ // Hebrew year ${hyear} occurs on or before original date in ${origYear}
578
+ return undefined;
579
+ }
580
+ const isOrigLeap = isLeapYear(origYear);
581
+ let month = orig.mm;
582
+ let day = orig.dd;
583
+ if (month === ADAR_I$1 && !isOrigLeap || month === ADAR_II$1 && isOrigLeap) {
584
+ month = monthsInYear(hyear);
585
+ } else if (month === CHESHVAN && day === 30 && !longCheshvan(hyear)) {
586
+ month = KISLEV$1;
587
+ day = 1;
588
+ } else if (month === KISLEV$1 && day === 30 && shortKislev(hyear)) {
589
+ month = TEVET$1;
590
+ day = 1;
591
+ } else if (month === ADAR_I$1 && day === 30 && isOrigLeap && !isLeapYear(hyear)) {
592
+ month = NISAN$3;
593
+ day = 1;
594
+ }
595
+ return {
596
+ yy: hyear,
597
+ mm: month,
598
+ dd: day
599
+ };
644
600
  }
645
601
 
646
602
  const GERESH = '׳';
647
603
  const GERSHAYIM = '״';
648
604
  const alefbet = {
649
- 'א': 1,
650
- 'ב': 2,
651
- 'ג': 3,
652
- 'ד': 4,
653
- 'ה': 5,
654
- 'ו': 6,
655
- 'ז': 7,
656
- 'ח': 8,
657
- 'ט': 9,
658
- 'י': 10,
659
- 'כ': 20,
660
- 'ל': 30,
661
- 'מ': 40,
662
- 'נ': 50,
663
- 'ס': 60,
664
- 'ע': 70,
665
- 'פ': 80,
666
- 'צ': 90,
667
- 'ק': 100,
668
- 'ר': 200,
669
- 'ש': 300,
670
- 'ת': 400,
605
+ א: 1,
606
+ ב: 2,
607
+ ג: 3,
608
+ ד: 4,
609
+ ה: 5,
610
+ ו: 6,
611
+ ז: 7,
612
+ ח: 8,
613
+ ט: 9,
614
+ י: 10,
615
+ כ: 20,
616
+ ל: 30,
617
+ מ: 40,
618
+ נ: 50,
619
+ ס: 60,
620
+ ע: 70,
621
+ פ: 80,
622
+ צ: 90,
623
+ ק: 100,
624
+ ר: 200,
625
+ ש: 300,
626
+ ת: 400
671
627
  };
672
628
  const heb2num = new Map();
673
629
  const num2heb = new Map();
674
630
  for (const [key, val] of Object.entries(alefbet)) {
675
- heb2num.set(key, val);
676
- num2heb.set(val, key);
631
+ heb2num.set(key, val);
632
+ num2heb.set(val, key);
677
633
  }
678
634
  function num2digits(num) {
679
- const digits = [];
680
- while (num > 0) {
681
- if (num === 15 || num === 16) {
682
- digits.push(9);
683
- digits.push(num - 9);
684
- break;
685
- }
686
- let incr = 100;
687
- let i;
688
- for (i = 400; i > num; i -= incr) {
689
- if (i === incr) {
690
- incr = incr / 10;
691
- }
692
- }
693
- digits.push(i);
694
- num -= i;
635
+ const digits = [];
636
+ while (num > 0) {
637
+ if (num === 15 || num === 16) {
638
+ digits.push(9);
639
+ digits.push(num - 9);
640
+ break;
641
+ }
642
+ let incr = 100;
643
+ let i;
644
+ for (i = 400; i > num; i -= incr) {
645
+ if (i === incr) {
646
+ incr = incr / 10;
647
+ }
695
648
  }
696
- return digits;
649
+ digits.push(i);
650
+ num -= i;
651
+ }
652
+ return digits;
697
653
  }
698
654
  /**
699
655
  * Converts a numerical value to a string of Hebrew letters.
@@ -710,31 +666,31 @@ function num2digits(num) {
710
666
  * @return {string}
711
667
  */
712
668
  function gematriya(num) {
713
- const num0 = num;
714
- const num1 = parseInt(num0, 10);
715
- if (!num1) {
716
- throw new TypeError(`invalid parameter to gematriya ${num}`);
717
- }
718
- let str = '';
719
- const thousands = Math.floor(num1 / 1000);
720
- if (thousands > 0 && thousands !== 5) {
721
- const tdigits = num2digits(thousands);
722
- for (const tdig of tdigits) {
723
- str += num2heb.get(tdig);
724
- }
725
- str += GERESH;
726
- }
727
- const digits = num2digits(num1 % 1000);
728
- if (digits.length == 1) {
729
- return str + num2heb.get(digits[0]) + GERESH;
669
+ const num0 = num;
670
+ const num1 = parseInt(num0, 10);
671
+ if (!num1) {
672
+ throw new TypeError(`invalid parameter to gematriya ${num}`);
673
+ }
674
+ let str = '';
675
+ const thousands = Math.floor(num1 / 1000);
676
+ if (thousands > 0 && thousands !== 5) {
677
+ const tdigits = num2digits(thousands);
678
+ for (const tdig of tdigits) {
679
+ str += num2heb.get(tdig);
730
680
  }
731
- for (let i = 0; i < digits.length; i++) {
732
- if (i + 1 === digits.length) {
733
- str += GERSHAYIM;
734
- }
735
- str += num2heb.get(digits[i]);
681
+ str += GERESH;
682
+ }
683
+ const digits = num2digits(num1 % 1000);
684
+ if (digits.length === 1) {
685
+ return str + num2heb.get(digits[0]) + GERESH;
686
+ }
687
+ for (let i = 0; i < digits.length; i++) {
688
+ if (i + 1 === digits.length) {
689
+ str += GERSHAYIM;
736
690
  }
737
- return str;
691
+ str += num2heb.get(digits[i]);
692
+ }
693
+ return str;
738
694
  }
739
695
  /**
740
696
  * Converts a string of Hebrew letters to a numerical value.
@@ -747,20 +703,189 @@ function gematriya(num) {
747
703
  * @return {number}
748
704
  */
749
705
  function gematriyaStrToNum(str) {
750
- let num = 0;
751
- const gereshIdx = str.indexOf(GERESH);
752
- if (gereshIdx !== -1 && gereshIdx !== str.length - 1) {
753
- const thousands = str.substring(0, gereshIdx);
754
- num += gematriyaStrToNum(thousands) * 1000;
755
- str = str.substring(gereshIdx);
756
- }
757
- for (const ch of str) {
758
- const n = heb2num.get(ch);
759
- if (typeof n === 'number') {
760
- num += n;
761
- }
706
+ let num = 0;
707
+ const gereshIdx = str.indexOf(GERESH);
708
+ if (gereshIdx !== -1 && gereshIdx !== str.length - 1) {
709
+ const thousands = str.substring(0, gereshIdx);
710
+ num += gematriyaStrToNum(thousands) * 1000;
711
+ str = str.substring(gereshIdx);
712
+ }
713
+ for (const ch of str) {
714
+ const n = heb2num.get(ch);
715
+ if (typeof n === 'number') {
716
+ num += n;
717
+ }
718
+ }
719
+ return num;
720
+ }
721
+
722
+ const sefirot = {
723
+ en: {
724
+ infix: 'within ',
725
+ infix26: 'within ',
726
+ words: ['', 'Lovingkindness', 'Might', 'Beauty', 'Eternity', 'Splendor', 'Foundation', 'Majesty']
727
+ },
728
+ he: {
729
+ infix: 'שֶׁבְּ',
730
+ infix26: 'שֶׁבִּ',
731
+ words: ['', 'חֶֽסֶד', 'גְבוּרָה', 'תִּפאֶרֶת', 'נֶּֽצַח', 'הוֹד', 'יְּסוֹד', 'מַּלְכוּת']
732
+ },
733
+ translit: {
734
+ infix: "sheb'",
735
+ infix26: 'shebi',
736
+ words: ['', 'Chesed', 'Gevurah', 'Tiferet', 'Netzach', 'Hod', 'Yesod', 'Malkhut']
737
+ }
738
+ };
739
+ function checkDay(omerDay) {
740
+ if (omerDay < 1 || omerDay > 49) {
741
+ throw new RangeError(`Invalid Omer day ${omerDay}`);
742
+ }
743
+ }
744
+ function getWeeks(omerDay) {
745
+ const weekNum = Math.floor((omerDay - 1) / 7) + 1;
746
+ const daysWithinWeeks = omerDay % 7 || 7;
747
+ return [weekNum, daysWithinWeeks];
748
+ }
749
+ /**
750
+ * Returns the sefira. For example, on day 8
751
+ * חֶֽסֶד שֶׁבִּגְבוּרָה
752
+ * Chesed shebiGevurah
753
+ * Lovingkindness within Might
754
+ * @param omerDay the day of the omer, 1-49 inclusive
755
+ * @param lang `en` (English), `he` (Hebrew with nikud), or `translit` (Hebrew in Sephardic transliteration)
756
+ * @returns a string such as `Lovingkindness within Might` or `חֶֽסֶד שֶׁבִּגְבוּרָה`
757
+ */
758
+ function omerSefira(omerDay, lang) {
759
+ checkDay(omerDay);
760
+ const [weekNum, daysWithinWeeks] = getWeeks(omerDay);
761
+ const config = sefirot[lang];
762
+ const week = config.words[weekNum];
763
+ const dayWithinWeek = config.words[daysWithinWeeks];
764
+ const infix = weekNum === 2 || weekNum === 6 ? config.infix26 : config.infix;
765
+ return (dayWithinWeek + ' ' + infix + week).normalize();
766
+ }
767
+ /**
768
+ * Returns a sentence with that evening's omer count
769
+ * @param omerDay the day of the omer, 1-49 inclusive
770
+ * @param lang `en` (English), `he` (Hebrew with nikud)
771
+ * @returns a string such as `Today is 10 days, which is 1 week and 3 days of the Omer`
772
+ * or `הַיוֹם עֲשָׂרָה יָמִים, שְׁהֵם שָׁבוּעַ אֶחָד וְשְׁלוֹשָׁה יָמִים לָעוֹמֶר`
773
+ */
774
+ function omerTodayIs(omerDay, lang) {
775
+ checkDay(omerDay);
776
+ if (lang === 'en') {
777
+ return omerTodayIsEn(omerDay);
778
+ } else if (lang === 'he') {
779
+ return omerTodayIsHe(omerDay);
780
+ } else {
781
+ return undefined;
782
+ }
783
+ }
784
+ function omerTodayIsEn(omerDay) {
785
+ const [weekNumber, daysWithinWeeks] = getWeeks(omerDay);
786
+ const totalDaysStr = omerDay === 1 ? 'day' : 'days';
787
+ let str = `Today is ${omerDay} ${totalDaysStr}`;
788
+ if (weekNumber > 1 || omerDay === 7) {
789
+ const day7 = daysWithinWeeks === 7;
790
+ const numWeeks = day7 ? weekNumber : weekNumber - 1;
791
+ const weeksStr = numWeeks === 1 ? 'week' : 'weeks';
792
+ str += `, which is ${numWeeks} ${weeksStr}`;
793
+ if (!day7) {
794
+ const daysStr = daysWithinWeeks === 1 ? 'day' : 'days';
795
+ str += ` and ${daysWithinWeeks} ${daysStr}`;
796
+ }
797
+ }
798
+ return str + ' of the Omer';
799
+ }
800
+ // adapted from pip hdate package (GPL)
801
+ // https://github.com/py-libhdate/py-libhdate/blob/master/hdate/date.py
802
+ const tens = ['', 'עֲשָׂרָה', 'עֶשְׂרִים', 'שְׁלוֹשִׁים', 'אַרְבָּעִים'];
803
+ const ones = ['', 'אֶחָד', 'שְׁנַיִם', 'שְׁלוֹשָׁה', 'אַרְבָּעָה', 'חֲמִשָּׁה', 'שִׁשָּׁה', 'שִׁבְעָה', 'שְׁמוֹנָה', 'תִּשְׁעָה'];
804
+ const shnei = 'שְׁנֵי';
805
+ const yamim = 'יָמִים';
806
+ const shneiYamim = shnei + ' ' + yamim;
807
+ const shavuot = 'שָׁבוּעוֹת';
808
+ const yom = 'יוֹם';
809
+ const yomEchad = yom + ' ' + ones[1];
810
+ function omerTodayIsHe(omerDay) {
811
+ const ten = Math.floor(omerDay / 10);
812
+ const one = omerDay % 10;
813
+ let str = 'הַיּוֹם ';
814
+ if (10 < omerDay && omerDay < 20) {
815
+ str += ones[one] + ' עָשָׂר';
816
+ } else if (omerDay > 9) {
817
+ str += ones[one];
818
+ if (one) {
819
+ str += ' ';
820
+ str += ten === 3 ? 'וּ' : 'וְ';
821
+ }
822
+ }
823
+ if (omerDay > 2) {
824
+ if (omerDay > 20 || omerDay === 10 || omerDay === 20) {
825
+ str += tens[ten];
826
+ }
827
+ if (omerDay < 11) {
828
+ str += ones[one] + ' ' + yamim + ' ';
829
+ } else {
830
+ str += ' ' + yom + ' ';
831
+ }
832
+ } else if (omerDay === 1) {
833
+ str += yomEchad + ' ';
834
+ } else {
835
+ // omer == 2
836
+ str += shneiYamim + ' ';
837
+ }
838
+ if (omerDay > 6) {
839
+ str = str.trim(); // remove trailing space before comma
840
+ str += ', שְׁהֵם ';
841
+ const weeks = Math.floor(omerDay / 7);
842
+ const days = omerDay % 7;
843
+ if (weeks > 2) {
844
+ str += ones[weeks] + ' ' + shavuot + ' ';
845
+ } else if (weeks === 1) {
846
+ str += 'שָׁבֽוּעַ' + ' ' + ones[1] + ' ';
847
+ } else {
848
+ // weeks == 2
849
+ str += shnei + ' ' + shavuot + ' ';
850
+ }
851
+ if (days) {
852
+ if (days === 2 || days === 3) {
853
+ str += 'וּ';
854
+ } else if (days === 5) {
855
+ str += 'וַ';
856
+ } else {
857
+ str += 'וְ';
858
+ }
859
+ if (days > 2) {
860
+ str += ones[days] + ' ' + yamim + ' ';
861
+ } else if (days === 1) {
862
+ str += yomEchad + ' ';
863
+ } else {
864
+ // days == 2
865
+ str += shneiYamim + ' ';
866
+ }
762
867
  }
763
- return num;
868
+ }
869
+ str += 'לָעֽוֹמֶר';
870
+ return str.normalize();
871
+ }
872
+ /**
873
+ * Returns an emoji number symbol with a circle, for example `㊲`
874
+ * from the “Enclosed CJK Letters and Months” block of the Unicode standard
875
+ * @param omerDay the day of the omer, 1-49 inclusive
876
+ * @returns a single Unicode character from `①` through `㊾`
877
+ */
878
+ function omerEmoji(omerDay) {
879
+ checkDay(omerDay);
880
+ if (omerDay <= 20) {
881
+ return String.fromCodePoint(9312 + omerDay - 1);
882
+ } else if (omerDay <= 35) {
883
+ // between 21 and 35 inclusive
884
+ return String.fromCodePoint(12881 + omerDay - 21);
885
+ } else {
886
+ // between 36 and 49 inclusive
887
+ return String.fromCodePoint(12977 + omerDay - 36);
888
+ }
764
889
  }
765
890
 
766
891
  const noopLocale = {
@@ -6108,32 +6233,16 @@ class GeoLocation {
6108
6233
  * the <code>TimeZone</code> for the location.
6109
6234
  */
6110
6235
  constructor(name, latitude, longitude, elevation, timeZoneId) {
6236
+ /**
6237
+ * @private
6238
+ */
6239
+ this.locationName = null;
6111
6240
  this.setLocationName(name);
6112
6241
  this.setLatitude(latitude);
6113
6242
  this.setLongitude(longitude);
6114
6243
  this.setElevation(elevation);
6115
6244
  this.setTimeZone(timeZoneId);
6116
6245
  }
6117
- /**
6118
- * @private
6119
- */
6120
- latitude;
6121
- /**
6122
- * @private
6123
- */
6124
- longitude;
6125
- /**
6126
- * @private
6127
- */
6128
- locationName = null;
6129
- /**
6130
- * @private
6131
- */
6132
- timeZoneId;
6133
- /**
6134
- * @private
6135
- */
6136
- elevation;
6137
6246
  /**
6138
6247
  * Method to get the elevation in Meters.
6139
6248
  *
@@ -6256,39 +6365,6 @@ class NOAACalculator {
6256
6365
  this.date = date;
6257
6366
  this.geoLocation = geoLocation;
6258
6367
  }
6259
- /**
6260
- * The zenith of astronomical sunrise and sunset. The sun is 90&deg; from the vertical 0&deg;
6261
- * @private
6262
- */
6263
- static GEOMETRIC_ZENITH = 90;
6264
- /**
6265
- * Default value for Sun's zenith and true rise/set Zenith (used in this class and subclasses) is the angle that the
6266
- * center of the Sun makes to a line perpendicular to the Earth's surface. If the Sun were a point and the Earth
6267
- * were without an atmosphere, true sunset and sunrise would correspond to a 90&deg; zenith. Because the Sun is not
6268
- * a point, and because the atmosphere refracts light, this 90&deg; zenith does not, in fact, correspond to true
6269
- * sunset or sunrise, instead the center of the Sun's disk must lie just below the horizon for the upper edge to be
6270
- * obscured. This means that a zenith of just above 90&deg; must be used. The Sun subtends an angle of 16 minutes of
6271
- * arc, and atmospheric refraction accounts for
6272
- * 34 minutes or so, giving a total of 50
6273
- * arcminutes. The total value for ZENITH is 90+(5/6) or 90.8333333&deg; for true sunrise/sunset.
6274
- */
6275
- // const ZENITH: number = GEOMETRIC_ZENITH + 5.0 / 6.0;
6276
- /** Sun's zenith at civil twilight (96&deg;). */
6277
- static CIVIL_ZENITH = 96;
6278
- /** Sun's zenith at nautical twilight (102&deg;). */
6279
- static NAUTICAL_ZENITH = 102;
6280
- /** Sun's zenith at astronomical twilight (108&deg;). */
6281
- static ASTRONOMICAL_ZENITH = 108;
6282
- /**
6283
- * The Java Calendar encapsulated by this class to track the current date used by the class
6284
- * @private
6285
- */
6286
- date;
6287
- /**
6288
- * the {@link GeoLocation} used for calculations.
6289
- * @private
6290
- */
6291
- geoLocation;
6292
6368
  /**
6293
6369
  * The getSunrise method Returns a `Date` representing the
6294
6370
  * {@link getElevationAdjustment elevation adjusted} sunrise time. The zenith used
@@ -6638,16 +6714,6 @@ class NOAACalculator {
6638
6714
  }
6639
6715
  return adjustedZenith;
6640
6716
  }
6641
- /**
6642
- * The <a href="http://en.wikipedia.org/wiki/Julian_day">Julian day</a> of January 1, 2000
6643
- * @private
6644
- */
6645
- static JULIAN_DAY_JAN_1_2000 = 2451545;
6646
- /**
6647
- * Julian days per century
6648
- * @private
6649
- */
6650
- static JULIAN_DAYS_PER_CENTURY = 36525;
6651
6717
  /**
6652
6718
  * A method that calculates UTC sunrise as well as any time based on an angle above or below sunrise.
6653
6719
  * @param date
@@ -7187,6 +7253,39 @@ class NOAACalculator {
7187
7253
  return timeUTC;
7188
7254
  }
7189
7255
  }
7256
+ /**
7257
+ * The zenith of astronomical sunrise and sunset. The sun is 90&deg; from the vertical 0&deg;
7258
+ * @private
7259
+ */
7260
+ NOAACalculator.GEOMETRIC_ZENITH = 90;
7261
+ /**
7262
+ * Default value for Sun's zenith and true rise/set Zenith (used in this class and subclasses) is the angle that the
7263
+ * center of the Sun makes to a line perpendicular to the Earth's surface. If the Sun were a point and the Earth
7264
+ * were without an atmosphere, true sunset and sunrise would correspond to a 90&deg; zenith. Because the Sun is not
7265
+ * a point, and because the atmosphere refracts light, this 90&deg; zenith does not, in fact, correspond to true
7266
+ * sunset or sunrise, instead the center of the Sun's disk must lie just below the horizon for the upper edge to be
7267
+ * obscured. This means that a zenith of just above 90&deg; must be used. The Sun subtends an angle of 16 minutes of
7268
+ * arc, and atmospheric refraction accounts for
7269
+ * 34 minutes or so, giving a total of 50
7270
+ * arcminutes. The total value for ZENITH is 90+(5/6) or 90.8333333&deg; for true sunrise/sunset.
7271
+ */
7272
+ // const ZENITH: number = GEOMETRIC_ZENITH + 5.0 / 6.0;
7273
+ /** Sun's zenith at civil twilight (96&deg;). */
7274
+ NOAACalculator.CIVIL_ZENITH = 96;
7275
+ /** Sun's zenith at nautical twilight (102&deg;). */
7276
+ NOAACalculator.NAUTICAL_ZENITH = 102;
7277
+ /** Sun's zenith at astronomical twilight (108&deg;). */
7278
+ NOAACalculator.ASTRONOMICAL_ZENITH = 108;
7279
+ /**
7280
+ * The <a href="http://en.wikipedia.org/wiki/Julian_day">Julian day</a> of January 1, 2000
7281
+ * @private
7282
+ */
7283
+ NOAACalculator.JULIAN_DAY_JAN_1_2000 = 2451545;
7284
+ /**
7285
+ * Julian days per century
7286
+ * @private
7287
+ */
7288
+ NOAACalculator.JULIAN_DAYS_PER_CENTURY = 36525;
7190
7289
 
7191
7290
  /*
7192
7291
  Hebcal - A Jewish Calendar Generator
@@ -8400,9 +8499,6 @@ class MoladEvent extends Event {
8400
8499
  }
8401
8500
  }
8402
8501
 
8403
- const sefirot = [null, 'Lovingkindness', 'Might', 'Beauty', 'Eternity', 'Splendor', 'Foundation', 'Majesty'];
8404
- const sefirotTranslit = [null, 'Chesed', 'Gevurah', 'Tiferet', 'Netzach', 'Hod', 'Yesod', 'Malkhut'];
8405
-
8406
8502
  /** Represents a day 1-49 of counting the Omer from Pesach to Shavuot */
8407
8503
  class OmerEvent extends Event {
8408
8504
  /**
@@ -8423,39 +8519,10 @@ class OmerEvent extends Event {
8423
8519
  * @return {string}
8424
8520
  */
8425
8521
  sefira(lang = 'en') {
8426
- if (lang === 'he') {
8427
- return this.sefiraHe();
8428
- } else if (lang === 'translit') {
8429
- return this.sefiraTranslit();
8430
- } else {
8431
- const week = sefirot[this.weekNumber];
8432
- const dayWithinWeek = sefirot[this.daysWithinWeeks];
8433
- return `${dayWithinWeek} within ${week}`;
8522
+ if (lang !== 'he' && lang !== 'translit') {
8523
+ lang = 'en';
8434
8524
  }
8435
- }
8436
- /**
8437
- * @private
8438
- * @return {string}
8439
- */
8440
- sefiraTranslit() {
8441
- const weekNum = this.weekNumber;
8442
- const translitWeek = sefirotTranslit[weekNum];
8443
- const translitDayWithinWeek = sefirotTranslit[this.daysWithinWeeks];
8444
- const translitPrefix = weekNum === 2 || weekNum === 6 ? 'shebi' : `sheb'`;
8445
- return `${translitDayWithinWeek} ${translitPrefix}${translitWeek}`;
8446
- }
8447
- /**
8448
- * @private
8449
- * @return {string}
8450
- */
8451
- sefiraHe() {
8452
- const weekNum = this.weekNumber;
8453
- const week = sefirot[weekNum];
8454
- const dayWithinWeek = sefirot[this.daysWithinWeeks];
8455
- const heWeek = Locale.gettext(week, 'he');
8456
- const heDayWithinWeek = Locale.gettext(dayWithinWeek, 'he');
8457
- const hePrefix = weekNum === 2 || weekNum === 6 ? 'שֶׁבִּ' : 'שֶׁבְּ';
8458
- return `${heDayWithinWeek} ${hePrefix}${heWeek}`.normalize();
8525
+ return omerSefira(this.omer, lang);
8459
8526
  }
8460
8527
  /**
8461
8528
  * @todo use gettext()
@@ -8479,16 +8546,7 @@ class OmerEvent extends Event {
8479
8546
  /** @return {string} */
8480
8547
  getEmoji() {
8481
8548
  if (typeof this.emoji === 'string') return this.emoji;
8482
- const number = this.omer;
8483
- if (number <= 20) {
8484
- return String.fromCodePoint(9312 + number - 1);
8485
- } else if (number <= 35) {
8486
- // between 21 and 35 inclusive
8487
- return String.fromCodePoint(12881 + number - 21);
8488
- } else {
8489
- // between 36 and 49 inclusive
8490
- return String.fromCodePoint(12977 + number - 36);
8491
- }
8549
+ return omerEmoji(this.omer);
8492
8550
  }
8493
8551
  /** @return {number} */
8494
8552
  getWeeks() {
@@ -8509,23 +8567,12 @@ class OmerEvent extends Event {
8509
8567
  locale = locale.toLowerCase();
8510
8568
  }
8511
8569
  if (locale === 'he') {
8512
- return getTodayIsHe(this.omer);
8570
+ return omerTodayIs(this.omer, 'he');
8513
8571
  } else if (locale === 'he-x-nonikud') {
8514
- return Locale.hebrewStripNikkud(getTodayIsHe(this.omer));
8515
- }
8516
- const totalDaysStr = this.omer === 1 ? 'day' : 'days';
8517
- let str = `Today is ${this.omer} ${totalDaysStr}`;
8518
- if (this.weekNumber > 1 || this.omer === 7) {
8519
- const day7 = this.daysWithinWeeks === 7;
8520
- const numWeeks = day7 ? this.weekNumber : this.weekNumber - 1;
8521
- const weeksStr = numWeeks === 1 ? 'week' : 'weeks';
8522
- str += `, which is ${numWeeks} ${weeksStr}`;
8523
- if (!day7) {
8524
- const daysStr = this.daysWithinWeeks === 1 ? 'day' : 'days';
8525
- str += ` and ${this.daysWithinWeeks} ${daysStr}`;
8526
- }
8572
+ const str = omerTodayIs(this.omer, 'he');
8573
+ return Locale.hebrewStripNikkud(str);
8527
8574
  }
8528
- return str + ' of the Omer';
8575
+ return omerTodayIs(this.omer, 'en');
8529
8576
  }
8530
8577
  /** @return {string} */
8531
8578
  url() {
@@ -8533,79 +8580,6 @@ class OmerEvent extends Event {
8533
8580
  }
8534
8581
  }
8535
8582
 
8536
- // adapted from pip hdate package (GPL)
8537
- // https://github.com/py-libhdate/py-libhdate/blob/master/hdate/date.py
8538
-
8539
- const tens = ['', 'עֲשָׂרָה', 'עֶשְׂרִים', 'שְׁלוֹשִׁים', 'אַרְבָּעִים'];
8540
- const ones = ['', 'אֶחָד', 'שְׁנַיִם', 'שְׁלוֹשָׁה', 'אַרְבָּעָה', 'חֲמִשָׁה', 'שִׁשָׁה', 'שִׁבְעָה', 'שְׁמוֹנָה', 'תִּשְׁעָה'];
8541
- const shnei = 'שְׁנֵי';
8542
- const yamim = 'יָמִים';
8543
- const shneiYamim = shnei + ' ' + yamim;
8544
- const shavuot = 'שָׁבוּעוֹת';
8545
- const yom = 'יוֹם';
8546
- const yomEchad = yom + ' ' + ones[1];
8547
-
8548
- /**
8549
- * @private
8550
- * @param {number} omer
8551
- * @return {string}
8552
- */
8553
- function getTodayIsHe(omer) {
8554
- const ten = Math.floor(omer / 10);
8555
- const one = omer % 10;
8556
- let str = 'הַיוֹם ';
8557
- if (10 < omer && omer < 20) {
8558
- str += ones[one] + ' עָשָׂר';
8559
- } else if (omer > 9) {
8560
- str += ones[one];
8561
- if (one) {
8562
- str += ' וְ';
8563
- }
8564
- }
8565
- if (omer > 2) {
8566
- if (omer > 20 || omer === 10 || omer === 20) {
8567
- str += tens[ten];
8568
- }
8569
- if (omer < 11) {
8570
- str += ones[one] + ' ' + yamim + ' ';
8571
- } else {
8572
- str += ' ' + yom + ' ';
8573
- }
8574
- } else if (omer === 1) {
8575
- str += yomEchad + ' ';
8576
- } else {
8577
- // omer == 2
8578
- str += shneiYamim + ' ';
8579
- }
8580
- if (omer > 6) {
8581
- str = str.trim(); // remove trailing space before comma
8582
- str += ', שְׁהֵם ';
8583
- const weeks = Math.floor(omer / 7);
8584
- const days = omer % 7;
8585
- if (weeks > 2) {
8586
- str += ones[weeks] + ' ' + shavuot + ' ';
8587
- } else if (weeks == 1) {
8588
- str += 'שָׁבוּעַ' + ' ' + ones[1] + ' ';
8589
- } else {
8590
- // weeks == 2
8591
- str += shnei + ' ' + shavuot + ' ';
8592
- }
8593
- if (days) {
8594
- str += 'וְ';
8595
- if (days > 2) {
8596
- str += ones[days] + ' ' + yamim + ' ';
8597
- } else if (days == 1) {
8598
- str += yomEchad + ' ';
8599
- } else {
8600
- // days == 2
8601
- str += shneiYamim + ' ';
8602
- }
8603
- }
8604
- }
8605
- str += 'לָעוֹמֶר';
8606
- return str.normalize();
8607
- }
8608
-
8609
8583
  class QuickLRU extends Map {
8610
8584
  #size = 0;
8611
8585
  #cache = new Map();
@@ -10379,7 +10353,7 @@ class DailyLearning {
10379
10353
  }
10380
10354
 
10381
10355
  // DO NOT EDIT THIS AUTO-GENERATED FILE!
10382
- const version = '5.3.2';
10356
+ const version = '5.3.4';
10383
10357
 
10384
10358
  const NONE$1 = 0;
10385
10359
  const HALF = 1;